From dedf583301056ecdb7457994c94924e41a790a1c Mon Sep 17 00:00:00 2001 From: andrewbents Date: Wed, 13 Sep 2017 10:35:15 +0700 Subject: [PATCH] add sessionTimeout option to config --- README.md | 9 ++++++++ src/app/app.component.ts | 6 ++--- .../sg-rules/sg-rules.component.spec.ts | 1 - src/app/shared/services/user.service.spec.ts | 2 +- src/app/shared/services/user.service.ts | 23 +++++++++++++++---- src/config/config.json | 1 + 6 files changed, 33 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index 7f1a79e5f1..6c82059377 100644 --- a/README.md +++ b/README.md @@ -306,6 +306,15 @@ In this sections you can specify limits for custom offerings in the following fo Any of these parameters may be left unspecified, in which case 0 will be used for min and infinity will be used for max. +### sessionTimeout + +Number of minutes a user's session should stay active. After this time passes the user is +logged out. + +Defaults to `30` (minutes). + +You can set it to `0` to turn this off, although in this case the session is likely to expire on the server side. + ### allowReorderingSidebar A boolean value which allows or forbids a user to reorder links in the main sidebar diff --git a/src/app/app.component.ts b/src/app/app.component.ts index 881c67bde7..053d682f41 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -22,7 +22,7 @@ import { ZoneService } from './shared/services/zone.service'; templateUrl: './app.component.html', styleUrls: ['./app.component.scss'] }) -export class AppComponent implements OnInit{ +export class AppComponent implements OnInit { @ViewChild(MdlLayoutComponent) public layoutComponent: MdlLayoutComponent; public loggedIn: boolean; @@ -57,13 +57,13 @@ export class AppComponent implements OnInit{ this.loggedIn = isLoggedIn; this.updateAccount(this.loggedIn); if (isLoggedIn) { - this.userService.startInactivityCounter(); + this.userService.startIdleMonitor(); this.loadSettings(); this.zoneService .areAllZonesBasic() .subscribe(basic => (this.disableSecurityGroups = basic)); } else { - this.userService.clearInactivityTimer(); + this.userService.stopIdleMonitor(); } this.asyncJobService.completeAllJobs(); this.cacheService.invalidateAll(); diff --git a/src/app/security-group/sg-rules/sg-rules.component.spec.ts b/src/app/security-group/sg-rules/sg-rules.component.spec.ts index 74087e067b..58aadbcb3e 100644 --- a/src/app/security-group/sg-rules/sg-rules.component.spec.ts +++ b/src/app/security-group/sg-rules/sg-rules.component.spec.ts @@ -59,7 +59,6 @@ describe('Security group firewall rules component', () => { TestBed.compileComponents().then(() => { f = TestBed.createComponent(SgRulesComponent); comp = f.componentInstance; - console.log(comp); }); })); diff --git a/src/app/shared/services/user.service.spec.ts b/src/app/shared/services/user.service.spec.ts index e56db08cbf..f2513d8b84 100644 --- a/src/app/shared/services/user.service.spec.ts +++ b/src/app/shared/services/user.service.spec.ts @@ -202,7 +202,7 @@ describe('User service session', () => { const inactivityTimeout = 10; const logout = spyOn(router, 'navigate').and.callThrough(); const refresh = spyOn(userService, 'sendRefreshRequest'); - userService.startInactivityCounter(); + userService.startIdleMonitor(); userService.setInactivityTimeout(inactivityTimeout).subscribe(); tick(getRefreshInterval() * (inactivityTimeout - 1) * 60 / refreshInterval); diff --git a/src/app/shared/services/user.service.ts b/src/app/shared/services/user.service.ts index ffd186a5e3..bae502d511 100644 --- a/src/app/shared/services/user.service.ts +++ b/src/app/shared/services/user.service.ts @@ -10,6 +10,7 @@ import { RouterUtilsService } from './router-utils.service'; import { UserTagService } from './tags/user-tag.service'; const DEFAULT_SESSION_REFRESH_INTERVAL = 60; +const DEFAULT_SESSION_TIMEOUT = 30; @Injectable() @BackendResource({ @@ -40,8 +41,7 @@ export class UserService extends BaseBackendService { return this.sendCommand('register;Keys', { id }).map(res => res.userkeys); } - - public startInactivityCounter() { + public startIdleMonitor() { const sessionRefreshInterval = this.getSessionRefreshInterval(); this.getInactivityTimeout().subscribe(inactivityTimeout => { @@ -67,8 +67,8 @@ export class UserService extends BaseBackendService { return this.userTagService.getSessionTimeout() .switchMap(timeout => { - if (Number.isNaN(timeout)) { - return this.userTagService.setSessionTimeout(0); + if (Number.isNaN(timeout) || timeout < 0) { + return Observable.of(this.getSessionTimeout()); } return Observable.of(timeout); @@ -116,6 +116,11 @@ export class UserService extends BaseBackendService { clearInterval(this.refreshTimer); } + public stopIdleMonitor(): void { + this.clearInactivityTimer(); + this.inactivityTimeout = 0; + } + private setInactivityTimer(): void { if (this.sessionRefreshInterval && this.inactivityTimeout) { this.refreshTimer = setInterval( @@ -134,4 +139,14 @@ export class UserService extends BaseBackendService { return DEFAULT_SESSION_REFRESH_INTERVAL; } + + private getSessionTimeout(): number { + const sessionTimeout = this.configService.get('sessionTimeout'); + + if (Number.isInteger(sessionTimeout) && sessionTimeout > 0) { + return sessionTimeout; + } + + return DEFAULT_SESSION_TIMEOUT; + } } diff --git a/src/config/config.json b/src/config/config.json index 6a05fea0a9..c42635eec9 100644 --- a/src/config/config.json +++ b/src/config/config.json @@ -257,6 +257,7 @@ }, "apiDocLink": "https://cloudstack.apache.org/api/apidocs-4.9/", "sessionRefreshInterval": 60, + "sessionTimeout": 30, "allowReorderingSidebar": false, "defaultServiceOfferingConfig": { "031a55bb-5d6b-4336-ab93-d5dead28a887": {