#3527 fix - Added pack/license actions and a lot of bugfixing
| .. | .. |
|---|
| 35 | 35 | //res.addHeader("Access-Control-Request-Headers", "*"); |
|---|
| 36 | 36 | res.addHeader("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS"); |
|---|
| 37 | 37 | res.addHeader("Access-Control-Allow-Headers", "X-SECURIS-TOKEN, Content-Type"); |
|---|
| 38 | | - res.addHeader("Access-Control-Expose-Headers", "X-SECURIS-ERROR-MSG, X-SECURIS-ERROR-CODE, Content-Type"); |
|---|
| 38 | + res.addHeader("Access-Control-Expose-Headers", "X-SECURIS-ERROR-MSG, X-SECURIS-ERROR-CODE, Content-Type, Content-Disposition"); |
|---|
| 39 | 39 | |
|---|
| 40 | 40 | // LOG.info("Added header to: " + res.getHeaderNames()); |
|---|
| 41 | 41 | if (!req.getMethod().equals("OPTIONS")) { |
|---|
| .. | .. |
|---|
| 39 | 39 | "angular-2-local-storage": "^1.0.1", |
|---|
| 40 | 40 | "angular-in-memory-web-api": "~0.2.4", |
|---|
| 41 | 41 | "core-js": "^2.4.1", |
|---|
| 42 | + "file-saver": "^1.3.3", |
|---|
| 42 | 43 | "hammerjs": "^2.0.8", |
|---|
| 43 | 44 | "ng2-toastr": "^1.5.1", |
|---|
| 44 | 45 | "rxjs": "^5.0.1", |
|---|
| .. | .. |
|---|
| 46 | 47 | "zone.js": "^0.7.4" |
|---|
| 47 | 48 | }, |
|---|
| 48 | 49 | "devDependencies": { |
|---|
| 50 | + "@types/file-saver": "0.0.0", |
|---|
| 49 | 51 | "@types/jasmine": "2.5.36", |
|---|
| 50 | 52 | "@types/node": "^6.0.46", |
|---|
| 51 | 53 | "canonical-path": "0.0.2", |
|---|
| .. | .. |
|---|
| 35 | 35 | |
|---|
| 36 | 36 | import { LoginFormComponent } from './forms/login.form.component'; |
|---|
| 37 | 37 | import { LicenseFormComponent } from './forms/license.form.component'; |
|---|
| 38 | +import { ApplicationFormComponent } from './forms/application.form.component'; |
|---|
| 39 | +import { PackFormComponent } from "./forms/pack.form.component"; |
|---|
| 38 | 40 | import { LicenseTypeFormComponent } from './forms/licensetype.form.component'; |
|---|
| 39 | 41 | import { OrganizationFormComponent } from './forms/organization.form.component'; |
|---|
| 40 | 42 | import { UserFormComponent } from './forms/user.form.component'; |
|---|
| 41 | | -import { ApplicationFormComponent } from './forms/application.form.component'; |
|---|
| 42 | | -import { PackFormComponent } from "./forms/pack.form.component"; |
|---|
| 43 | 43 | |
|---|
| 44 | 44 | |
|---|
| 45 | 45 | import { appRoutes, appRoutingProviders } from './app.routes'; |
|---|
| .. | .. |
|---|
| 23 | 23 | |
|---|
| 24 | 24 | // Set the default 'Content-Type' header |
|---|
| 25 | 25 | this.headers.set('Content-Type', 'application/json'); |
|---|
| 26 | | - let token = this.store.get<string>('token'); |
|---|
| 27 | | - if (token) { |
|---|
| 28 | | - this.headers.set('X-SECURIS-TOKEN', token); |
|---|
| 29 | | - |
|---|
| 30 | | - } |
|---|
| 31 | 26 | |
|---|
| 32 | 27 | } |
|---|
| 33 | 28 | } |
|---|
| .. | .. |
|---|
| 35 | 30 | @Injectable() |
|---|
| 36 | 31 | export class ApiXHRBackend extends XHRBackend { |
|---|
| 37 | 32 | |
|---|
| 38 | | - constructor(_browserXHR: BrowserXhr, _baseResponseOptions: ResponseOptions, _xsrfStrategy: XSRFStrategy) { |
|---|
| 33 | + constructor(_browserXHR: BrowserXhr, _baseResponseOptions: ResponseOptions, _xsrfStrategy: XSRFStrategy, private store: LocalStorageService) { |
|---|
| 39 | 34 | super(_browserXHR, _baseResponseOptions, _xsrfStrategy); |
|---|
| 40 | 35 | } |
|---|
| 41 | 36 | |
|---|
| 42 | 37 | createConnection(request: Request): XHRConnection { |
|---|
| 38 | + let token = this.store.get<string>('token'); |
|---|
| 39 | + if (token) { |
|---|
| 40 | + request.headers.set('X-SECURIS-TOKEN', token); |
|---|
| 41 | + } |
|---|
| 43 | 42 | if (!request.url.endsWith('.js') && !request.url.endsWith('.json') && !request.url.endsWith('.html') && !request.url.endsWith('.svg')){ |
|---|
| 44 | 43 | request.url = 'http://localhost:8080/securis/' + request.url; // prefix base url |
|---|
| 45 | 44 | } |
|---|
| .. | .. |
|---|
| 56 | 56 | protected abstract init(): void; |
|---|
| 57 | 57 | protected abstract goBack(): void; |
|---|
| 58 | 58 | |
|---|
| 59 | | - save() { |
|---|
| 60 | | - var command = this.isNew ? this.resourceServices.create(this.data) : this.resourceServices.modify(this.data.id, this.data); |
|---|
| 59 | + save(fieldId : string = 'id') { |
|---|
| 60 | + var command = this.isNew ? this.resourceServices.create(this.data) : this.resourceServices.modify(this.data[fieldId], this.data); |
|---|
| 61 | 61 | command.subscribe( |
|---|
| 62 | 62 | data => { |
|---|
| 63 | 63 | this.toaster.success(this.$L.get('{} saved sucessfully', this.resourceName.capitalize())); |
|---|
| .. | .. |
|---|
| 94 | 94 | this.form_title = this.$L.get('{} data', this.resourceName.capitalize()); |
|---|
| 95 | 95 | this.isNew = true; |
|---|
| 96 | 96 | !!this.route && this.route.params.subscribe(params => { |
|---|
| 97 | | - var eleId = +params[idparam]; // (+) converts string 'id' to a number |
|---|
| 97 | + var eleId = params[idparam]; |
|---|
| 98 | 98 | if (!eleId) { |
|---|
| 99 | 99 | this.data = {}; |
|---|
| 100 | 100 | Object.keys(default_values).forEach((k : string) => this.data[k] = default_values[k]); |
|---|
| .. | .. |
|---|
| 50 | 50 | reader.readAsText(file); |
|---|
| 51 | 51 | this.requestFileUploader.clear(); |
|---|
| 52 | 52 | } |
|---|
| 53 | + |
|---|
| 54 | + |
|---|
| 55 | + licenseAction(action: string) { |
|---|
| 56 | + return this.licenses[action](this.data.id).subscribe( |
|---|
| 57 | + (actionResponse : any) => { |
|---|
| 58 | + this.toaster.success(this.$L.get('Action "{}" executed successfully', action)); |
|---|
| 59 | + this.reload(); |
|---|
| 60 | + }, |
|---|
| 61 | + (err : any) => this.toaster.error(this.$L.get('Action "{}" failed', action)) |
|---|
| 62 | + ); |
|---|
| 63 | + } |
|---|
| 64 | + |
|---|
| 53 | 65 | |
|---|
| 66 | + canBeDeleted() : boolean { |
|---|
| 67 | + return !this.isNew && this.licenses.isActionAvailable('delete', this.data); |
|---|
| 68 | + } |
|---|
| 54 | 69 | |
|---|
| 55 | 70 | requestFileUploaded(file: File) : void { |
|---|
| 56 | 71 | console.log(file); |
|---|
| .. | .. |
|---|
| 39 | 39 | <field-readonly [value]="data.activation_code" label="field.activation_code" flex></field-readonly> |
|---|
| 40 | 40 | </div> |
|---|
| 41 | 41 | <div layout="row" layout-fill layout-padding *ngIf="!isNew"> |
|---|
| 42 | | - <field-readonly [value]="data.expiration_date | date: 'dateMedium'" label="field.expiration_date" flex></field-readonly> |
|---|
| 42 | + <field-readonly [value]="data.expiration_date | date: 'mediumDate'" label="field.expiration_date" flex></field-readonly> |
|---|
| 43 | 43 | <field-readonly [value]="licenses.getStatusName(data.status)" label="field.status" flex></field-readonly> |
|---|
| 44 | 44 | </div> |
|---|
| 45 | 45 | <div layout="row" layout-fill layout-padding> |
|---|
| .. | .. |
|---|
| 59 | 59 | <span i18n="field.email"></span> |
|---|
| 60 | 60 | </md-placeholder> |
|---|
| 61 | 61 | </md-input-container> |
|---|
| 62 | | - <error-checker [fieldName]="$L.get('field.full_name')" [formField]="form.controls.email"></error-checker> |
|---|
| 62 | + <error-checker [fieldName]="$L.get('field.email')" [formField]="form.controls.email"></error-checker> |
|---|
| 63 | 63 | </div> |
|---|
| 64 | 64 | </div> |
|---|
| 65 | 65 | <div layout="row" layout-fill layout-padding> |
|---|
| .. | .. |
|---|
| 99 | 99 | <md-divider></md-divider> |
|---|
| 100 | 100 | <md-card-actions> |
|---|
| 101 | 101 | <div layout="row" layout-align="start center" class="margin"> |
|---|
| 102 | + <button *ngIf="canBeDeleted()" md-raised-button color="warn" (click)="delete(data.id)">Delete</button> |
|---|
| 102 | 103 | <span flex></span> |
|---|
| 104 | + <button md-icon-button [mdMenuTriggerFor]="licMenu" aria-label="License menu"> |
|---|
| 105 | + <md-icon>more_vert</md-icon> |
|---|
| 106 | + </button> |
|---|
| 107 | + <md-menu #licMenu="mdMenu"> |
|---|
| 108 | + <button md-menu-item *ngFor="let action of license_menu_options" (click)="licenseAction(action.command)" [disabled]="!licenses.isActionAvailable(action.command, data)"> |
|---|
| 109 | + <md-icon *ngIf="!!action.icon">{{ action.icon }}</md-icon> {{ action.name }} |
|---|
| 110 | + </button> |
|---|
| 111 | + </md-menu> |
|---|
| 103 | 112 | <button [disabled]="!form.form.valid" md-raised-button color="primary" (click)="save()">Save</button> |
|---|
| 104 | 113 | <button md-button (click)="goBack()">Cancel</button> |
|---|
| 105 | 114 | </div> |
|---|
| .. | .. |
|---|
| 1 | 1 | import { Http } from '@angular/http'; |
|---|
| 2 | 2 | import { ToastsManager } from 'ng2-toastr/ng2-toastr'; |
|---|
| 3 | 3 | |
|---|
| 4 | | -import { PacksService, PACK_STATUS } from '../resources/packs'; |
|---|
| 4 | +import { PacksService, PACK_STATUS, PACK_ACTIONS } from '../resources/packs'; |
|---|
| 5 | 5 | import { LicenseTypesService } from '../resources/license_types'; |
|---|
| 6 | 6 | import { LocaleService } from '../common/i18n'; |
|---|
| 7 | 7 | import { TdDataTableService, TdDataTableSortingOrder, ITdDataTableSortChangeEvent, ITdDataTableColumn } from '@covalent/core'; |
|---|
| .. | .. |
|---|
| 21 | 21 | |
|---|
| 22 | 22 | organizations : IComboOption[]; |
|---|
| 23 | 23 | licensetypes : IComboOption[]; |
|---|
| 24 | | - |
|---|
| 24 | + pack_menu_options = PACK_ACTIONS; |
|---|
| 25 | 25 | constructor(private http: Http, |
|---|
| 26 | 26 | private licenseTypes: LicenseTypesService, |
|---|
| 27 | 27 | private packs: PacksService, |
|---|
| .. | .. |
|---|
| 65 | 65 | ); |
|---|
| 66 | 66 | } |
|---|
| 67 | 67 | |
|---|
| 68 | + packAction(action: string) { |
|---|
| 69 | + return this.packs[action](this.data.id).subscribe( |
|---|
| 70 | + (actionResponse : any) => { |
|---|
| 71 | + this.toaster.success(this.$L.get('Action "{}" executed successfully', action)); |
|---|
| 72 | + this.reload(); |
|---|
| 73 | + }, |
|---|
| 74 | + (err : any) => this.toaster.error(this.$L.get('Action "{}" failed', action)) |
|---|
| 75 | + ); |
|---|
| 76 | + } |
|---|
| 77 | + |
|---|
| 68 | 78 | changeOrg(event: any) { |
|---|
| 69 | | - console.log(event); |
|---|
| 70 | 79 | console.log(this.data.organization_id); |
|---|
| 71 | 80 | } |
|---|
| 72 | | - |
|---|
| 81 | + |
|---|
| 82 | + canBeDeleted(event: any) : boolean{ |
|---|
| 83 | + return !this.isNew && this.packs.isActionAvailable('delete', this.data); |
|---|
| 84 | + } |
|---|
| 85 | + |
|---|
| 86 | + convertToEpoch(str: string) : number { |
|---|
| 87 | + return new Date(str).getTime(); |
|---|
| 88 | + } |
|---|
| 73 | 89 | |
|---|
| 74 | 90 | ngAfterViewInit(): void { |
|---|
| 75 | 91 | this.init(); |
|---|
| .. | .. |
|---|
| 48 | 48 | <div layout="row" layout-fill layout-padding> |
|---|
| 49 | 49 | <div layout="column" layout-fill flex> |
|---|
| 50 | 50 | <md-input-container flex> |
|---|
| 51 | | - <input mdInput type="date" [(ngModel)]="data.init_valid_date" name="init_valid_date" required /> |
|---|
| 51 | + <input mdInput type="date" [ngModel]="data.init_valid_date | date:'yyyy-MM-dd'" |
|---|
| 52 | + (ngModelChange)="data.init_valid_date = $event" name="init_valid_date" required /> |
|---|
| 52 | 53 | <md-placeholder> |
|---|
| 53 | 54 | <span i18n="field.end_valid_date"></span> |
|---|
| 54 | 55 | </md-placeholder> |
|---|
| .. | .. |
|---|
| 57 | 58 | </div> |
|---|
| 58 | 59 | <div layout="column" layout-fill flex> |
|---|
| 59 | 60 | <md-input-container flex> |
|---|
| 60 | | - <input mdInput type="date" [(ngModel)]="data.end_valid_date" name="end_valid_date" required /> |
|---|
| 61 | + <input mdInput type="date" [ngModel]="data.end_valid_date | date:'yyyy-MM-dd'" |
|---|
| 62 | + (ngModelChange)="data.end_valid_date = $event" name="end_valid_date" required /> |
|---|
| 61 | 63 | <md-placeholder> |
|---|
| 62 | 64 | <span i18n="field.end_valid_date"></span> |
|---|
| 63 | 65 | </md-placeholder> |
|---|
| .. | .. |
|---|
| 133 | 135 | <md-divider></md-divider> |
|---|
| 134 | 136 | <md-card-actions> |
|---|
| 135 | 137 | <div layout="row" layout-align="start center" class="margin"> |
|---|
| 138 | + <button *ngIf="canBeDeleted()" md-raised-button color="warn" (click)="delete(data.id)">Delete</button> |
|---|
| 136 | 139 | <span flex></span> |
|---|
| 140 | + |
|---|
| 141 | + <button md-icon-button [mdMenuTriggerFor]="packMenu" aria-label="Pack menu"> |
|---|
| 142 | + <md-icon>more_vert</md-icon> |
|---|
| 143 | + </button> |
|---|
| 144 | + <md-menu #packMenu="mdMenu"> |
|---|
| 145 | + <button md-menu-item *ngFor="let action of pack_menu_options" (click)="packAction(action.command)" [disabled]="!packs.isActionAvailable(action.command, data)"> |
|---|
| 146 | + <md-icon *ngIf="!!action.icon">{{ action.icon }}</md-icon> {{ action.name }} |
|---|
| 147 | + </button> |
|---|
| 148 | + </md-menu> |
|---|
| 137 | 149 | <button [disabled]="!form.form.valid" md-raised-button color="primary" (click)="save()">Save</button> |
|---|
| 138 | 150 | <button md-button (click)="goBack()">Cancel</button> |
|---|
| 139 | 151 | </div> |
|---|
| .. | .. |
|---|
| 9 | 9 | import { TdMediaService } from '@covalent/core'; |
|---|
| 10 | 10 | import { FormBase, IComboOption } from './base'; |
|---|
| 11 | 11 | import { ActivatedRoute, Router } from '@angular/router'; |
|---|
| 12 | +import { OrganizationsService } from "../resources/organizations"; |
|---|
| 12 | 13 | |
|---|
| 13 | 14 | var user_example = { |
|---|
| 14 | 15 | username: 'rym', |
|---|
| .. | .. |
|---|
| 27 | 28 | templateUrl: 'src/app/forms/user.form.html' |
|---|
| 28 | 29 | }) |
|---|
| 29 | 30 | export class UserFormComponent extends FormBase { |
|---|
| 30 | | - |
|---|
| 31 | + allOrganizations: IComboOption[]; |
|---|
| 32 | + orgNames: string[] = []; |
|---|
| 33 | + allRoles: any[] = [{"id":1, "code": "advance", "label":"Advance"}, {"id":2, "code": "admin","label":"Admin"}]; |
|---|
| 34 | + user_orgs: string[] = []; |
|---|
| 35 | + user_roles: any = {}; |
|---|
| 31 | 36 | constructor(private http: Http, |
|---|
| 32 | 37 | private users: UsersService, |
|---|
| 33 | | - private applications: ApplicationsService, |
|---|
| 38 | + private organizations: OrganizationsService, |
|---|
| 34 | 39 | router: Router, |
|---|
| 35 | 40 | toaster: ToastsManager, |
|---|
| 36 | 41 | route: ActivatedRoute, |
|---|
| .. | .. |
|---|
| 39 | 44 | super($L, router, route, toaster, users, $L.get('user'), dialogs); |
|---|
| 40 | 45 | } |
|---|
| 41 | 46 | |
|---|
| 42 | | - |
|---|
| 47 | + save() : void { |
|---|
| 48 | + this.data.organizations_ids = []; |
|---|
| 49 | + this.data.roles = []; |
|---|
| 50 | + this.user_orgs.forEach(orgName => { |
|---|
| 51 | + var selectedOrg = this.allOrganizations.find(org => org.label === orgName); |
|---|
| 52 | + this.data.organizations_ids.push(selectedOrg.id); |
|---|
| 53 | + }); |
|---|
| 54 | + this.user_roles.advance && this.data.roles.push(1); |
|---|
| 55 | + this.user_roles.admin && this.data.roles.push(2); |
|---|
| 56 | + super.save('username'); |
|---|
| 57 | + } |
|---|
| 58 | + |
|---|
| 59 | + canBeDeleted() { |
|---|
| 60 | + return this.data && this.data.username !== 'admin' && this.data.username !== '_client'; |
|---|
| 61 | + } |
|---|
| 62 | + |
|---|
| 63 | + loadCombos() : void { |
|---|
| 64 | + this.organizations.get() |
|---|
| 65 | + .map(list => list.map((org : any) => <IComboOption>{id: org.id, label: org.name})) |
|---|
| 66 | + .subscribe( |
|---|
| 67 | + data => { |
|---|
| 68 | + this.allOrganizations = (<IComboOption[]>data).sort((e1, e2) => e1.label.localeCompare(e2.label)); |
|---|
| 69 | + this.orgNames = this.allOrganizations.map(org => org.label); |
|---|
| 70 | + this._loadOrgs(); |
|---|
| 71 | + }, |
|---|
| 72 | + err => console.error('Error loading organizations') |
|---|
| 73 | + ); |
|---|
| 74 | + } |
|---|
| 75 | + |
|---|
| 43 | 76 | goBack(): void { |
|---|
| 44 | 77 | this.router.navigate([`users`]); |
|---|
| 45 | 78 | } |
|---|
| 46 | | - |
|---|
| 79 | + _loadOrgs() { |
|---|
| 80 | + if (this.data && this.data.organizations_ids && this.allOrganizations && this.allOrganizations.length > 0) { |
|---|
| 81 | + this.data.organizations_ids.forEach((orgId : number) => { |
|---|
| 82 | + var selectedOrg = this.allOrganizations.find(org => org.id === orgId); |
|---|
| 83 | + this.user_orgs.push(selectedOrg.label); |
|---|
| 84 | + }); |
|---|
| 85 | + } |
|---|
| 86 | + } |
|---|
| 47 | 87 | init() : void { |
|---|
| 88 | + this.loadCombos(); |
|---|
| 89 | + this.user_orgs = []; |
|---|
| 90 | + this.user_roles = {}; |
|---|
| 48 | 91 | super.setFirstFocus(); |
|---|
| 49 | 92 | super.reset(); |
|---|
| 50 | 93 | super.prepareInitialData('username', { |
|---|
| 51 | | - metadata: [] |
|---|
| 94 | + organizations_ids: [], |
|---|
| 95 | + roles: [] |
|---|
| 96 | + }, (data) => { |
|---|
| 97 | + this._loadOrgs(); |
|---|
| 98 | + data.roles.forEach((roleId : number) => { |
|---|
| 99 | + var selectedRole = this.allRoles.find(r => r.id === roleId); |
|---|
| 100 | + this.user_roles[selectedRole.code] = true; |
|---|
| 101 | + }); |
|---|
| 102 | + |
|---|
| 52 | 103 | }); |
|---|
| 53 | 104 | } |
|---|
| 54 | 105 | |
|---|
| .. | .. |
|---|
| 8 | 8 | <button md-icon-button (click)="save()"><md-icon>save</md-icon></button> |
|---|
| 9 | 9 | </md-toolbar> |
|---|
| 10 | 10 | <!-- |
|---|
| 11 | | - code: 'CICS', |
|---|
| 12 | | - creation_timestamp: 1418384439000, |
|---|
| 13 | | - description: 'Wellbore integrity analysis software', |
|---|
| 14 | | - id: 1, |
|---|
| 15 | | - license_filename: 'config_server.lic', |
|---|
| 16 | | - name: 'CurisIntegrity', |
|---|
| 17 | | - metadata: |
|---|
| 18 | | - [ { key: 'max_docs', |
|---|
| 19 | | - value: '250000', |
|---|
| 20 | | - readonly: true, |
|---|
| 21 | | - mandatory: true } ] |
|---|
| 11 | + username: 'rym', |
|---|
| 12 | + roles: [ 1 ], |
|---|
| 13 | + lastLogin: 1488885433000, |
|---|
| 14 | + modificationTimestamp: 1479898458000, |
|---|
| 15 | + email: 'rbouchair@curistec.com', |
|---|
| 16 | + first_name: 'Rym', |
|---|
| 17 | + last_name: 'Bouchair', |
|---|
| 18 | + creation_timestamp: 1479898458000, |
|---|
| 19 | + organizations_ids: [ 1, 2, 5, 6, 7, 8 ] |
|---|
| 22 | 20 | } |
|---|
| 23 | 21 | --> |
|---|
| 24 | 22 | <div class="margin" layout-align-gt-xs="center start" layout-fill="" layout-gt-xs="row"> |
|---|
| .. | .. |
|---|
| 31 | 29 | <form #form="ngForm" class="inset"> |
|---|
| 32 | 30 | <div layout="column" layout-align="start center"> |
|---|
| 33 | 31 | <div layout="row" layout-fill layout-padding> |
|---|
| 34 | | - <field-readonly [value]="data.id" label="field.id" flex="15" *ngIf="!isNew"></field-readonly> |
|---|
| 35 | 32 | <div layout="column" layout-fill flex> |
|---|
| 36 | 33 | <md-input-container> |
|---|
| 37 | | - <input #firstField mdInput maxLength="50" type="text" [(ngModel)]="data.code" name="code" required [readonly]="!isNew" /> |
|---|
| 34 | + <input #firstField mdInput maxLength="50" type="text" [(ngModel)]="data.username" name="username" required [readonly]="!isNew" /> |
|---|
| 38 | 35 | <md-placeholder> |
|---|
| 39 | | - <span i18n="field.code"></span> |
|---|
| 36 | + <span i18n="field.username"></span> |
|---|
| 40 | 37 | </md-placeholder> |
|---|
| 41 | 38 | </md-input-container> |
|---|
| 42 | | - <error-checker [fieldName]="getFieldName('code')" [formField]="form.controls.code"></error-checker> |
|---|
| 39 | + <error-checker [fieldName]="getFieldName('username')" [formField]="form.controls.username"></error-checker> |
|---|
| 40 | + </div> |
|---|
| 41 | + <div layout="column" layout-fill flex> |
|---|
| 42 | + <md-input-container flex> |
|---|
| 43 | + <input mdInput type="password" [(ngModel)]="data.password" name="password" [required]="isNew" /> |
|---|
| 44 | + <md-placeholder> |
|---|
| 45 | + <span i18n="field.password"></span> |
|---|
| 46 | + </md-placeholder> |
|---|
| 47 | + </md-input-container> |
|---|
| 48 | + <error-checker [fieldName]="getFieldName('password')" [formField]="form.controls.password"></error-checker> |
|---|
| 43 | 49 | </div> |
|---|
| 44 | 50 | </div> |
|---|
| 45 | 51 | <div layout="row" layout-fill layout-padding> |
|---|
| 46 | 52 | <div layout="column" layout-fill flex> |
|---|
| 47 | 53 | <md-input-container flex> |
|---|
| 48 | | - <input mdInput type="text" [(ngModel)]="data.name" name="name" required /> |
|---|
| 54 | + <input mdInput type="text" [(ngModel)]="data.first_name" name="first_name" required /> |
|---|
| 49 | 55 | <md-placeholder> |
|---|
| 50 | | - <span i18n="field.name"></span> |
|---|
| 56 | + <span i18n="field.first_name"></span> |
|---|
| 51 | 57 | </md-placeholder> |
|---|
| 52 | 58 | </md-input-container> |
|---|
| 53 | | - <error-checker [fieldName]="getFieldName('name')" [formField]="form.controls.name"></error-checker> |
|---|
| 59 | + <error-checker [fieldName]="getFieldName('first_name')" [formField]="form.controls.first_name"></error-checker> |
|---|
| 54 | 60 | </div> |
|---|
| 55 | 61 | <div layout="column" layout-fill flex> |
|---|
| 56 | 62 | <md-input-container flex> |
|---|
| 57 | | - <input mdInput type="text" [(ngModel)]="data.license_filename" name="license_filename" required /> |
|---|
| 63 | + <input mdInput type="text" [(ngModel)]="data.last_name" name="last_name" /> |
|---|
| 58 | 64 | <md-placeholder> |
|---|
| 59 | | - <span i18n="field.license_filename"></span> |
|---|
| 65 | + <span i18n="field.last_name"></span> |
|---|
| 60 | 66 | </md-placeholder> |
|---|
| 61 | 67 | </md-input-container> |
|---|
| 62 | | - <error-checker [fieldName]="getFieldName('license_filename')" [formField]="form.controls.license_filename"></error-checker> |
|---|
| 68 | + <error-checker [fieldName]="getFieldName('last_name')" [formField]="form.controls.last_name"></error-checker> |
|---|
| 63 | 69 | </div> |
|---|
| 64 | 70 | </div> |
|---|
| 65 | 71 | <div layout="row" layout-fill layout-padding> |
|---|
| 66 | 72 | <div layout="column" layout-fill flex> |
|---|
| 67 | 73 | <md-input-container flex> |
|---|
| 68 | | - <textarea mdInput type="text" type="text" [(ngModel)]="data.description" name="description" maxlength="1024"></textarea> |
|---|
| 74 | + <input mdInput type="email" [(ngModel)]="data.email" name="email" required maxlength="200" /> |
|---|
| 69 | 75 | <md-placeholder> |
|---|
| 70 | | - <span i18n="field.description"></span> |
|---|
| 76 | + <span i18n="field.email"></span> |
|---|
| 71 | 77 | </md-placeholder> |
|---|
| 72 | | - <md-hint align="end">(max 1024)</md-hint> |
|---|
| 73 | 78 | </md-input-container> |
|---|
| 79 | + <error-checker [fieldName]="$L.get('field.email')" [formField]="form.controls.email"></error-checker> |
|---|
| 80 | + </div> |
|---|
| 81 | + </div> |
|---|
| 82 | + <div layout="row" layout-fill layout-padding > |
|---|
| 83 | + <td-chips flex [mdTooltip]="$L.get('Organizations that user can access')" [placeholder]="$L.get('Select organizations')" |
|---|
| 84 | + [items]="orgNames" [(ngModel)]="user_orgs" name="user_orgs" requireMatch> |
|---|
| 85 | + </td-chips> |
|---|
| 86 | + <div layout="column" layout-fill flex="25"> |
|---|
| 87 | + <md-checkbox [(ngModel)]="user_roles.advance" name="advance_role" [mdTooltip]="$L.get('Role {}', 'advance')"> |
|---|
| 88 | + <span i18n>Advance</span> |
|---|
| 89 | + </md-checkbox> |
|---|
| 90 | + <md-checkbox [(ngModel)]="user_roles.admin" name="admin_role" [mdTooltip]="$L.get('Role {}', 'admin')"> |
|---|
| 91 | + <span i18n>Admin</span> |
|---|
| 92 | + </md-checkbox> |
|---|
| 74 | 93 | </div> |
|---|
| 75 | 94 | </div> |
|---|
| 76 | 95 | <div layout="row" layout-fill layout-padding *ngIf="!isNew"> |
|---|
| 96 | + <field-readonly [value]="data.lastLogin || '' | timeAgo" label="field.lastLogin" flex></field-readonly> |
|---|
| 77 | 97 | <field-readonly [value]="data.creation_timestamp | date: 'medium'" label="field.creation_timestamp" flex></field-readonly> |
|---|
| 78 | 98 | </div> |
|---|
| 79 | | - <metadata-manager addOrDelete="true" editKeys="true" [metadata]="data.metadata" ></metadata-manager> |
|---|
| 80 | 99 | </div> |
|---|
| 81 | 100 | </form> |
|---|
| 82 | 101 | </md-card-content> |
|---|
| 83 | 102 | <md-divider></md-divider> |
|---|
| 84 | 103 | <md-card-actions> |
|---|
| 85 | 104 | <div layout="row" layout-align="start center" class="margin"> |
|---|
| 86 | | - <button *ngIf="!isNew" md-raised-button color="warn" (click)="delete(data.id)">Delete</button> |
|---|
| 105 | + <button *ngIf="!isNew" [disabled]="!canBeDeleted()" md-raised-button color="warn" (click)="delete(data.username)">Delete</button> |
|---|
| 87 | 106 | <span flex></span> |
|---|
| 88 | 107 | <button [disabled]="!form.form.valid" md-raised-button color="primary" (click)="save()">Save</button> |
|---|
| 89 | 108 | <button md-button (click)="goBack()">Cancel</button> |
|---|
| .. | .. |
|---|
| 40 | 40 | <span style="white-space: nowrap">{{value}}</span> |
|---|
| 41 | 41 | </div> |
|---|
| 42 | 42 | </template> |
|---|
| 43 | | - <template tdDataTableTemplate="status" let-row="row"> |
|---|
| 43 | + <template tdDataTableTemplate="status" let-row="row" let-value="value"> |
|---|
| 44 | 44 | <div layout="row" layout-align="start center"> |
|---|
| 45 | | - <md-icon [style.color]="licenses.getStatusColor(row.status)">brightness_1</md-icon> <span>{{licenses.getStatusName(row.status)}}</span> |
|---|
| 45 | + <md-chip selected [mdTooltip]="licenses.getStatusName(value)" [style.background-color]="licenses.getStatusColor(value)" >{{value}}</md-chip> |
|---|
| 46 | 46 | </div> |
|---|
| 47 | 47 | </template> |
|---|
| 48 | 48 | <template tdDataTableTemplate="email" let-row="row" let-value="value"> |
|---|
| .. | .. |
|---|
| 63 | 63 | <md-icon>more_vert</md-icon> |
|---|
| 64 | 64 | </button> |
|---|
| 65 | 65 | <md-menu #licenseMenu="mdMenu"> |
|---|
| 66 | | - <button md-menu-item *ngFor="let action of license_menu_options" (click)="licenseAction(action.command, row)" [disabled]="!isActionAvailable(row)"> |
|---|
| 66 | + <button md-menu-item *ngFor="let action of license_menu_options" (click)="licenseAction(action.command, row)" [disabled]="!isActionAvailable(action.command, row)"> |
|---|
| 67 | 67 | <md-icon *ngIf="!!action.icon">{{ action.icon }}</md-icon> {{ action.name }} |
|---|
| 68 | 68 | </button> |
|---|
| 69 | 69 | </md-menu> |
|---|
| .. | .. |
|---|
| 74 | 74 | <span i18n td-paging-bar-label hide-xs>Rows per page:</span> {{pagingBar.range}} <span hide-xs>of {{pagingBar.total}}</span> |
|---|
| 75 | 75 | </td-paging-bar> |
|---|
| 76 | 76 | </div> |
|---|
| 77 | | -</td-layout-card-over> |
|---|
| 77 | +</td-layout-card-over> |
|---|
| .. | .. |
|---|
| 5 | 5 | import { Component, AfterViewInit, ViewChild } from '@angular/core'; |
|---|
| 6 | 6 | import { TdMediaService } from '@covalent/core'; |
|---|
| 7 | 7 | import { Location } from '@angular/common'; |
|---|
| 8 | +import { ToastsManager } from 'ng2-toastr/ng2-toastr'; |
|---|
| 8 | 9 | |
|---|
| 9 | 10 | import { LocaleService } from '../common/i18n'; |
|---|
| 10 | | -import { LicensesService } from '../resources/licenses'; |
|---|
| 11 | +import { LicensesService, LICENSE_ACTIONS } from '../resources/licenses'; |
|---|
| 11 | 12 | import { PacksService } from '../resources/packs'; |
|---|
| 12 | 13 | import { LicenseFormComponent } from '../forms/license.form.component'; |
|---|
| 13 | 14 | import { ListingBase } from './base'; |
|---|
| .. | .. |
|---|
| 43 | 44 | { name: 'menu', label: '' } |
|---|
| 44 | 45 | ]; |
|---|
| 45 | 46 | |
|---|
| 46 | | - license_menu_options : any[] = [{ |
|---|
| 47 | | - icon: 'edit', |
|---|
| 48 | | - command: 'edit', |
|---|
| 49 | | - name: 'Edit' |
|---|
| 50 | | - },{ |
|---|
| 51 | | - icon: 'cancel', |
|---|
| 52 | | - command: 'cancel', |
|---|
| 53 | | - name: 'Cancel' |
|---|
| 54 | | - }] |
|---|
| 47 | + license_menu_options = LICENSE_ACTIONS; |
|---|
| 55 | 48 | |
|---|
| 56 | | - licenseAction(action: any) { |
|---|
| 57 | | - console.log(action.command); |
|---|
| 49 | + licenseAction(action: string, license: any) { |
|---|
| 50 | + return this.licenses[action](license.id).subscribe( |
|---|
| 51 | + (actionResponse : any) => { |
|---|
| 52 | + this.toaster.success(this.$L.get('Action "{}" executed successfully', action)); |
|---|
| 53 | + this.reload(this.pack.id); |
|---|
| 54 | + }, |
|---|
| 55 | + (err : any) => this.toaster.error(this.$L.get('Action "{}" failed', action)) |
|---|
| 56 | + ); |
|---|
| 58 | 57 | } |
|---|
| 59 | 58 | |
|---|
| 60 | | - isActionAvailable(pack : any) : boolean { |
|---|
| 61 | | - return true; |
|---|
| 59 | + reload(packId: number) : void { |
|---|
| 60 | + this.licenses.getByPack(packId).subscribe( |
|---|
| 61 | + list => { |
|---|
| 62 | + this.data = list; |
|---|
| 63 | + this.refresh(); |
|---|
| 64 | + }, |
|---|
| 65 | + err => console.error(err) |
|---|
| 66 | + ); |
|---|
| 67 | + } |
|---|
| 68 | + |
|---|
| 69 | + isActionAvailable(action: string, license : any) : boolean { |
|---|
| 70 | + return this.licenses.isActionAvailable(action, license); |
|---|
| 62 | 71 | } |
|---|
| 63 | 72 | |
|---|
| 64 | 73 | constructor( _dataTableService: TdDataTableService, |
|---|
| .. | .. |
|---|
| 66 | 75 | private $L: LocaleService, |
|---|
| 67 | 76 | private router: Router, |
|---|
| 68 | 77 | private location: Location, |
|---|
| 78 | + private toaster: ToastsManager, |
|---|
| 69 | 79 | private route: ActivatedRoute, |
|---|
| 70 | 80 | private dialog: MdDialog, |
|---|
| 71 | 81 | private licenseForm: LicenseFormComponent, |
|---|
| .. | .. |
|---|
| 75 | 85 | } |
|---|
| 76 | 86 | |
|---|
| 77 | 87 | ngOnInit(): void { |
|---|
| 78 | | - this.route.params.subscribe(params => { |
|---|
| 79 | | - var packId = +params['packId']; // (+) converts string 'id' to a number |
|---|
| 80 | | - this.licenses.getByPack(packId).subscribe( |
|---|
| 81 | | - list => { |
|---|
| 82 | | - this.data = list; |
|---|
| 83 | | - this.refresh(); |
|---|
| 84 | | - }, |
|---|
| 85 | | - err => console.error(err) |
|---|
| 86 | | - ); |
|---|
| 87 | | - this.packs.get(packId).subscribe( |
|---|
| 88 | | - packData => { |
|---|
| 89 | | - this.pack = packData; |
|---|
| 90 | | - }, |
|---|
| 91 | | - err => console.error(err) |
|---|
| 92 | | - ); |
|---|
| 93 | | - }); |
|---|
| 94 | 88 | } |
|---|
| 95 | 89 | |
|---|
| 96 | 90 | goBack() : void { |
|---|
| .. | .. |
|---|
| 111 | 105 | |
|---|
| 112 | 106 | ngAfterViewInit(): void { |
|---|
| 113 | 107 | this.media.broadcast(); |
|---|
| 114 | | - |
|---|
| 108 | + this.route.params.subscribe(params => { |
|---|
| 109 | + var packId = +params['packId']; // (+) converts string 'id' to a number |
|---|
| 110 | + this.reload(packId); |
|---|
| 111 | + this.packs.get(packId).subscribe( |
|---|
| 112 | + packData => { |
|---|
| 113 | + this.pack = packData; |
|---|
| 114 | + }, |
|---|
| 115 | + err => console.error(err) |
|---|
| 116 | + ); |
|---|
| 117 | + }); |
|---|
| 115 | 118 | } |
|---|
| 116 | 119 | } |
|---|
| 117 | 120 | |
|---|
| .. | .. |
|---|
| 33 | 33 | <span style="white-space: nowrap">{{value}}</span> |
|---|
| 34 | 34 | </div> |
|---|
| 35 | 35 | </template> |
|---|
| 36 | + <template tdDataTableTemplate="status" let-row="row" let-value="value"> |
|---|
| 37 | + <div layout="row" layout-align="start center"> |
|---|
| 38 | + <md-chip selected [mdTooltip]="$L.get('pack.status.' +value)" [style.background-color]="packs.getStatusColor(value)" >{{value}}</md-chip> |
|---|
| 39 | + </div> |
|---|
| 40 | + </template> |
|---|
| 36 | 41 | <template tdDataTableTemplate="menu" let-row="row" let-index="index"> |
|---|
| 37 | 42 | <div layout="row" layout-align="end center"> |
|---|
| 38 | 43 | <button md-icon-button (click)="edit(row.id)" color="primary"><md-icon>edit</md-icon></button> |
|---|
| .. | .. |
|---|
| 41 | 46 | </button> |
|---|
| 42 | 47 | |
|---|
| 43 | 48 | <md-menu #packMenu="mdMenu"> |
|---|
| 44 | | - <button md-menu-item *ngFor="let action of pack_menu_options" (click)="packAction(action.command, row)" [disabled]="!isActionAvailable(row)"> |
|---|
| 49 | + <button md-menu-item *ngFor="let action of pack_menu_options" (click)="packAction(action.command, row)" [disabled]="!packs.isActionAvailable(action.command, row)"> |
|---|
| 45 | 50 | <md-icon *ngIf="!!action.icon">{{ action.icon }}</md-icon> {{ action.name }} |
|---|
| 46 | 51 | </button> |
|---|
| 47 | 52 | </md-menu> |
|---|
| .. | .. |
|---|
| 1 | 1 | import { Router, ActivatedRoute } from '@angular/router'; |
|---|
| 2 | +import { ToastsManager } from 'ng2-toastr/ng2-toastr'; |
|---|
| 2 | 3 | import { MdDialog, MdDialogConfig } from '@angular/material'; |
|---|
| 3 | 4 | import { |
|---|
| 4 | 5 | ITdDataTableColumn, |
|---|
| .. | .. |
|---|
| 10 | 11 | import { IPageChangeEvent } from '@covalent/core'; |
|---|
| 11 | 12 | import { Component, ViewChild, AfterViewInit } from '@angular/core'; |
|---|
| 12 | 13 | import { TdMediaService } from '@covalent/core'; |
|---|
| 13 | | -import { PacksService } from '../resources/packs'; |
|---|
| 14 | +import { PacksService, PACK_ACTIONS } from '../resources/packs'; |
|---|
| 14 | 15 | import { PackFormComponent } from '../forms/pack.form.component'; |
|---|
| 15 | 16 | import { LocaleService } from '../common/i18n'; |
|---|
| 16 | 17 | import { ListingBase } from './base'; |
|---|
| .. | .. |
|---|
| 57 | 58 | { name: 'licensetype_code', label: 'License type' }, |
|---|
| 58 | 59 | { name: 'organization_name', label: 'Organization' }, |
|---|
| 59 | 60 | { name: 'used_licenses', label: 'Licenses', tooltip: 'Initial/Available pack licenses' }, |
|---|
| 61 | + { name: 'status', label: 'Status', tooltip: 'Pack status' }, |
|---|
| 60 | 62 | { name: 'menu', label: '' } |
|---|
| 61 | 63 | ]; |
|---|
| 62 | 64 | |
|---|
| 63 | | - pack_menu_options : any[] = [{ |
|---|
| 64 | | - command: 'edit', |
|---|
| 65 | | - name: 'Edit' |
|---|
| 66 | | - },{ |
|---|
| 67 | | - command: 'cancel', |
|---|
| 68 | | - name: 'Cancel' |
|---|
| 69 | | - }] |
|---|
| 70 | | - |
|---|
| 65 | + pack_menu_options = PACK_ACTIONS; |
|---|
| 71 | 66 | |
|---|
| 72 | 67 | constructor(_dataTableService: TdDataTableService, |
|---|
| 73 | 68 | private media: TdMediaService, |
|---|
| .. | .. |
|---|
| 75 | 70 | private route: ActivatedRoute, |
|---|
| 76 | 71 | private dialog: MdDialog, |
|---|
| 77 | 72 | private $L: LocaleService, |
|---|
| 73 | + private toaster: ToastsManager, |
|---|
| 78 | 74 | private packForm: PackFormComponent, |
|---|
| 79 | 75 | private packs: PacksService) { |
|---|
| 80 | 76 | super(_dataTableService); |
|---|
| 81 | | - this.packs.get().subscribe( |
|---|
| 82 | | - (list : any[]) => { |
|---|
| 83 | | - this.data = list; |
|---|
| 84 | | - this.refresh(); |
|---|
| 85 | | - }, |
|---|
| 86 | | - (err: any) => console.error(err) |
|---|
| 87 | | - ); |
|---|
| 88 | 77 | } |
|---|
| 89 | 78 | |
|---|
| 90 | | - |
|---|
| 91 | | - packAction(action: any) { |
|---|
| 92 | | - console.log(action.command); |
|---|
| 79 | + reload() : void { |
|---|
| 80 | + this.packs.get().subscribe( |
|---|
| 81 | + (list : any[]) => { |
|---|
| 82 | + this.data = list; |
|---|
| 83 | + this.refresh(); |
|---|
| 84 | + }, |
|---|
| 85 | + (err: any) => console.error(err) |
|---|
| 86 | + ); |
|---|
| 93 | 87 | } |
|---|
| 94 | 88 | |
|---|
| 95 | | - isActionAvailable(pack : any) : boolean { |
|---|
| 96 | | - return true; |
|---|
| 89 | + packAction(action: string, pack: any) { |
|---|
| 90 | + return this.packs[action](pack.id).subscribe( |
|---|
| 91 | + (actionResponse : any) => { |
|---|
| 92 | + this.toaster.success(this.$L.get('Action "{}" executed successfully', action)); |
|---|
| 93 | + this.reload(); |
|---|
| 94 | + }, |
|---|
| 95 | + (err : any) => this.toaster.error(this.$L.get('Action "{}" failed', action)) |
|---|
| 96 | + ); |
|---|
| 97 | 97 | } |
|---|
| 98 | 98 | |
|---|
| 99 | 99 | showLicenses(pack: any) : void { |
|---|
| .. | .. |
|---|
| 115 | 115 | } |
|---|
| 116 | 116 | |
|---|
| 117 | 117 | ngAfterViewInit(): void { |
|---|
| 118 | + this.reload(); |
|---|
| 118 | 119 | this.media.broadcast(); |
|---|
| 119 | | - |
|---|
| 120 | 120 | } |
|---|
| 121 | 121 | } |
|---|
| 122 | 122 | |
|---|
| .. | .. |
|---|
| 1 | 1 | import { LocaleService } from '../common/i18n'; |
|---|
| 2 | 2 | import { Observable } from 'rxjs/Rx'; |
|---|
| 3 | 3 | import { Injectable } from '@angular/core'; |
|---|
| 4 | | -import { Http, RequestOptions } from '@angular/http'; |
|---|
| 4 | +import { Http, RequestOptions, ResponseContentType, Response } from '@angular/http'; |
|---|
| 5 | 5 | import { SeCurisResourceServices } from './base'; |
|---|
| 6 | | - |
|---|
| 7 | | -var lic_example = { |
|---|
| 8 | | - id: 101, |
|---|
| 9 | | - activation_code: 'f3e2d27e-7f81-4ac7-87ba-b9e38b4fdbb8', |
|---|
| 10 | | - code: 'CITR01-436-1', |
|---|
| 11 | | - code_suffix: 1, |
|---|
| 12 | | - created_by_id: '_client', |
|---|
| 13 | | - creation_timestamp: 1445898088000, |
|---|
| 14 | | - email: 'GQuercia@trican.ca', |
|---|
| 15 | | - expiration_date: 1487523828000, |
|---|
| 16 | | - full_name: 'George Quercia', |
|---|
| 17 | | - licenseData: '{"appCode":"CICS","appName":"CurisIntegrity","licenseCode":"CITR01-436-1","activationCode":"f3e2d27e-7f81-4ac7-87ba-b9e38b4fdbb8","expirationDate":1487523828416,"arch":"amd64","osName":"Windows 7","macAddresses":["C4-D9-87-5D-53-72","C4-D9-87-5D-53-76","FC-15-B4-EB-70-F9"],"crcLogo":"10f6379e0e1c00ebc403160307e3c5d0aba0727c9cae0bf1ac7cd19d84fdc80f","metadata":{"a2Mode":"false","datasetPrefix":"TR","extendedMode":"false","maxConcurrentInstances":"-1","maxInstances":"3","maxUsers":"0","maxWellLifeLines":"50","timeThreshold":"0"},"signature":"cjyLYFyhXpWWsMNnG6ER9mtCREgw02aQDnXPSQQWZtiLWbu/GyHZzK+1msLhwuKMGYG6I90s5wp82HVIqhIheHOsov3JfnHgNtYzf3BdkqUinwPFuDqPqkXz5Sjb6bouWkmvTI1TN/s4U2DJOXVnYN4FnYl0/dBTcU9RP4NZlQxMu6oFuRrZSMfdMCxEJYZAU62SWgTSurkdmHhFgwRjIwsOXRWHYsr6vGT//yILI7UvMGbMc6dRCGwyJLPNi4nXwF9PRMLinB7fYK8HxKylTJx2O7bvWCZd6EOdwi6gRI/0HhOqZ7E4DzBDrqEnsHeuH4L47DfRdIMGDnA492F+mg=="}', |
|---|
| 18 | | - modification_timestamp: 1484931828000, |
|---|
| 19 | | - pack_code: 'CITR01', |
|---|
| 20 | | - pack_id: 12, |
|---|
| 21 | | - request_data: '{"appCode":"CICS","activationCode":"f3e2d27e-7f81-4ac7-87ba-b9e38b4fdbb8","arch":"amd64","osName":"Windows 7","macAddresses":["C4-D9-87-5D-53-72","C4-D9-87-5D-53-76","FC-15-B4-EB-70-F9"],"crcLogo":"10f6379e0e1c00ebc403160307e3c5d0aba0727c9cae0bf1ac7cd19d84fdc80f"}', |
|---|
| 22 | | - status: 'AC' |
|---|
| 23 | | -} |
|---|
| 6 | +import * as saveAsFile from "file-saver"; |
|---|
| 24 | 7 | |
|---|
| 25 | 8 | export const LIC_STATUS = { |
|---|
| 26 | 9 | CREATED: 'CR', |
|---|
| .. | .. |
|---|
| 41 | 24 | 'CA': '#a21717' |
|---|
| 42 | 25 | }; |
|---|
| 43 | 26 | |
|---|
| 27 | + |
|---|
| 44 | 28 | /** |
|---|
| 45 | 29 | * These transitions could be get from server, class License.Status, but |
|---|
| 46 | 30 | * we copy them for simplicity, this info won't change easily |
|---|
| .. | .. |
|---|
| 56 | 40 | cancel: [LIC_STATUS.REQUESTED, LIC_STATUS.EXPIRED, LIC_STATUS.PREACTIVE, LIC_STATUS.ACTIVE], |
|---|
| 57 | 41 | 'delete': [LIC_STATUS.CREATED, LIC_STATUS.CANCELLED, LIC_STATUS.BLOCKED] |
|---|
| 58 | 42 | } |
|---|
| 43 | + |
|---|
| 44 | +export const LICENSE_ACTIONS : any[] = [{ |
|---|
| 45 | +/* command: 'add_request', |
|---|
| 46 | + icon: 'add_to_photos', |
|---|
| 47 | + name: 'Add request' |
|---|
| 48 | + },{ */ |
|---|
| 49 | + command: 'activate', |
|---|
| 50 | + icon: 'play_circle_outline', |
|---|
| 51 | + name: 'Activate' |
|---|
| 52 | + },{ |
|---|
| 53 | + command: 'send', |
|---|
| 54 | + icon: 'send', |
|---|
| 55 | + name: 'Send' |
|---|
| 56 | + },{ |
|---|
| 57 | + command: 'download', |
|---|
| 58 | + icon: 'file_download', |
|---|
| 59 | + name: 'Download' |
|---|
| 60 | + },{ |
|---|
| 61 | + command: 'block', |
|---|
| 62 | + icon: 'do_not_disturb_on', |
|---|
| 63 | + name: 'Block' |
|---|
| 64 | + },{ |
|---|
| 65 | + command: 'unblock', |
|---|
| 66 | + icon: 'do_not_disturb_off', |
|---|
| 67 | + name: 'Unblock' |
|---|
| 68 | + },{ |
|---|
| 69 | + command: 'cancel', |
|---|
| 70 | + icon: 'cancel', |
|---|
| 71 | + name: 'Cancel' |
|---|
| 72 | + }] |
|---|
| 73 | + |
|---|
| 59 | 74 | |
|---|
| 60 | 75 | @Injectable() |
|---|
| 61 | 76 | export class LicensesService extends SeCurisResourceServices { |
|---|
| .. | .. |
|---|
| 73 | 88 | return super.action(id, "activate"); |
|---|
| 74 | 89 | } |
|---|
| 75 | 90 | |
|---|
| 91 | + public block(id: number) { |
|---|
| 92 | + return super.action(id, "block"); |
|---|
| 93 | + } |
|---|
| 94 | + |
|---|
| 95 | + public unblock(id: number) { |
|---|
| 96 | + return super.action(id, "unblock"); |
|---|
| 97 | + } |
|---|
| 98 | + |
|---|
| 99 | + public send(id: number) { |
|---|
| 100 | + return super.action(id, "send"); |
|---|
| 101 | + } |
|---|
| 102 | + |
|---|
| 76 | 103 | public cancel(id: number) { |
|---|
| 77 | 104 | return super.action(id, "cancel"); |
|---|
| 78 | 105 | } |
|---|
| 79 | 106 | |
|---|
| 80 | | - public putonhold(id: number) { |
|---|
| 81 | | - return super.action(id, "putonhold"); |
|---|
| 107 | + public download(id: number) { |
|---|
| 108 | + let url = `${this.resource}/${id}/download`; |
|---|
| 109 | + return this.http.get(url).map((response : Response) => { |
|---|
| 110 | + let filename = JSON.parse(response.headers.get('Content-Disposition').match(/".*"$/g)[0]); |
|---|
| 111 | + let content = JSON.stringify(response.json(), null, 2); |
|---|
| 112 | + saveAsFile( new Blob([ content ], { type : 'application/octet-stream' }), filename); |
|---|
| 113 | + return Observable.of(true); |
|---|
| 114 | + }).catch(err => super.processErrorResponse(err)); |
|---|
| 82 | 115 | } |
|---|
| 83 | 116 | |
|---|
| 84 | 117 | public isActionAvailable(action:string, lic:any) { |
|---|
| 85 | 118 | var validStatuses = LIC_ACTIONS_BY_STATUS[action]; |
|---|
| 86 | 119 | return lic && validStatuses && validStatuses.indexOf(lic.status) !== -1; |
|---|
| 87 | 120 | } |
|---|
| 88 | | - |
|---|
| 89 | 121 | |
|---|
| 90 | 122 | getStatusName(statusCode: string): string { |
|---|
| 91 | 123 | return this.$L.get(`pack.status.${statusCode}`, this.$L.get('Unknown')); |
|---|
| .. | .. |
|---|
| 57 | 57 | 'delete': [PACK_STATUS.CREATED, PACK_STATUS.CANCELLED] |
|---|
| 58 | 58 | } |
|---|
| 59 | 59 | |
|---|
| 60 | +export const PACK_ACTIONS : any[] = [{ |
|---|
| 61 | + command: 'activate', |
|---|
| 62 | + icon: 'play_circle_outline', |
|---|
| 63 | + name: 'Activate' |
|---|
| 64 | + },{ |
|---|
| 65 | + command: 'putonhold', |
|---|
| 66 | + icon: 'pause_circle_outline', |
|---|
| 67 | + name: 'Put on hold' |
|---|
| 68 | + },{ |
|---|
| 69 | + command: 'cancel', |
|---|
| 70 | + icon: 'cancel', |
|---|
| 71 | + name: 'Cancel' |
|---|
| 72 | + }] |
|---|
| 73 | + |
|---|
| 74 | + |
|---|
| 60 | 75 | |
|---|
| 61 | 76 | @Injectable() |
|---|
| 62 | 77 | export class PacksService extends SeCurisResourceServices { |
|---|
| .. | .. |
|---|
| 20 | 20 | "field.metadata": "Metadata", |
|---|
| 21 | 21 | "field.key": "Parameter", |
|---|
| 22 | 22 | "field.value": "Value", |
|---|
| 23 | + "field.username": "Username", |
|---|
| 24 | + "field.password": "Password", |
|---|
| 25 | + "field.first_name": "Firstname", |
|---|
| 26 | + "field.last_name": "Lastname", |
|---|
| 23 | 27 | "field.created_by": "Created by", |
|---|
| 24 | 28 | "field.creation_date": "Creation date", |
|---|
| 29 | + "field.expiration_date": "Expiration date", |
|---|
| 25 | 30 | "field.request_data": "Request data", |
|---|
| 26 | | - "field.full_name": "Full name", |
|---|
| 31 | + "field.full_name": "Fullname", |
|---|
| 27 | 32 | "field.email": "Email", |
|---|
| 33 | + "field.lastLogin": "Last login", |
|---|
| 28 | 34 | "field.creation_timestamp": "Creation timestamp", |
|---|
| 29 | 35 | "field.comments": "Comments", |
|---|
| 30 | 36 | "field.mandatory": "Required", |
|---|
| .. | .. |
|---|
| 16 | 16 | // other libraries |
|---|
| 17 | 17 | 'rxjs': 'npm:rxjs', |
|---|
| 18 | 18 | 'ng2-toastr': 'npm:ng2-toastr', |
|---|
| 19 | + 'file-saver': 'npm:file-saver/FileSaver.js', |
|---|
| 19 | 20 | 'angular-2-local-storage': 'npm:angular-2-local-storage/dist', |
|---|
| 20 | 21 | 'angular-in-memory-web-api': 'npm:angular-in-memory-web-api/bundles/in-memory-web-api.umd.js' |
|---|
| 21 | 22 | } |
|---|