mirror of
https://github.com/bitwarden/jslib
synced 2025-12-19 17:53:48 +00:00
[feature] Implement account switching capable services across components and processes
* Replace calls to StorageService and deprecated services with calls to a StateService
This commit is contained in:
@@ -22,10 +22,10 @@ import { FolderService } from 'jslib-common/abstractions/folder.service';
|
|||||||
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
||||||
import { LogService } from 'jslib-common/abstractions/log.service';
|
import { LogService } from 'jslib-common/abstractions/log.service';
|
||||||
import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
||||||
|
import { OrganizationService } from 'jslib-common/abstractions/organization.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
||||||
import { StateService } from 'jslib-common/abstractions/state.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
|
|
||||||
import { Cipher } from 'jslib-common/models/domain/cipher';
|
import { Cipher } from 'jslib-common/models/domain/cipher';
|
||||||
|
|
||||||
@@ -87,9 +87,9 @@ export class AddEditComponent implements OnInit {
|
|||||||
constructor(protected cipherService: CipherService, protected folderService: FolderService,
|
constructor(protected cipherService: CipherService, protected folderService: FolderService,
|
||||||
protected i18nService: I18nService, protected platformUtilsService: PlatformUtilsService,
|
protected i18nService: I18nService, protected platformUtilsService: PlatformUtilsService,
|
||||||
protected auditService: AuditService, protected stateService: StateService,
|
protected auditService: AuditService, protected stateService: StateService,
|
||||||
protected userService: UserService, protected collectionService: CollectionService,
|
protected collectionService: CollectionService, protected messagingService: MessagingService,
|
||||||
protected messagingService: MessagingService, protected eventService: EventService,
|
protected eventService: EventService, protected policyService: PolicyService,
|
||||||
protected policyService: PolicyService, private logService: LogService) {
|
private logService: LogService, private organizationService: OrganizationService) {
|
||||||
this.typeOptions = [
|
this.typeOptions = [
|
||||||
{ name: i18nService.t('typeLogin'), value: CipherType.Login },
|
{ name: i18nService.t('typeLogin'), value: CipherType.Login },
|
||||||
{ name: i18nService.t('typeCard'), value: CipherType.Card },
|
{ name: i18nService.t('typeCard'), value: CipherType.Card },
|
||||||
@@ -154,11 +154,11 @@ export class AddEditComponent implements OnInit {
|
|||||||
if (await this.policyService.policyAppliesToUser(PolicyType.PersonalOwnership)) {
|
if (await this.policyService.policyAppliesToUser(PolicyType.PersonalOwnership)) {
|
||||||
this.allowPersonal = false;
|
this.allowPersonal = false;
|
||||||
} else {
|
} else {
|
||||||
const myEmail = await this.userService.getEmail();
|
const myEmail = await this.stateService.getEmail();
|
||||||
this.ownershipOptions.push({ name: myEmail, value: null });
|
this.ownershipOptions.push({ name: myEmail, value: null });
|
||||||
}
|
}
|
||||||
|
|
||||||
const orgs = await this.userService.getAllOrganizations();
|
const orgs = await this.organizationService.getAll();
|
||||||
orgs.sort(Utils.getSortFunction(this.i18nService, 'name')).forEach(o => {
|
orgs.sort(Utils.getSortFunction(this.i18nService, 'name')).forEach(o => {
|
||||||
if (o.enabled && o.status === OrganizationUserStatusType.Confirmed) {
|
if (o.enabled && o.status === OrganizationUserStatusType.Confirmed) {
|
||||||
this.ownershipOptions.push({ name: o.name, value: o.id });
|
this.ownershipOptions.push({ name: o.name, value: o.id });
|
||||||
@@ -185,12 +185,12 @@ export class AddEditComponent implements OnInit {
|
|||||||
this.title = this.i18nService.t('addItem');
|
this.title = this.i18nService.t('addItem');
|
||||||
}
|
}
|
||||||
|
|
||||||
const addEditCipherInfo: any = await this.stateService.get<any>('addEditCipherInfo');
|
const addEditCipherInfo: any = await this.stateService.getAddEditCipherInfo();
|
||||||
if (addEditCipherInfo != null) {
|
if (addEditCipherInfo != null) {
|
||||||
this.cipher = addEditCipherInfo.cipher;
|
this.cipher = addEditCipherInfo.cipher;
|
||||||
this.collectionIds = addEditCipherInfo.collectionIds;
|
this.collectionIds = addEditCipherInfo.collectionIds;
|
||||||
}
|
}
|
||||||
await this.stateService.remove('addEditCipherInfo');
|
await this.stateService.setAddEditCipherInfo(null);
|
||||||
|
|
||||||
if (this.cipher == null) {
|
if (this.cipher == null) {
|
||||||
if (this.editMode) {
|
if (this.editMode) {
|
||||||
@@ -434,7 +434,7 @@ export class AddEditComponent implements OnInit {
|
|||||||
}
|
}
|
||||||
if (this.cipher.organizationId != null) {
|
if (this.cipher.organizationId != null) {
|
||||||
this.collections = this.writeableCollections.filter(c => c.organizationId === this.cipher.organizationId);
|
this.collections = this.writeableCollections.filter(c => c.organizationId === this.cipher.organizationId);
|
||||||
const org = await this.userService.getOrganization(this.cipher.organizationId);
|
const org = await this.organizationService.get(this.cipher.organizationId);
|
||||||
if (org != null) {
|
if (org != null) {
|
||||||
this.cipher.organizationUseTotp = org.useTotp;
|
this.cipher.organizationUseTotp = org.useTotp;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ import { CryptoService } from 'jslib-common/abstractions/crypto.service';
|
|||||||
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
||||||
import { LogService } from 'jslib-common/abstractions/log.service';
|
import { LogService } from 'jslib-common/abstractions/log.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
|
|
||||||
import { Cipher } from 'jslib-common/models/domain/cipher';
|
import { Cipher } from 'jslib-common/models/domain/cipher';
|
||||||
import { ErrorResponse } from 'jslib-common/models/response/errorResponse';
|
import { ErrorResponse } from 'jslib-common/models/response/errorResponse';
|
||||||
@@ -37,9 +37,9 @@ export class AttachmentsComponent implements OnInit {
|
|||||||
emergencyAccessId?: string = null;
|
emergencyAccessId?: string = null;
|
||||||
|
|
||||||
constructor(protected cipherService: CipherService, protected i18nService: I18nService,
|
constructor(protected cipherService: CipherService, protected i18nService: I18nService,
|
||||||
protected cryptoService: CryptoService, protected userService: UserService,
|
protected cryptoService: CryptoService, protected platformUtilsService: PlatformUtilsService,
|
||||||
protected platformUtilsService: PlatformUtilsService, protected apiService: ApiService,
|
protected apiService: ApiService, protected win: Window,
|
||||||
protected win: Window, private logService: LogService) { }
|
protected logService: LogService, protected stateService: StateService) { }
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
await this.init();
|
await this.init();
|
||||||
@@ -164,7 +164,7 @@ export class AttachmentsComponent implements OnInit {
|
|||||||
this.cipher = await this.cipherDomain.decrypt();
|
this.cipher = await this.cipherDomain.decrypt();
|
||||||
|
|
||||||
this.hasUpdatedKey = await this.cryptoService.hasEncKey();
|
this.hasUpdatedKey = await this.cryptoService.hasEncKey();
|
||||||
const canAccessPremium = await this.userService.canAccessPremium();
|
const canAccessPremium = await this.stateService.getCanAccessPremium();
|
||||||
this.canAccessAttachments = canAccessPremium || this.cipher.organizationId != null;
|
this.canAccessAttachments = canAccessPremium || this.cipher.organizationId != null;
|
||||||
|
|
||||||
if (!this.canAccessAttachments) {
|
if (!this.canAccessAttachments) {
|
||||||
|
|||||||
@@ -45,7 +45,7 @@ export class AvatarComponent implements OnChanges, OnInit {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async generate() {
|
private async generate() {
|
||||||
const enableGravatars = await this.stateService.get<boolean>('enableGravatars');
|
const enableGravatars = await this.stateService.getEnableGravitars();
|
||||||
if (enableGravatars && this.email != null) {
|
if (enableGravatars && this.email != null) {
|
||||||
const hashBytes = await this.cryptoFunctionService.hash(this.email.toLowerCase().trim(), 'md5');
|
const hashBytes = await this.cryptoFunctionService.hash(this.email.toLowerCase().trim(), 'md5');
|
||||||
const hash = Utils.fromBufferToHex(hashBytes).toLowerCase();
|
const hash = Utils.fromBufferToHex(hashBytes).toLowerCase();
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
|||||||
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
|
|
||||||
import { EncString } from 'jslib-common/models/domain/encString';
|
import { EncString } from 'jslib-common/models/domain/encString';
|
||||||
import { MasterPasswordPolicyOptions } from 'jslib-common/models/domain/masterPasswordPolicyOptions';
|
import { MasterPasswordPolicyOptions } from 'jslib-common/models/domain/masterPasswordPolicyOptions';
|
||||||
@@ -29,12 +29,12 @@ export class ChangePasswordComponent implements OnInit {
|
|||||||
private masterPasswordStrengthTimeout: any;
|
private masterPasswordStrengthTimeout: any;
|
||||||
|
|
||||||
constructor(protected i18nService: I18nService, protected cryptoService: CryptoService,
|
constructor(protected i18nService: I18nService, protected cryptoService: CryptoService,
|
||||||
protected messagingService: MessagingService, protected userService: UserService,
|
protected messagingService: MessagingService, protected passwordGenerationService: PasswordGenerationService,
|
||||||
protected passwordGenerationService: PasswordGenerationService,
|
protected platformUtilsService: PlatformUtilsService, protected policyService: PolicyService,
|
||||||
protected platformUtilsService: PlatformUtilsService, protected policyService: PolicyService) { }
|
protected stateService: StateService) { }
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
this.email = await this.userService.getEmail();
|
this.email = await this.stateService.getEmail();
|
||||||
this.enforcedPolicyOptions = await this.policyService.getMasterPasswordPolicyOptions();
|
this.enforcedPolicyOptions = await this.policyService.getMasterPasswordPolicyOptions();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -47,12 +47,12 @@ export class ChangePasswordComponent implements OnInit {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const email = await this.userService.getEmail();
|
const email = await this.stateService.getEmail();
|
||||||
if (this.kdf == null) {
|
if (this.kdf == null) {
|
||||||
this.kdf = await this.userService.getKdf();
|
this.kdf = await this.stateService.getKdfType();
|
||||||
}
|
}
|
||||||
if (this.kdfIterations == null) {
|
if (this.kdfIterations == null) {
|
||||||
this.kdfIterations = await this.userService.getKdfIterations();
|
this.kdfIterations = await this.stateService.getKdfIterations();
|
||||||
}
|
}
|
||||||
const key = await this.cryptoService.makeKey(this.masterPassword, email.trim().toLowerCase(),
|
const key = await this.cryptoService.makeKey(this.masterPassword, email.trim().toLowerCase(),
|
||||||
this.kdf, this.kdfIterations);
|
this.kdf, this.kdfIterations);
|
||||||
|
|||||||
@@ -14,10 +14,7 @@ import { TreeNode } from 'jslib-common/models/domain/treeNode';
|
|||||||
|
|
||||||
import { CollectionService } from 'jslib-common/abstractions/collection.service';
|
import { CollectionService } from 'jslib-common/abstractions/collection.service';
|
||||||
import { FolderService } from 'jslib-common/abstractions/folder.service';
|
import { FolderService } from 'jslib-common/abstractions/folder.service';
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
|
|
||||||
import { ConstantsService } from 'jslib-common/services/constants.service';
|
|
||||||
|
|
||||||
@Directive()
|
@Directive()
|
||||||
export class GroupingsComponent {
|
export class GroupingsComponent {
|
||||||
@@ -50,15 +47,12 @@ export class GroupingsComponent {
|
|||||||
selectedCollectionId: string = null;
|
selectedCollectionId: string = null;
|
||||||
|
|
||||||
private collapsedGroupings: Set<string>;
|
private collapsedGroupings: Set<string>;
|
||||||
private collapsedGroupingsKey: string;
|
|
||||||
|
|
||||||
constructor(protected collectionService: CollectionService, protected folderService: FolderService,
|
constructor(protected collectionService: CollectionService, protected folderService: FolderService,
|
||||||
protected storageService: StorageService, protected userService: UserService) { }
|
private stateService: StateService) { }
|
||||||
|
|
||||||
async load(setLoaded = true) {
|
async load(setLoaded = true) {
|
||||||
const userId = await this.userService.getUserId();
|
const collapsedGroupings = await this.stateService.getCollapsedGroupings();
|
||||||
this.collapsedGroupingsKey = ConstantsService.collapsedGroupingsKey + '_' + userId;
|
|
||||||
const collapsedGroupings = await this.storageService.get<string[]>(this.collapsedGroupingsKey);
|
|
||||||
if (collapsedGroupings == null) {
|
if (collapsedGroupings == null) {
|
||||||
this.collapsedGroupings = new Set<string>();
|
this.collapsedGroupings = new Set<string>();
|
||||||
} else {
|
} else {
|
||||||
@@ -149,7 +143,7 @@ export class GroupingsComponent {
|
|||||||
this.selectedCollectionId = null;
|
this.selectedCollectionId = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
collapse(grouping: FolderView | CollectionView, idPrefix = '') {
|
async collapse(grouping: FolderView | CollectionView, idPrefix = '') {
|
||||||
if (grouping.id == null) {
|
if (grouping.id == null) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -159,7 +153,7 @@ export class GroupingsComponent {
|
|||||||
} else {
|
} else {
|
||||||
this.collapsedGroupings.add(id);
|
this.collapsedGroupings.add(id);
|
||||||
}
|
}
|
||||||
this.storageService.save(this.collapsedGroupingsKey, this.collapsedGroupings);
|
await this.stateService.setCollapsedGroupings(this.collapsedGroupings);
|
||||||
}
|
}
|
||||||
|
|
||||||
isCollapsed(grouping: FolderView | CollectionView, idPrefix = '') {
|
isCollapsed(grouping: FolderView | CollectionView, idPrefix = '') {
|
||||||
|
|||||||
@@ -11,8 +11,6 @@ import { CipherView } from 'jslib-common/models/view/cipherView';
|
|||||||
import { EnvironmentService } from 'jslib-common/abstractions/environment.service';
|
import { EnvironmentService } from 'jslib-common/abstractions/environment.service';
|
||||||
import { StateService } from 'jslib-common/abstractions/state.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
|
|
||||||
import { ConstantsService } from 'jslib-common/services/constants.service';
|
|
||||||
|
|
||||||
import { Utils } from 'jslib-common/misc/utils';
|
import { Utils } from 'jslib-common/misc/utils';
|
||||||
|
|
||||||
const IconMap: any = {
|
const IconMap: any = {
|
||||||
@@ -37,7 +35,7 @@ export class IconComponent implements OnChanges {
|
|||||||
|
|
||||||
private iconsUrl: string;
|
private iconsUrl: string;
|
||||||
|
|
||||||
constructor(environmentService: EnvironmentService, protected stateService: StateService) {
|
constructor(environmentService: EnvironmentService, private stateService: StateService) {
|
||||||
this.iconsUrl = environmentService.getIconsUrl();
|
this.iconsUrl = environmentService.getIconsUrl();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -46,7 +44,7 @@ export class IconComponent implements OnChanges {
|
|||||||
// to avoid this we reset all state variables.
|
// to avoid this we reset all state variables.
|
||||||
this.image = null;
|
this.image = null;
|
||||||
this.fallbackImage = null;
|
this.fallbackImage = null;
|
||||||
this.imageEnabled = !(await this.stateService.get<boolean>(ConstantsService.disableFaviconKey));
|
this.imageEnabled = !(await this.stateService.getDisableFavicon());
|
||||||
this.load();
|
this.load();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -9,12 +9,8 @@ import { LogService } from 'jslib-common/abstractions/log.service';
|
|||||||
import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { StateService } from 'jslib-common/abstractions/state.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
import { VaultTimeoutService } from 'jslib-common/abstractions/vaultTimeout.service';
|
import { VaultTimeoutService } from 'jslib-common/abstractions/vaultTimeout.service';
|
||||||
|
|
||||||
import { ConstantsService } from 'jslib-common/services/constants.service';
|
|
||||||
|
|
||||||
import { EncString } from 'jslib-common/models/domain/encString';
|
import { EncString } from 'jslib-common/models/domain/encString';
|
||||||
import { SymmetricCryptoKey } from 'jslib-common/models/domain/symmetricCryptoKey';
|
import { SymmetricCryptoKey } from 'jslib-common/models/domain/symmetricCryptoKey';
|
||||||
|
|
||||||
@@ -23,6 +19,7 @@ import { PasswordVerificationRequest } from 'jslib-common/models/request/passwor
|
|||||||
import { Utils } from 'jslib-common/misc/utils';
|
import { Utils } from 'jslib-common/misc/utils';
|
||||||
|
|
||||||
import { HashPurpose } from 'jslib-common/enums/hashPurpose';
|
import { HashPurpose } from 'jslib-common/enums/hashPurpose';
|
||||||
|
import { KeySuffixOptions } from 'jslib-common/enums/keySuffixOptions';
|
||||||
|
|
||||||
@Directive()
|
@Directive()
|
||||||
export class LockComponent implements OnInit {
|
export class LockComponent implements OnInit {
|
||||||
@@ -45,19 +42,18 @@ export class LockComponent implements OnInit {
|
|||||||
|
|
||||||
constructor(protected router: Router, protected i18nService: I18nService,
|
constructor(protected router: Router, protected i18nService: I18nService,
|
||||||
protected platformUtilsService: PlatformUtilsService, protected messagingService: MessagingService,
|
protected platformUtilsService: PlatformUtilsService, protected messagingService: MessagingService,
|
||||||
protected userService: UserService, protected cryptoService: CryptoService,
|
protected cryptoService: CryptoService, protected vaultTimeoutService: VaultTimeoutService,
|
||||||
protected storageService: StorageService, protected vaultTimeoutService: VaultTimeoutService,
|
|
||||||
protected environmentService: EnvironmentService, protected stateService: StateService,
|
protected environmentService: EnvironmentService, protected stateService: StateService,
|
||||||
protected apiService: ApiService, private logService: LogService) { }
|
protected apiService: ApiService, private logService: LogService) { }
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
this.pinSet = await this.vaultTimeoutService.isPinLockSet();
|
this.pinSet = await this.vaultTimeoutService.isPinLockSet();
|
||||||
this.pinLock = (this.pinSet[0] && this.vaultTimeoutService.pinProtectedKey != null) || this.pinSet[1];
|
this.pinLock = (this.pinSet[0] && (await this.stateService.getEncryptedPinProtected()) != null) || this.pinSet[1];
|
||||||
this.supportsBiometric = await this.platformUtilsService.supportsBiometric();
|
this.supportsBiometric = await this.platformUtilsService.supportsBiometric();
|
||||||
this.biometricLock = await this.vaultTimeoutService.isBiometricLockSet() &&
|
this.biometricLock = await this.vaultTimeoutService.isBiometricLockSet() &&
|
||||||
(await this.cryptoService.hasKeyStored('biometric') || !this.platformUtilsService.supportsSecureStorage());
|
(await this.cryptoService.hasKeyStored(KeySuffixOptions.Biometric) || !this.platformUtilsService.supportsSecureStorage());
|
||||||
this.biometricText = await this.storageService.get(ConstantsService.biometricText);
|
this.biometricText = await this.stateService.getBiometricText();
|
||||||
this.email = await this.userService.getEmail();
|
this.email = await this.stateService.getEmail();
|
||||||
|
|
||||||
const webVaultUrl = this.environmentService.getWebVaultUrl();
|
const webVaultUrl = this.environmentService.getWebVaultUrl();
|
||||||
const vaultUrl = webVaultUrl === 'https://vault.bitwarden.com' ? 'https://bitwarden.com' : webVaultUrl;
|
const vaultUrl = webVaultUrl === 'https://vault.bitwarden.com' ? 'https://bitwarden.com' : webVaultUrl;
|
||||||
@@ -76,17 +72,17 @@ export class LockComponent implements OnInit {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const kdf = await this.userService.getKdf();
|
const kdf = await this.stateService.getKdfType();
|
||||||
const kdfIterations = await this.userService.getKdfIterations();
|
const kdfIterations = await this.stateService.getKdfIterations();
|
||||||
|
|
||||||
if (this.pinLock) {
|
if (this.pinLock) {
|
||||||
let failed = true;
|
let failed = true;
|
||||||
try {
|
try {
|
||||||
if (this.pinSet[0]) {
|
if (this.pinSet[0]) {
|
||||||
const key = await this.cryptoService.makeKeyFromPin(this.pin, this.email, kdf, kdfIterations,
|
const key = await this.cryptoService.makeKeyFromPin(this.pin, this.email, kdf, kdfIterations,
|
||||||
this.vaultTimeoutService.pinProtectedKey);
|
await this.stateService.getDecryptedPinProtected());
|
||||||
const encKey = await this.cryptoService.getEncKey(key);
|
const encKey = await this.cryptoService.getEncKey(key);
|
||||||
const protectedPin = await this.storageService.get<string>(ConstantsService.protectedPin);
|
const protectedPin = await this.stateService.getProtectedPin();
|
||||||
const decPin = await this.cryptoService.decryptToUtf8(new EncString(protectedPin), encKey);
|
const decPin = await this.cryptoService.decryptToUtf8(new EncString(protectedPin), encKey);
|
||||||
failed = decPin !== this.pin;
|
failed = decPin !== this.pin;
|
||||||
if (!failed) {
|
if (!failed) {
|
||||||
@@ -137,11 +133,11 @@ export class LockComponent implements OnInit {
|
|||||||
|
|
||||||
if (passwordValid) {
|
if (passwordValid) {
|
||||||
if (this.pinSet[0]) {
|
if (this.pinSet[0]) {
|
||||||
const protectedPin = await this.storageService.get<string>(ConstantsService.protectedPin);
|
const protectedPin = await this.stateService.getProtectedPin();
|
||||||
const encKey = await this.cryptoService.getEncKey(key);
|
const encKey = await this.cryptoService.getEncKey(key);
|
||||||
const decPin = await this.cryptoService.decryptToUtf8(new EncString(protectedPin), encKey);
|
const decPin = await this.cryptoService.decryptToUtf8(new EncString(protectedPin), encKey);
|
||||||
const pinKey = await this.cryptoService.makePinKey(decPin, this.email, kdf, kdfIterations);
|
const pinKey = await this.cryptoService.makePinKey(decPin, this.email, kdf, kdfIterations);
|
||||||
this.vaultTimeoutService.pinProtectedKey = await this.cryptoService.encrypt(key.key, pinKey);
|
await this.stateService.setDecryptedPinProtected(await this.cryptoService.encrypt(key.key, pinKey));
|
||||||
}
|
}
|
||||||
this.setKeyAndContinue(key);
|
this.setKeyAndContinue(key);
|
||||||
} else {
|
} else {
|
||||||
@@ -164,7 +160,7 @@ export class LockComponent implements OnInit {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const success = (await this.cryptoService.getKey('biometric')) != null;
|
const success = (await this.cryptoService.getKey(KeySuffixOptions.Biometric)) != null;
|
||||||
|
|
||||||
if (success) {
|
if (success) {
|
||||||
await this.doContinue();
|
await this.doContinue();
|
||||||
@@ -184,10 +180,10 @@ export class LockComponent implements OnInit {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async doContinue() {
|
private async doContinue() {
|
||||||
this.vaultTimeoutService.biometricLocked = false;
|
await this.stateService.setBiometricLocked(false);
|
||||||
this.vaultTimeoutService.everBeenUnlocked = true;
|
await this.stateService.setEverBeenUnlocked(true);
|
||||||
const disableFavicon = await this.storageService.get<boolean>(ConstantsService.disableFaviconKey);
|
const disableFavicon = await this.stateService.getDisableFavicon();
|
||||||
await this.stateService.save(ConstantsService.disableFaviconKey, !!disableFavicon);
|
await this.stateService.setDisableFavicon(!!disableFavicon);
|
||||||
this.messagingService.send('unlocked');
|
this.messagingService.send('unlocked');
|
||||||
if (this.onSuccessfulSubmit != null) {
|
if (this.onSuccessfulSubmit != null) {
|
||||||
this.onSuccessfulSubmit();
|
this.onSuccessfulSubmit();
|
||||||
|
|||||||
@@ -16,19 +16,11 @@ import { LogService } from 'jslib-common/abstractions/log.service';
|
|||||||
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { StateService } from 'jslib-common/abstractions/state.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
|
||||||
|
|
||||||
import { ConstantsService } from 'jslib-common/services/constants.service';
|
|
||||||
|
|
||||||
import { Utils } from 'jslib-common/misc/utils';
|
import { Utils } from 'jslib-common/misc/utils';
|
||||||
|
|
||||||
import { CaptchaProtectedComponent } from './captchaProtected.component';
|
import { CaptchaProtectedComponent } from './captchaProtected.component';
|
||||||
|
|
||||||
const Keys = {
|
|
||||||
rememberedEmail: 'rememberedEmail',
|
|
||||||
rememberEmail: 'rememberEmail',
|
|
||||||
};
|
|
||||||
|
|
||||||
@Directive()
|
@Directive()
|
||||||
export class LoginComponent extends CaptchaProtectedComponent implements OnInit {
|
export class LoginComponent extends CaptchaProtectedComponent implements OnInit {
|
||||||
@Input() email: string = '';
|
@Input() email: string = '';
|
||||||
@@ -50,19 +42,18 @@ export class LoginComponent extends CaptchaProtectedComponent implements OnInit
|
|||||||
platformUtilsService: PlatformUtilsService, i18nService: I18nService,
|
platformUtilsService: PlatformUtilsService, i18nService: I18nService,
|
||||||
protected stateService: StateService, environmentService: EnvironmentService,
|
protected stateService: StateService, environmentService: EnvironmentService,
|
||||||
protected passwordGenerationService: PasswordGenerationService,
|
protected passwordGenerationService: PasswordGenerationService,
|
||||||
protected cryptoFunctionService: CryptoFunctionService, private storageService: StorageService,
|
protected cryptoFunctionService: CryptoFunctionService, protected logService: LogService) {
|
||||||
protected logService: LogService) {
|
|
||||||
super(environmentService, i18nService, platformUtilsService);
|
super(environmentService, i18nService, platformUtilsService);
|
||||||
}
|
}
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
if (this.email == null || this.email === '') {
|
if (this.email == null || this.email === '') {
|
||||||
this.email = await this.storageService.get<string>(Keys.rememberedEmail);
|
this.email = await this.stateService.getRememberedEmail();
|
||||||
if (this.email == null) {
|
if (this.email == null) {
|
||||||
this.email = '';
|
this.email = '';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
this.rememberEmail = await this.storageService.get<boolean>(Keys.rememberEmail);
|
this.rememberEmail = await this.stateService.getRememberEmail();
|
||||||
if (this.rememberEmail == null) {
|
if (this.rememberEmail == null) {
|
||||||
this.rememberEmail = true;
|
this.rememberEmail = true;
|
||||||
}
|
}
|
||||||
@@ -93,11 +84,10 @@ export class LoginComponent extends CaptchaProtectedComponent implements OnInit
|
|||||||
try {
|
try {
|
||||||
this.formPromise = this.authService.logIn(this.email, this.masterPassword, this.captchaToken);
|
this.formPromise = this.authService.logIn(this.email, this.masterPassword, this.captchaToken);
|
||||||
const response = await this.formPromise;
|
const response = await this.formPromise;
|
||||||
await this.storageService.save(Keys.rememberEmail, this.rememberEmail);
|
|
||||||
if (this.rememberEmail) {
|
if (this.rememberEmail) {
|
||||||
await this.storageService.save(Keys.rememberedEmail, this.email);
|
await this.stateService.setRememberedEmail(this.email);
|
||||||
} else {
|
} else {
|
||||||
await this.storageService.remove(Keys.rememberedEmail);
|
await this.stateService.setRememberedEmail(null);
|
||||||
}
|
}
|
||||||
if (this.handleCaptchaRequired(response)) {
|
if (this.handleCaptchaRequired(response)) {
|
||||||
return;
|
return;
|
||||||
@@ -114,8 +104,8 @@ export class LoginComponent extends CaptchaProtectedComponent implements OnInit
|
|||||||
this.router.navigate([this.forcePasswordResetRoute]);
|
this.router.navigate([this.forcePasswordResetRoute]);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
const disableFavicon = await this.storageService.get<boolean>(ConstantsService.disableFaviconKey);
|
const disableFavicon = await this.stateService.getDisableFavicon();
|
||||||
await this.stateService.save(ConstantsService.disableFaviconKey, !!disableFavicon);
|
await this.stateService.setDisableFavicon(!!disableFavicon);
|
||||||
if (this.onSuccessfulLogin != null) {
|
if (this.onSuccessfulLogin != null) {
|
||||||
this.onSuccessfulLogin();
|
this.onSuccessfulLogin();
|
||||||
}
|
}
|
||||||
@@ -151,8 +141,8 @@ export class LoginComponent extends CaptchaProtectedComponent implements OnInit
|
|||||||
const codeChallenge = Utils.fromBufferToUrlB64(codeVerifierHash);
|
const codeChallenge = Utils.fromBufferToUrlB64(codeVerifierHash);
|
||||||
|
|
||||||
// Save sso params
|
// Save sso params
|
||||||
await this.storageService.save(ConstantsService.ssoStateKey, state);
|
await this.stateService.setSsoState(state);
|
||||||
await this.storageService.save(ConstantsService.ssoCodeVerifierKey, ssoCodeVerifier);
|
await this.stateService.setSsoCodeVerifier(ssoCodeVerifier);
|
||||||
|
|
||||||
// Build URI
|
// Build URI
|
||||||
const webUrl = this.environmentService.getWebVaultUrl();
|
const webUrl = this.environmentService.getWebVaultUrl();
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ import { ApiService } from 'jslib-common/abstractions/api.service';
|
|||||||
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
||||||
import { LogService } from 'jslib-common/abstractions/log.service';
|
import { LogService } from 'jslib-common/abstractions/log.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
|
|
||||||
@Directive()
|
@Directive()
|
||||||
export class PremiumComponent implements OnInit {
|
export class PremiumComponent implements OnInit {
|
||||||
@@ -13,10 +13,11 @@ export class PremiumComponent implements OnInit {
|
|||||||
refreshPromise: Promise<any>;
|
refreshPromise: Promise<any>;
|
||||||
|
|
||||||
constructor(protected i18nService: I18nService, protected platformUtilsService: PlatformUtilsService,
|
constructor(protected i18nService: I18nService, protected platformUtilsService: PlatformUtilsService,
|
||||||
protected apiService: ApiService, protected userService: UserService, private logService: LogService) { }
|
protected apiService: ApiService, private logService: LogService,
|
||||||
|
protected stateService: StateService) { }
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
this.isPremium = await this.userService.canAccessPremium();
|
this.isPremium = await this.stateService.getCanAccessPremium();
|
||||||
}
|
}
|
||||||
|
|
||||||
async refresh() {
|
async refresh() {
|
||||||
@@ -24,7 +25,7 @@ export class PremiumComponent implements OnInit {
|
|||||||
this.refreshPromise = this.apiService.refreshIdentityToken();
|
this.refreshPromise = this.apiService.refreshIdentityToken();
|
||||||
await this.refreshPromise;
|
await this.refreshPromise;
|
||||||
this.platformUtilsService.showToast('success', null, this.i18nService.t('refreshComplete'));
|
this.platformUtilsService.showToast('success', null, this.i18nService.t('refreshComplete'));
|
||||||
this.isPremium = await this.userService.canAccessPremium();
|
this.isPremium = await this.stateService.getCanAccessPremium();
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
this.logService.error(e);
|
this.logService.error(e);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -141,7 +141,7 @@ export class RegisterComponent extends CaptchaProtectedComponent implements OnIn
|
|||||||
const request = new RegisterRequest(this.email, this.name, hashedPassword,
|
const request = new RegisterRequest(this.email, this.name, hashedPassword,
|
||||||
this.hint, encKey[1].encryptedString, kdf, kdfIterations, this.referenceData, this.captchaToken);
|
this.hint, encKey[1].encryptedString, kdf, kdfIterations, this.referenceData, this.captchaToken);
|
||||||
request.keys = new KeysRequest(keys[0], keys[1].encryptedString);
|
request.keys = new KeysRequest(keys[0], keys[1].encryptedString);
|
||||||
const orgInvite = await this.stateService.get<any>('orgInvitation');
|
const orgInvite = await this.stateService.getOrganizationInvitation();
|
||||||
if (orgInvite != null && orgInvite.token != null && orgInvite.organizationUserId != null) {
|
if (orgInvite != null && orgInvite.token != null && orgInvite.organizationUserId != null) {
|
||||||
request.token = orgInvite.token;
|
request.token = orgInvite.token;
|
||||||
request.organizationUserId = orgInvite.organizationUserId;
|
request.organizationUserId = orgInvite.organizationUserId;
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
|||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
||||||
import { SendService } from 'jslib-common/abstractions/send.service';
|
import { SendService } from 'jslib-common/abstractions/send.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
|
|
||||||
import { SendFileView } from 'jslib-common/models/view/sendFileView';
|
import { SendFileView } from 'jslib-common/models/view/sendFileView';
|
||||||
import { SendTextView } from 'jslib-common/models/view/sendTextView';
|
import { SendTextView } from 'jslib-common/models/view/sendTextView';
|
||||||
@@ -57,9 +57,9 @@ export class AddEditComponent implements OnInit {
|
|||||||
|
|
||||||
constructor(protected i18nService: I18nService, protected platformUtilsService: PlatformUtilsService,
|
constructor(protected i18nService: I18nService, protected platformUtilsService: PlatformUtilsService,
|
||||||
protected environmentService: EnvironmentService, protected datePipe: DatePipe,
|
protected environmentService: EnvironmentService, protected datePipe: DatePipe,
|
||||||
protected sendService: SendService, protected userService: UserService,
|
protected sendService: SendService, protected messagingService: MessagingService,
|
||||||
protected messagingService: MessagingService, protected policyService: PolicyService,
|
protected policyService: PolicyService, private logService: LogService,
|
||||||
private logService: LogService) {
|
protected stateService: StateService) {
|
||||||
this.typeOptions = [
|
this.typeOptions = [
|
||||||
{ name: i18nService.t('sendTypeFile'), value: SendType.File },
|
{ name: i18nService.t('sendTypeFile'), value: SendType.File },
|
||||||
{ name: i18nService.t('sendTypeText'), value: SendType.Text },
|
{ name: i18nService.t('sendTypeText'), value: SendType.Text },
|
||||||
@@ -108,8 +108,8 @@ export class AddEditComponent implements OnInit {
|
|||||||
this.disableHideEmail = await this.policyService.policyAppliesToUser(PolicyType.SendOptions,
|
this.disableHideEmail = await this.policyService.policyAppliesToUser(PolicyType.SendOptions,
|
||||||
p => p.data.disableHideEmail);
|
p => p.data.disableHideEmail);
|
||||||
|
|
||||||
this.canAccessPremium = await this.userService.canAccessPremium();
|
this.canAccessPremium = await this.stateService.getCanAccessPremium();
|
||||||
this.emailVerified = await this.userService.getEmailVerified();
|
this.emailVerified = await this.stateService.getEmailVerified();
|
||||||
if (!this.canAccessPremium || !this.emailVerified) {
|
if (!this.canAccessPremium || !this.emailVerified) {
|
||||||
this.type = SendType.Text;
|
this.type = SendType.Text;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -16,7 +16,6 @@ import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.se
|
|||||||
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
||||||
import { SearchService } from 'jslib-common/abstractions/search.service';
|
import { SearchService } from 'jslib-common/abstractions/search.service';
|
||||||
import { SendService } from 'jslib-common/abstractions/send.service';
|
import { SendService } from 'jslib-common/abstractions/send.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
|
|
||||||
@Directive()
|
@Directive()
|
||||||
export class SendComponent implements OnInit {
|
export class SendComponent implements OnInit {
|
||||||
@@ -48,8 +47,7 @@ export class SendComponent implements OnInit {
|
|||||||
constructor(protected sendService: SendService, protected i18nService: I18nService,
|
constructor(protected sendService: SendService, protected i18nService: I18nService,
|
||||||
protected platformUtilsService: PlatformUtilsService, protected environmentService: EnvironmentService,
|
protected platformUtilsService: PlatformUtilsService, protected environmentService: EnvironmentService,
|
||||||
protected ngZone: NgZone, protected searchService: SearchService,
|
protected ngZone: NgZone, protected searchService: SearchService,
|
||||||
protected policyService: PolicyService, protected userService: UserService,
|
protected policyService: PolicyService, private logService: LogService) { }
|
||||||
private logService: LogService) { }
|
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
this.disableSend = await this.policyService.policyAppliesToUser(PolicyType.DisableSend);
|
this.disableSend = await this.policyService.policyAppliesToUser(PolicyType.DisableSend);
|
||||||
|
|||||||
@@ -13,8 +13,8 @@ import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
|||||||
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
||||||
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { SyncService } from 'jslib-common/abstractions/sync.service';
|
import { SyncService } from 'jslib-common/abstractions/sync.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
|
|
||||||
import { EncString } from 'jslib-common/models/domain/encString';
|
import { EncString } from 'jslib-common/models/domain/encString';
|
||||||
import { SymmetricCryptoKey } from 'jslib-common/models/domain/symmetricCryptoKey';
|
import { SymmetricCryptoKey } from 'jslib-common/models/domain/symmetricCryptoKey';
|
||||||
@@ -42,12 +42,13 @@ export class SetPasswordComponent extends BaseChangePasswordComponent {
|
|||||||
onSuccessfulChangePassword: () => Promise<any>;
|
onSuccessfulChangePassword: () => Promise<any>;
|
||||||
successRoute = 'vault';
|
successRoute = 'vault';
|
||||||
|
|
||||||
constructor(i18nService: I18nService, cryptoService: CryptoService, messagingService: MessagingService,
|
constructor(i18nService: I18nService, cryptoService: CryptoService,
|
||||||
userService: UserService, passwordGenerationService: PasswordGenerationService,
|
messagingService: MessagingService, passwordGenerationService: PasswordGenerationService,
|
||||||
platformUtilsService: PlatformUtilsService, policyService: PolicyService, protected router: Router,
|
platformUtilsService: PlatformUtilsService, policyService: PolicyService,
|
||||||
private apiService: ApiService, private syncService: SyncService, private route: ActivatedRoute) {
|
protected router: Router, private apiService: ApiService,
|
||||||
super(i18nService, cryptoService, messagingService, userService, passwordGenerationService,
|
private syncService: SyncService, private route: ActivatedRoute, stateService: StateService) {
|
||||||
platformUtilsService, policyService);
|
super(i18nService, cryptoService, messagingService, passwordGenerationService,
|
||||||
|
platformUtilsService, policyService, stateService);
|
||||||
}
|
}
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
@@ -102,7 +103,7 @@ export class SetPasswordComponent extends BaseChangePasswordComponent {
|
|||||||
if (response == null) {
|
if (response == null) {
|
||||||
throw new Error(this.i18nService.t('resetPasswordOrgKeysError'));
|
throw new Error(this.i18nService.t('resetPasswordOrgKeysError'));
|
||||||
}
|
}
|
||||||
const userId = await this.userService.getUserId();
|
const userId = await this.stateService.getUserId();
|
||||||
const publicKey = Utils.fromB64ToArray(response.publicKey);
|
const publicKey = Utils.fromB64ToArray(response.publicKey);
|
||||||
|
|
||||||
// RSA Encrypt user's encKey.key with organization public key
|
// RSA Encrypt user's encKey.key with organization public key
|
||||||
@@ -138,8 +139,8 @@ export class SetPasswordComponent extends BaseChangePasswordComponent {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private async onSetPasswordSuccess(key: SymmetricCryptoKey, encKey: [SymmetricCryptoKey, EncString], keys: [string, EncString]) {
|
private async onSetPasswordSuccess(key: SymmetricCryptoKey, encKey: [SymmetricCryptoKey, EncString], keys: [string, EncString]) {
|
||||||
await this.userService.setInformation(await this.userService.getUserId(), await this.userService.getEmail(),
|
await this.stateService.setKdfType(this.kdf);
|
||||||
this.kdf, this.kdfIterations);
|
await this.stateService.setKdfIterations(this.kdfIterations);
|
||||||
await this.cryptoService.setKey(key);
|
await this.cryptoService.setKey(key);
|
||||||
await this.cryptoService.setEncKey(encKey[1].encryptedString);
|
await this.cryptoService.setEncKey(encKey[1].encryptedString);
|
||||||
await this.cryptoService.setEncPrivateKey(keys[1].encryptedString);
|
await this.cryptoService.setEncPrivateKey(keys[1].encryptedString);
|
||||||
|
|||||||
@@ -1,11 +1,7 @@
|
|||||||
import { Directive } from '@angular/core';
|
import { Directive } from '@angular/core';
|
||||||
|
|
||||||
import { CryptoService } from 'jslib-common/abstractions/crypto.service';
|
import { CryptoService } from 'jslib-common/abstractions/crypto.service';
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
import { VaultTimeoutService } from 'jslib-common/abstractions/vaultTimeout.service';
|
|
||||||
|
|
||||||
import { ConstantsService } from 'jslib-common/services/constants.service';
|
|
||||||
|
|
||||||
import { Utils } from 'jslib-common/misc/utils';
|
import { Utils } from 'jslib-common/misc/utils';
|
||||||
|
|
||||||
@@ -18,8 +14,8 @@ export class SetPinComponent {
|
|||||||
showPin = false;
|
showPin = false;
|
||||||
masterPassOnRestart = true;
|
masterPassOnRestart = true;
|
||||||
|
|
||||||
constructor(private modalRef: ModalRef, private cryptoService: CryptoService, private userService: UserService,
|
constructor(private modalRef: ModalRef, private cryptoService: CryptoService,
|
||||||
private storageService: StorageService, private vaultTimeoutService: VaultTimeoutService) { }
|
private stateService: StateService) { }
|
||||||
|
|
||||||
toggleVisibility() {
|
toggleVisibility() {
|
||||||
this.showPin = !this.showPin;
|
this.showPin = !this.showPin;
|
||||||
@@ -30,18 +26,18 @@ export class SetPinComponent {
|
|||||||
this.modalRef.close(false);
|
this.modalRef.close(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
const kdf = await this.userService.getKdf();
|
const kdf = await this.stateService.getKdfType();
|
||||||
const kdfIterations = await this.userService.getKdfIterations();
|
const kdfIterations = await this.stateService.getKdfIterations();
|
||||||
const email = await this.userService.getEmail();
|
const email = await this.stateService.getEmail();
|
||||||
const pinKey = await this.cryptoService.makePinKey(this.pin, email, kdf, kdfIterations);
|
const pinKey = await this.cryptoService.makePinKey(this.pin, email, kdf, kdfIterations);
|
||||||
const key = await this.cryptoService.getKey();
|
const key = await this.cryptoService.getKey();
|
||||||
const pinProtectedKey = await this.cryptoService.encrypt(key.key, pinKey);
|
const pinProtectedKey = await this.cryptoService.encrypt(key.key, pinKey);
|
||||||
if (this.masterPassOnRestart) {
|
if (this.masterPassOnRestart) {
|
||||||
const encPin = await this.cryptoService.encrypt(this.pin);
|
const encPin = await this.cryptoService.encrypt(this.pin);
|
||||||
await this.storageService.save(ConstantsService.protectedPin, encPin.encryptedString);
|
await this.stateService.setProtectedPin(encPin.encryptedString);
|
||||||
this.vaultTimeoutService.pinProtectedKey = pinProtectedKey;
|
await this.stateService.setDecryptedPinProtected(pinProtectedKey);
|
||||||
} else {
|
} else {
|
||||||
await this.storageService.save(ConstantsService.pinProtectedKey, pinProtectedKey.encryptedString);
|
await this.stateService.setEncryptedPinProtected(pinProtectedKey.encryptedString);
|
||||||
}
|
}
|
||||||
|
|
||||||
this.modalRef.close(true);
|
this.modalRef.close(true);
|
||||||
|
|||||||
@@ -12,8 +12,8 @@ import { CipherService } from 'jslib-common/abstractions/cipher.service';
|
|||||||
import { CollectionService } from 'jslib-common/abstractions/collection.service';
|
import { CollectionService } from 'jslib-common/abstractions/collection.service';
|
||||||
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
||||||
import { LogService } from 'jslib-common/abstractions/log.service';
|
import { LogService } from 'jslib-common/abstractions/log.service';
|
||||||
|
import { OrganizationService } from 'jslib-common/abstractions/organization.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
|
|
||||||
import { Organization } from 'jslib-common/models/domain/organization';
|
import { Organization } from 'jslib-common/models/domain/organization';
|
||||||
import { CipherView } from 'jslib-common/models/view/cipherView';
|
import { CipherView } from 'jslib-common/models/view/cipherView';
|
||||||
@@ -35,8 +35,8 @@ export class ShareComponent implements OnInit {
|
|||||||
protected writeableCollections: CollectionView[] = [];
|
protected writeableCollections: CollectionView[] = [];
|
||||||
|
|
||||||
constructor(protected collectionService: CollectionService, protected platformUtilsService: PlatformUtilsService,
|
constructor(protected collectionService: CollectionService, protected platformUtilsService: PlatformUtilsService,
|
||||||
protected i18nService: I18nService, protected userService: UserService,
|
protected i18nService: I18nService, protected cipherService: CipherService,
|
||||||
protected cipherService: CipherService, private logService: LogService) { }
|
private logService: LogService, protected organizationService: OrganizationService) { }
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
await this.load();
|
await this.load();
|
||||||
@@ -45,7 +45,7 @@ export class ShareComponent implements OnInit {
|
|||||||
async load() {
|
async load() {
|
||||||
const allCollections = await this.collectionService.getAllDecrypted();
|
const allCollections = await this.collectionService.getAllDecrypted();
|
||||||
this.writeableCollections = allCollections.map(c => c).filter(c => !c.readOnly);
|
this.writeableCollections = allCollections.map(c => c).filter(c => !c.readOnly);
|
||||||
const orgs = await this.userService.getAllOrganizations();
|
const orgs = await this.organizationService.getAll();
|
||||||
this.organizations = orgs.sort(Utils.getSortFunction(this.i18nService, 'name'))
|
this.organizations = orgs.sort(Utils.getSortFunction(this.i18nService, 'name'))
|
||||||
.filter(o => o.enabled && o.status === OrganizationUserStatusType.Confirmed);
|
.filter(o => o.enabled && o.status === OrganizationUserStatusType.Confirmed);
|
||||||
|
|
||||||
|
|||||||
@@ -15,9 +15,6 @@ import { LogService } from 'jslib-common/abstractions/log.service';
|
|||||||
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { StateService } from 'jslib-common/abstractions/state.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
|
||||||
|
|
||||||
import { ConstantsService } from 'jslib-common/services/constants.service';
|
|
||||||
|
|
||||||
import { Utils } from 'jslib-common/misc/utils';
|
import { Utils } from 'jslib-common/misc/utils';
|
||||||
|
|
||||||
@@ -47,18 +44,18 @@ export class SsoComponent {
|
|||||||
|
|
||||||
constructor(protected authService: AuthService, protected router: Router,
|
constructor(protected authService: AuthService, protected router: Router,
|
||||||
protected i18nService: I18nService, protected route: ActivatedRoute,
|
protected i18nService: I18nService, protected route: ActivatedRoute,
|
||||||
protected storageService: StorageService, protected stateService: StateService,
|
protected stateService: StateService, protected platformUtilsService: PlatformUtilsService,
|
||||||
protected platformUtilsService: PlatformUtilsService, protected apiService: ApiService,
|
protected apiService: ApiService, protected cryptoFunctionService: CryptoFunctionService,
|
||||||
protected cryptoFunctionService: CryptoFunctionService, protected environmentService: EnvironmentService,
|
protected environmentService: EnvironmentService, protected passwordGenerationService: PasswordGenerationService,
|
||||||
protected passwordGenerationService: PasswordGenerationService, protected logService: LogService) { }
|
protected logService: LogService) { }
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
this.route.queryParams.pipe(first()).subscribe(async qParams => {
|
this.route.queryParams.pipe(first()).subscribe(async qParams => {
|
||||||
if (qParams.code != null && qParams.state != null) {
|
if (qParams.code != null && qParams.state != null) {
|
||||||
const codeVerifier = await this.storageService.get<string>(ConstantsService.ssoCodeVerifierKey);
|
const codeVerifier = await this.stateService.getSsoCodeVerifier();
|
||||||
const state = await this.storageService.get<string>(ConstantsService.ssoStateKey);
|
const state = await this.stateService.getSsoState();
|
||||||
await this.storageService.remove(ConstantsService.ssoCodeVerifierKey);
|
await this.stateService.setSsoCodeVerifier(null);
|
||||||
await this.storageService.remove(ConstantsService.ssoStateKey);
|
await this.stateService.setSsoState(null);
|
||||||
if (qParams.code != null && codeVerifier != null && state != null && this.checkState(state, qParams.state)) {
|
if (qParams.code != null && codeVerifier != null && state != null && this.checkState(state, qParams.state)) {
|
||||||
await this.logIn(qParams.code, codeVerifier, this.getOrgIdentiferFromState(qParams.state));
|
await this.logIn(qParams.code, codeVerifier, this.getOrgIdentiferFromState(qParams.state));
|
||||||
}
|
}
|
||||||
@@ -106,7 +103,7 @@ export class SsoComponent {
|
|||||||
const codeVerifier = await this.passwordGenerationService.generatePassword(passwordOptions);
|
const codeVerifier = await this.passwordGenerationService.generatePassword(passwordOptions);
|
||||||
const codeVerifierHash = await this.cryptoFunctionService.hash(codeVerifier, 'sha256');
|
const codeVerifierHash = await this.cryptoFunctionService.hash(codeVerifier, 'sha256');
|
||||||
codeChallenge = Utils.fromBufferToUrlB64(codeVerifierHash);
|
codeChallenge = Utils.fromBufferToUrlB64(codeVerifierHash);
|
||||||
await this.storageService.save(ConstantsService.ssoCodeVerifierKey, codeVerifier);
|
await this.stateService.setSsoCodeVerifier(codeVerifier);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (state == null) {
|
if (state == null) {
|
||||||
@@ -120,7 +117,7 @@ export class SsoComponent {
|
|||||||
state += `_identifier=${this.identifier}`;
|
state += `_identifier=${this.identifier}`;
|
||||||
|
|
||||||
// Save state (regardless of new or existing)
|
// Save state (regardless of new or existing)
|
||||||
await this.storageService.save(ConstantsService.ssoStateKey, state);
|
await this.stateService.setSsoState(state);
|
||||||
|
|
||||||
let authorizeUrl = this.environmentService.getIdentityUrl() + '/connect/authorize?' +
|
let authorizeUrl = this.environmentService.getIdentityUrl() + '/connect/authorize?' +
|
||||||
'client_id=' + this.clientId + '&redirect_uri=' + encodeURIComponent(this.redirectUri) + '&' +
|
'client_id=' + this.clientId + '&redirect_uri=' + encodeURIComponent(this.redirectUri) + '&' +
|
||||||
@@ -170,8 +167,8 @@ export class SsoComponent {
|
|||||||
this.router.navigate([this.forcePasswordResetRoute]);
|
this.router.navigate([this.forcePasswordResetRoute]);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
const disableFavicon = await this.storageService.get<boolean>(ConstantsService.disableFaviconKey);
|
const disableFavicon = await this.stateService.getDisableFavicon();
|
||||||
await this.stateService.save(ConstantsService.disableFaviconKey, !!disableFavicon);
|
await this.stateService.setDisableFavicon(!!disableFavicon);
|
||||||
if (this.onSuccessfulLogin != null) {
|
if (this.onSuccessfulLogin != null) {
|
||||||
this.onSuccessfulLogin();
|
this.onSuccessfulLogin();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -20,10 +20,8 @@ import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
|||||||
import { LogService } from 'jslib-common/abstractions/log.service';
|
import { LogService } from 'jslib-common/abstractions/log.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { StateService } from 'jslib-common/abstractions/state.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
|
||||||
|
|
||||||
import { TwoFactorProviders } from 'jslib-common/services/auth.service';
|
import { TwoFactorProviders } from 'jslib-common/services/auth.service';
|
||||||
import { ConstantsService } from 'jslib-common/services/constants.service';
|
|
||||||
|
|
||||||
import * as DuoWebSDK from 'duo_web_sdk';
|
import * as DuoWebSDK from 'duo_web_sdk';
|
||||||
import { WebAuthnIFrame } from 'jslib-common/misc/webauthn_iframe';
|
import { WebAuthnIFrame } from 'jslib-common/misc/webauthn_iframe';
|
||||||
@@ -58,8 +56,7 @@ export class TwoFactorComponent implements OnInit, OnDestroy {
|
|||||||
protected i18nService: I18nService, protected apiService: ApiService,
|
protected i18nService: I18nService, protected apiService: ApiService,
|
||||||
protected platformUtilsService: PlatformUtilsService, protected win: Window,
|
protected platformUtilsService: PlatformUtilsService, protected win: Window,
|
||||||
protected environmentService: EnvironmentService, protected stateService: StateService,
|
protected environmentService: EnvironmentService, protected stateService: StateService,
|
||||||
protected storageService: StorageService, protected route: ActivatedRoute,
|
protected route: ActivatedRoute, protected logService: LogService) {
|
||||||
protected logService: LogService) {
|
|
||||||
this.webAuthnSupported = this.platformUtilsService.supportsWebAuthn(win);
|
this.webAuthnSupported = this.platformUtilsService.supportsWebAuthn(win);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -179,8 +176,8 @@ export class TwoFactorComponent implements OnInit, OnDestroy {
|
|||||||
async doSubmit() {
|
async doSubmit() {
|
||||||
this.formPromise = this.authService.logInTwoFactor(this.selectedProviderType, this.token, this.remember);
|
this.formPromise = this.authService.logInTwoFactor(this.selectedProviderType, this.token, this.remember);
|
||||||
const response: AuthResult = await this.formPromise;
|
const response: AuthResult = await this.formPromise;
|
||||||
const disableFavicon = await this.storageService.get<boolean>(ConstantsService.disableFaviconKey);
|
const disableFavicon = await this.stateService.getDisableFavicon();
|
||||||
await this.stateService.save(ConstantsService.disableFaviconKey, !!disableFavicon);
|
await this.stateService.setDisableFavicon(!!disableFavicon);
|
||||||
if (this.onSuccessfulLogin != null) {
|
if (this.onSuccessfulLogin != null) {
|
||||||
this.onSuccessfulLogin();
|
this.onSuccessfulLogin();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -8,8 +8,8 @@ import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
|||||||
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
||||||
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { SyncService } from 'jslib-common/abstractions/sync.service';
|
import { SyncService } from 'jslib-common/abstractions/sync.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
|
|
||||||
import { ChangePasswordComponent as BaseChangePasswordComponent } from './change-password.component';
|
import { ChangePasswordComponent as BaseChangePasswordComponent } from './change-password.component';
|
||||||
|
|
||||||
@@ -30,11 +30,11 @@ export class UpdateTempPasswordComponent extends BaseChangePasswordComponent {
|
|||||||
|
|
||||||
constructor(i18nService: I18nService, platformUtilsService: PlatformUtilsService,
|
constructor(i18nService: I18nService, platformUtilsService: PlatformUtilsService,
|
||||||
passwordGenerationService: PasswordGenerationService, policyService: PolicyService,
|
passwordGenerationService: PasswordGenerationService, policyService: PolicyService,
|
||||||
cryptoService: CryptoService, userService: UserService,
|
cryptoService: CryptoService, messagingService: MessagingService,
|
||||||
messagingService: MessagingService, private apiService: ApiService,
|
private apiService: ApiService, stateService: StateService,
|
||||||
private syncService: SyncService, private logService: LogService) {
|
private syncService: SyncService, private logService: LogService) {
|
||||||
super(i18nService, cryptoService, messagingService, userService, passwordGenerationService,
|
super(i18nService, cryptoService, messagingService, passwordGenerationService,
|
||||||
platformUtilsService, policyService);
|
platformUtilsService, policyService, stateService);
|
||||||
}
|
}
|
||||||
|
|
||||||
async ngOnInit() {
|
async ngOnInit() {
|
||||||
@@ -49,9 +49,9 @@ export class UpdateTempPasswordComponent extends BaseChangePasswordComponent {
|
|||||||
|
|
||||||
async setupSubmitActions(): Promise<boolean> {
|
async setupSubmitActions(): Promise<boolean> {
|
||||||
this.enforcedPolicyOptions = await this.policyService.getMasterPasswordPolicyOptions();
|
this.enforcedPolicyOptions = await this.policyService.getMasterPasswordPolicyOptions();
|
||||||
this.email = await this.userService.getEmail();
|
this.email = await this.stateService.getEmail();
|
||||||
this.kdf = await this.userService.getKdf();
|
this.kdf = await this.stateService.getKdfType();
|
||||||
this.kdfIterations = await this.userService.getKdfIterations();
|
this.kdfIterations = await this.stateService.getKdfIterations();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -24,9 +24,9 @@ import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
|||||||
import { LogService } from 'jslib-common/abstractions/log.service';
|
import { LogService } from 'jslib-common/abstractions/log.service';
|
||||||
import { PasswordRepromptService } from 'jslib-common/abstractions/passwordReprompt.service';
|
import { PasswordRepromptService } from 'jslib-common/abstractions/passwordReprompt.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { TokenService } from 'jslib-common/abstractions/token.service';
|
import { TokenService } from 'jslib-common/abstractions/token.service';
|
||||||
import { TotpService } from 'jslib-common/abstractions/totp.service';
|
import { TotpService } from 'jslib-common/abstractions/totp.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
|
|
||||||
import { ErrorResponse } from 'jslib-common/models/response/errorResponse';
|
import { ErrorResponse } from 'jslib-common/models/response/errorResponse';
|
||||||
|
|
||||||
@@ -67,9 +67,9 @@ export class ViewComponent implements OnDestroy, OnInit {
|
|||||||
protected cryptoService: CryptoService, protected platformUtilsService: PlatformUtilsService,
|
protected cryptoService: CryptoService, protected platformUtilsService: PlatformUtilsService,
|
||||||
protected auditService: AuditService, protected win: Window,
|
protected auditService: AuditService, protected win: Window,
|
||||||
protected broadcasterService: BroadcasterService, protected ngZone: NgZone,
|
protected broadcasterService: BroadcasterService, protected ngZone: NgZone,
|
||||||
protected changeDetectorRef: ChangeDetectorRef, protected userService: UserService,
|
protected changeDetectorRef: ChangeDetectorRef, protected eventService: EventService,
|
||||||
protected eventService: EventService, protected apiService: ApiService,
|
protected apiService: ApiService, protected passwordRepromptService: PasswordRepromptService,
|
||||||
protected passwordRepromptService: PasswordRepromptService, private logService: LogService) { }
|
private logService: LogService, protected stateService: StateService) { }
|
||||||
|
|
||||||
ngOnInit() {
|
ngOnInit() {
|
||||||
this.broadcasterService.subscribe(BroadcasterSubscriptionId, (message: any) => {
|
this.broadcasterService.subscribe(BroadcasterSubscriptionId, (message: any) => {
|
||||||
@@ -96,7 +96,7 @@ export class ViewComponent implements OnDestroy, OnInit {
|
|||||||
|
|
||||||
const cipher = await this.cipherService.get(this.cipherId);
|
const cipher = await this.cipherService.get(this.cipherId);
|
||||||
this.cipher = await cipher.decrypt();
|
this.cipher = await cipher.decrypt();
|
||||||
this.canAccessPremium = await this.userService.canAccessPremium();
|
this.canAccessPremium = await this.stateService.getCanAccessPremium();
|
||||||
|
|
||||||
if (this.cipher.type === CipherType.Login && this.cipher.login.totp &&
|
if (this.cipher.type === CipherType.Login && this.cipher.login.totp &&
|
||||||
(cipher.organizationUseTotp || this.canAccessPremium)) {
|
(cipher.organizationUseTotp || this.canAccessPremium)) {
|
||||||
|
|||||||
@@ -7,16 +7,16 @@ import {
|
|||||||
} from '@angular/router';
|
} from '@angular/router';
|
||||||
|
|
||||||
import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
import { MessagingService } from 'jslib-common/abstractions/messaging.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { VaultTimeoutService } from 'jslib-common/abstractions/vaultTimeout.service';
|
import { VaultTimeoutService } from 'jslib-common/abstractions/vaultTimeout.service';
|
||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class AuthGuardService implements CanActivate {
|
export class AuthGuardService implements CanActivate {
|
||||||
constructor(private vaultTimeoutService: VaultTimeoutService, private userService: UserService,
|
constructor(private vaultTimeoutService: VaultTimeoutService, private router: Router,
|
||||||
private router: Router, private messagingService: MessagingService) { }
|
private messagingService: MessagingService, private stateService: StateService) { }
|
||||||
|
|
||||||
async canActivate(route: ActivatedRouteSnapshot, routerState: RouterStateSnapshot) {
|
async canActivate(route: ActivatedRouteSnapshot, routerState: RouterStateSnapshot) {
|
||||||
const isAuthed = await this.userService.isAuthenticated();
|
const isAuthed = this.stateService.getIsAuthenticated();
|
||||||
if (!isAuthed) {
|
if (!isAuthed) {
|
||||||
this.messagingService.send('authBlocked');
|
this.messagingService.send('authBlocked');
|
||||||
return false;
|
return false;
|
||||||
|
|||||||
@@ -4,29 +4,25 @@ import {
|
|||||||
Router,
|
Router,
|
||||||
} from '@angular/router';
|
} from '@angular/router';
|
||||||
|
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { VaultTimeoutService } from 'jslib-common/abstractions/vaultTimeout.service';
|
import { VaultTimeoutService } from 'jslib-common/abstractions/vaultTimeout.service';
|
||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class LockGuardService implements CanActivate {
|
export class LockGuardService implements CanActivate {
|
||||||
|
constructor(private vaultTimeoutService: VaultTimeoutService, private router: Router,
|
||||||
protected homepage = 'vault';
|
private stateService: StateService) { }
|
||||||
constructor(private vaultTimeoutService: VaultTimeoutService, private userService: UserService,
|
|
||||||
private router: Router) { }
|
|
||||||
|
|
||||||
async canActivate() {
|
async canActivate() {
|
||||||
const isAuthed = await this.userService.isAuthenticated();
|
if (!await this.stateService.getIsAuthenticated()) {
|
||||||
if (isAuthed) {
|
this.router.navigate(['login']);
|
||||||
const locked = await this.vaultTimeoutService.isLocked();
|
return false;
|
||||||
if (locked) {
|
|
||||||
return true;
|
|
||||||
} else {
|
|
||||||
this.router.navigate([this.homepage]);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
this.router.navigate(['']);
|
if (!await this.vaultTimeoutService.isLocked()) {
|
||||||
return false;
|
this.router.navigate(['vault']);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,22 +1,21 @@
|
|||||||
import { Injectable } from '@angular/core';
|
import { Injectable } from '@angular/core';
|
||||||
import {
|
import {
|
||||||
ActivatedRouteSnapshot,
|
|
||||||
CanActivate,
|
CanActivate,
|
||||||
Router,
|
Router,
|
||||||
} from '@angular/router';
|
} from '@angular/router';
|
||||||
|
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { VaultTimeoutService } from 'jslib-common/abstractions/vaultTimeout.service';
|
import { VaultTimeoutService } from 'jslib-common/abstractions/vaultTimeout.service';
|
||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class UnauthGuardService implements CanActivate {
|
export class UnauthGuardService implements CanActivate {
|
||||||
|
|
||||||
protected homepage = 'vault';
|
protected homepage = 'vault';
|
||||||
constructor(private vaultTimeoutService: VaultTimeoutService, private userService: UserService,
|
constructor(private vaultTimeoutService: VaultTimeoutService, private router: Router,
|
||||||
private router: Router) { }
|
private stateService: StateService) { }
|
||||||
|
|
||||||
async canActivate() {
|
async canActivate() {
|
||||||
const isAuthed = await this.userService.isAuthenticated();
|
const isAuthed = await this.stateService.getIsAuthenticated();
|
||||||
if (isAuthed) {
|
if (isAuthed) {
|
||||||
const locked = await this.vaultTimeoutService.isLocked();
|
const locked = await this.vaultTimeoutService.isLocked();
|
||||||
if (locked) {
|
if (locked) {
|
||||||
@@ -26,7 +25,5 @@ export class UnauthGuardService implements CanActivate {
|
|||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,21 +1,18 @@
|
|||||||
import { ipcMain, systemPreferences } from 'electron';
|
import { ipcMain, systemPreferences } from 'electron';
|
||||||
|
|
||||||
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
|
||||||
import { ConstantsService } from 'jslib-common/services/constants.service';
|
|
||||||
|
|
||||||
import { BiometricMain } from 'jslib-common/abstractions/biometric.main';
|
import { BiometricMain } from 'jslib-common/abstractions/biometric.main';
|
||||||
import { ElectronConstants } from './electronConstants';
|
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
||||||
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
|
|
||||||
export default class BiometricDarwinMain implements BiometricMain {
|
export default class BiometricDarwinMain implements BiometricMain {
|
||||||
isError: boolean = false;
|
isError: boolean = false;
|
||||||
|
|
||||||
constructor(private storageService: StorageService, private i18nservice: I18nService) {}
|
constructor(private i18nservice: I18nService, private stateService: StateService) {}
|
||||||
|
|
||||||
async init() {
|
async init() {
|
||||||
this.storageService.save(ElectronConstants.enableBiometric, await this.supportsBiometric());
|
await this.stateService.setEnableBiometric(await this.supportsBiometric());
|
||||||
this.storageService.save(ConstantsService.biometricText, 'unlockWithTouchId');
|
await this.stateService.setBiometricText('unlockWithTouchId');
|
||||||
this.storageService.save(ElectronConstants.noAutoPromptBiometricsText, 'noAutoPromptTouchId');
|
await this.stateService.setNoAutoPromptBiometricsText('noAutoPromptTouchId');
|
||||||
|
|
||||||
ipcMain.on('biometric', async (event: any, message: any) => {
|
ipcMain.on('biometric', async (event: any, message: any) => {
|
||||||
event.returnValue = await this.authenticateBiometric();
|
event.returnValue = await this.authenticateBiometric();
|
||||||
|
|||||||
@@ -1,22 +1,20 @@
|
|||||||
import { ipcMain } from 'electron';
|
import { ipcMain } from 'electron';
|
||||||
import forceFocus from 'forcefocus';
|
import forceFocus from 'forcefocus';
|
||||||
|
|
||||||
import { ElectronConstants } from './electronConstants';
|
|
||||||
import { WindowMain } from './window.main';
|
import { WindowMain } from './window.main';
|
||||||
|
|
||||||
import { BiometricMain } from 'jslib-common/abstractions/biometric.main';
|
import { BiometricMain } from 'jslib-common/abstractions/biometric.main';
|
||||||
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
||||||
import { LogService } from 'jslib-common/abstractions/log.service';
|
import { LogService } from 'jslib-common/abstractions/log.service';
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { ConstantsService } from 'jslib-common/services/constants.service';
|
|
||||||
|
|
||||||
export default class BiometricWindowsMain implements BiometricMain {
|
export default class BiometricWindowsMain implements BiometricMain {
|
||||||
isError: boolean = false;
|
isError: boolean = false;
|
||||||
|
|
||||||
private windowsSecurityCredentialsUiModule: any;
|
private windowsSecurityCredentialsUiModule: any;
|
||||||
|
|
||||||
constructor(private storageService: StorageService, private i18nservice: I18nService, private windowMain: WindowMain,
|
constructor(private i18nservice: I18nService, private windowMain: WindowMain,
|
||||||
private logService: LogService) { }
|
private stateService: StateService, private logService: LogService) { }
|
||||||
|
|
||||||
async init() {
|
async init() {
|
||||||
this.windowsSecurityCredentialsUiModule = this.getWindowsSecurityCredentialsUiModule();
|
this.windowsSecurityCredentialsUiModule = this.getWindowsSecurityCredentialsUiModule();
|
||||||
@@ -27,9 +25,9 @@ export default class BiometricWindowsMain implements BiometricMain {
|
|||||||
// store error state so we can let the user know on the settings page
|
// store error state so we can let the user know on the settings page
|
||||||
this.isError = true;
|
this.isError = true;
|
||||||
}
|
}
|
||||||
this.storageService.save(ElectronConstants.enableBiometric, supportsBiometric);
|
this.stateService.setEnableBiometric(supportsBiometric);
|
||||||
this.storageService.save(ConstantsService.biometricText, 'unlockWithWindowsHello');
|
this.stateService.setBiometricText('unlockWithWindowsHello');
|
||||||
this.storageService.save(ElectronConstants.noAutoPromptBiometricsText, 'noAutoPromptWindowsHello');
|
this.stateService.setNoAutoPromptBiometricsText('noAutoPromptWindowsHello');
|
||||||
|
|
||||||
ipcMain.on('biometric', async (event: any, message: any) => {
|
ipcMain.on('biometric', async (event: any, message: any) => {
|
||||||
event.returnValue = await this.authenticateBiometric();
|
event.returnValue = await this.authenticateBiometric();
|
||||||
|
|||||||
@@ -1,14 +0,0 @@
|
|||||||
export class ElectronConstants {
|
|
||||||
static readonly enableMinimizeToTrayKey: string = 'enableMinimizeToTray';
|
|
||||||
static readonly enableCloseToTrayKey: string = 'enableCloseToTray';
|
|
||||||
static readonly enableTrayKey: string = 'enableTray';
|
|
||||||
static readonly enableStartToTrayKey: string = 'enableStartToTrayKey';
|
|
||||||
static readonly enableAlwaysOnTopKey: string = 'enableAlwaysOnTopKey';
|
|
||||||
static readonly minimizeOnCopyToClipboardKey: string = 'minimizeOnCopyToClipboardKey';
|
|
||||||
static readonly enableBiometric: string = 'enabledBiometric';
|
|
||||||
static readonly enableBrowserIntegration: string = 'enableBrowserIntegration';
|
|
||||||
static readonly enableBrowserIntegrationFingerprint: string = 'enableBrowserIntegrationFingerprint';
|
|
||||||
static readonly alwaysShowDock: string = 'alwaysShowDock';
|
|
||||||
static readonly openAtLogin: string = 'openAtLogin';
|
|
||||||
static readonly noAutoPromptBiometricsText: string = 'noAutoPromptBiometricsText';
|
|
||||||
}
|
|
||||||
@@ -2,7 +2,6 @@ import {
|
|||||||
app,
|
app,
|
||||||
BrowserWindow,
|
BrowserWindow,
|
||||||
Menu,
|
Menu,
|
||||||
MenuItem,
|
|
||||||
MenuItemConstructorOptions,
|
MenuItemConstructorOptions,
|
||||||
nativeImage,
|
nativeImage,
|
||||||
Tray,
|
Tray,
|
||||||
@@ -10,9 +9,8 @@ import {
|
|||||||
import * as path from 'path';
|
import * as path from 'path';
|
||||||
|
|
||||||
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
|
|
||||||
import { ElectronConstants } from './electronConstants';
|
|
||||||
import { WindowMain } from './window.main';
|
import { WindowMain } from './window.main';
|
||||||
|
|
||||||
export class TrayMain {
|
export class TrayMain {
|
||||||
@@ -24,7 +22,7 @@ export class TrayMain {
|
|||||||
private pressedIcon: Electron.NativeImage;
|
private pressedIcon: Electron.NativeImage;
|
||||||
|
|
||||||
constructor(private windowMain: WindowMain, private i18nService: I18nService,
|
constructor(private windowMain: WindowMain, private i18nService: I18nService,
|
||||||
private storageService: StorageService) {
|
private stateService: StateService) {
|
||||||
if (process.platform === 'win32') {
|
if (process.platform === 'win32') {
|
||||||
this.icon = path.join(__dirname, '/images/icon.ico');
|
this.icon = path.join(__dirname, '/images/icon.ico');
|
||||||
} else if (process.platform === 'darwin') {
|
} else if (process.platform === 'darwin') {
|
||||||
@@ -55,21 +53,21 @@ export class TrayMain {
|
|||||||
}
|
}
|
||||||
|
|
||||||
this.contextMenu = Menu.buildFromTemplate(menuItemOptions);
|
this.contextMenu = Menu.buildFromTemplate(menuItemOptions);
|
||||||
if (await this.storageService.get<boolean>(ElectronConstants.enableTrayKey)) {
|
if (await this.stateService.getEnableTray()) {
|
||||||
this.showTray();
|
this.showTray();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
setupWindowListeners(win: BrowserWindow) {
|
setupWindowListeners(win: BrowserWindow) {
|
||||||
win.on('minimize', async (e: Event) => {
|
win.on('minimize', async (e: Event) => {
|
||||||
if (await this.storageService.get<boolean>(ElectronConstants.enableMinimizeToTrayKey)) {
|
if (await this.stateService.getEnableMinimizeToTray()) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
this.hideToTray();
|
this.hideToTray();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
win.on('close', async (e: Event) => {
|
win.on('close', async (e: Event) => {
|
||||||
if (await this.storageService.get<boolean>(ElectronConstants.enableCloseToTrayKey)) {
|
if (await this.stateService.getEnableCloseToTray()) {
|
||||||
if (!this.windowMain.isQuitting) {
|
if (!this.windowMain.isQuitting) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
this.hideToTray();
|
this.hideToTray();
|
||||||
@@ -78,7 +76,7 @@ export class TrayMain {
|
|||||||
});
|
});
|
||||||
|
|
||||||
win.on('show', async (e: Event) => {
|
win.on('show', async (e: Event) => {
|
||||||
const enableTray = await this.storageService.get<boolean>(ElectronConstants.enableTrayKey);
|
const enableTray = await this.stateService.getEnableTray();
|
||||||
if (!enableTray) {
|
if (!enableTray) {
|
||||||
setTimeout(() => this.removeTray(false), 100);
|
setTimeout(() => this.removeTray(false), 100);
|
||||||
}
|
}
|
||||||
@@ -103,7 +101,7 @@ export class TrayMain {
|
|||||||
if (this.windowMain.win != null) {
|
if (this.windowMain.win != null) {
|
||||||
this.windowMain.win.hide();
|
this.windowMain.win.hide();
|
||||||
}
|
}
|
||||||
if (this.isDarwin() && !await this.storageService.get<boolean>(ElectronConstants.alwaysShowDock)) {
|
if (this.isDarwin() && !await this.stateService.getAlwaysShowDock()) {
|
||||||
this.hideDock();
|
this.hideDock();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -167,7 +165,7 @@ export class TrayMain {
|
|||||||
}
|
}
|
||||||
if (this.windowMain.win.isVisible()) {
|
if (this.windowMain.win.isVisible()) {
|
||||||
this.windowMain.win.hide();
|
this.windowMain.win.hide();
|
||||||
if (this.isDarwin() && !await this.storageService.get<boolean>(ElectronConstants.alwaysShowDock)) {
|
if (this.isDarwin() && !await this.stateService.getAlwaysShowDock()) {
|
||||||
this.hideDock();
|
this.hideDock();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@@ -7,9 +7,8 @@ import * as path from 'path';
|
|||||||
import * as url from 'url';
|
import * as url from 'url';
|
||||||
|
|
||||||
import { LogService } from 'jslib-common/abstractions/log.service';
|
import { LogService } from 'jslib-common/abstractions/log.service';
|
||||||
import { StorageService } from 'jslib-common/abstractions/storage.service';
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
|
|
||||||
import { ElectronConstants } from './electronConstants';
|
|
||||||
import {
|
import {
|
||||||
cleanUserAgent,
|
cleanUserAgent,
|
||||||
isDev,
|
isDev,
|
||||||
@@ -17,11 +16,8 @@ import {
|
|||||||
isSnapStore,
|
isSnapStore,
|
||||||
} from './utils';
|
} from './utils';
|
||||||
|
|
||||||
|
const mainWindowSizeKey = 'mainWindowSize';
|
||||||
const WindowEventHandlingDelay = 100;
|
const WindowEventHandlingDelay = 100;
|
||||||
const Keys = {
|
|
||||||
mainWindowSize: 'mainWindowSize',
|
|
||||||
};
|
|
||||||
|
|
||||||
export class WindowMain {
|
export class WindowMain {
|
||||||
win: BrowserWindow;
|
win: BrowserWindow;
|
||||||
isQuitting: boolean = false;
|
isQuitting: boolean = false;
|
||||||
@@ -30,7 +26,7 @@ export class WindowMain {
|
|||||||
private windowStates: { [key: string]: any; } = {};
|
private windowStates: { [key: string]: any; } = {};
|
||||||
private enableAlwaysOnTop: boolean = false;
|
private enableAlwaysOnTop: boolean = false;
|
||||||
|
|
||||||
constructor(private storageService: StorageService, private logService: LogService,
|
constructor(private stateService: StateService, private logService: LogService,
|
||||||
private hideTitleBar = false, private defaultWidth = 950, private defaultHeight = 600,
|
private hideTitleBar = false, private defaultWidth = 950, private defaultHeight = 600,
|
||||||
private argvCallback: (argv: string[]) => void = null,
|
private argvCallback: (argv: string[]) => void = null,
|
||||||
private createWindowCallback: (win: BrowserWindow) => void) { }
|
private createWindowCallback: (win: BrowserWindow) => void) { }
|
||||||
@@ -81,7 +77,7 @@ export class WindowMain {
|
|||||||
// Quit when all windows are closed.
|
// Quit when all windows are closed.
|
||||||
app.on('window-all-closed', () => {
|
app.on('window-all-closed', () => {
|
||||||
// On OS X it is common for applications and their menu bar
|
// On OS X it is common for applications and their menu bar
|
||||||
// to stay active until the user quits explicitly with Cmd + Q
|
// to stay KKKactive until the user quits explicitly with Cmd + Q
|
||||||
if (process.platform !== 'darwin' || this.isQuitting || isMacAppStore()) {
|
if (process.platform !== 'darwin' || this.isQuitting || isMacAppStore()) {
|
||||||
app.quit();
|
app.quit();
|
||||||
}
|
}
|
||||||
@@ -107,100 +103,104 @@ export class WindowMain {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async createWindow(): Promise<void> {
|
async createWindow(): Promise<void> {
|
||||||
this.windowStates[Keys.mainWindowSize] = await this.getWindowState(Keys.mainWindowSize, this.defaultWidth,
|
try {
|
||||||
this.defaultHeight);
|
this.windowStates[mainWindowSizeKey] = await this.getWindowState(mainWindowSizeKey, this.defaultWidth,
|
||||||
this.enableAlwaysOnTop = await this.storageService.get<boolean>(ElectronConstants.enableAlwaysOnTopKey);
|
this.defaultHeight);
|
||||||
|
this.enableAlwaysOnTop = await this.stateService.getEnableAlwaysOnTop();
|
||||||
|
|
||||||
// Create the browser window.
|
// Create the browser window.
|
||||||
this.win = new BrowserWindow({
|
this.win = new BrowserWindow({
|
||||||
width: this.windowStates[Keys.mainWindowSize].width,
|
width: this.windowStates[mainWindowSizeKey].width,
|
||||||
height: this.windowStates[Keys.mainWindowSize].height,
|
height: this.windowStates[mainWindowSizeKey].height,
|
||||||
minWidth: 680,
|
minWidth: 680,
|
||||||
minHeight: 500,
|
minHeight: 500,
|
||||||
x: this.windowStates[Keys.mainWindowSize].x,
|
x: this.windowStates[mainWindowSizeKey].x,
|
||||||
y: this.windowStates[Keys.mainWindowSize].y,
|
y: this.windowStates[mainWindowSizeKey].y,
|
||||||
title: app.name,
|
title: app.name,
|
||||||
icon: process.platform === 'linux' ? path.join(__dirname, '/images/icon.png') : undefined,
|
icon: process.platform === 'linux' ? path.join(__dirname, '/images/icon.png') : undefined,
|
||||||
titleBarStyle: this.hideTitleBar && process.platform === 'darwin' ? 'hiddenInset' : undefined,
|
titleBarStyle: this.hideTitleBar && process.platform === 'darwin' ? 'hiddenInset' : undefined,
|
||||||
show: false,
|
show: false,
|
||||||
backgroundColor: '#fff',
|
backgroundColor: '#fff',
|
||||||
alwaysOnTop: this.enableAlwaysOnTop,
|
alwaysOnTop: this.enableAlwaysOnTop,
|
||||||
webPreferences: {
|
webPreferences: {
|
||||||
nodeIntegration: true,
|
nodeIntegration: true,
|
||||||
backgroundThrottling: false,
|
backgroundThrottling: false,
|
||||||
contextIsolation: false,
|
contextIsolation: false,
|
||||||
},
|
},
|
||||||
});
|
|
||||||
|
|
||||||
if (this.windowStates[Keys.mainWindowSize].isMaximized) {
|
|
||||||
this.win.maximize();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Show it later since it might need to be maximized.
|
|
||||||
this.win.show();
|
|
||||||
|
|
||||||
// and load the index.html of the app.
|
|
||||||
this.win.loadURL(url.format(
|
|
||||||
{
|
|
||||||
protocol: 'file:',
|
|
||||||
pathname: path.join(__dirname, '/index.html'),
|
|
||||||
slashes: true,
|
|
||||||
}),
|
|
||||||
{
|
|
||||||
userAgent: cleanUserAgent(this.win.webContents.userAgent),
|
|
||||||
}
|
|
||||||
);
|
|
||||||
|
|
||||||
// Open the DevTools.
|
|
||||||
if (isDev()) {
|
|
||||||
this.win.webContents.openDevTools();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Emitted when the window is closed.
|
|
||||||
this.win.on('closed', async () => {
|
|
||||||
await this.updateWindowState(Keys.mainWindowSize, this.win);
|
|
||||||
|
|
||||||
// Dereference the window object, usually you would store window
|
|
||||||
// in an array if your app supports multi windows, this is the time
|
|
||||||
// when you should delete the corresponding element.
|
|
||||||
this.win = null;
|
|
||||||
});
|
|
||||||
|
|
||||||
this.win.on('close', async () => {
|
|
||||||
await this.updateWindowState(Keys.mainWindowSize, this.win);
|
|
||||||
});
|
|
||||||
|
|
||||||
this.win.on('maximize', async () => {
|
|
||||||
await this.updateWindowState(Keys.mainWindowSize, this.win);
|
|
||||||
});
|
|
||||||
|
|
||||||
this.win.on('unmaximize', async () => {
|
|
||||||
await this.updateWindowState(Keys.mainWindowSize, this.win);
|
|
||||||
});
|
|
||||||
|
|
||||||
this.win.on('resize', () => {
|
|
||||||
this.windowStateChangeHandler(Keys.mainWindowSize, this.win);
|
|
||||||
});
|
|
||||||
|
|
||||||
this.win.on('move', () => {
|
|
||||||
this.windowStateChangeHandler(Keys.mainWindowSize, this.win);
|
|
||||||
});
|
|
||||||
this.win.on('focus', () => {
|
|
||||||
this.win.webContents.send('messagingService', {
|
|
||||||
command: 'windowIsFocused',
|
|
||||||
windowIsFocused: true,
|
|
||||||
});
|
});
|
||||||
});
|
|
||||||
|
|
||||||
if (this.createWindowCallback) {
|
if (this.windowStates[mainWindowSizeKey].isMaximized) {
|
||||||
this.createWindowCallback(this.win);
|
this.win.maximize();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Show it later since it might need to be maximized.
|
||||||
|
this.win.show();
|
||||||
|
|
||||||
|
// and load the index.html of the app.
|
||||||
|
this.win.loadURL(url.format(
|
||||||
|
{
|
||||||
|
protocol: 'file:',
|
||||||
|
pathname: path.join(__dirname, '/index.html'),
|
||||||
|
slashes: true,
|
||||||
|
}),
|
||||||
|
{
|
||||||
|
userAgent: cleanUserAgent(this.win.webContents.userAgent),
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
// Open the DevTools.
|
||||||
|
if (isDev()) {
|
||||||
|
this.win.webContents.openDevTools();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Emitted when the window is closed.
|
||||||
|
this.win.on('closed', async () => {
|
||||||
|
await this.updateWindowState(mainWindowSizeKey, this.win);
|
||||||
|
|
||||||
|
// Dereference the window object, usually you would store window
|
||||||
|
// in an array if your app supports multi windows, this is the time
|
||||||
|
// when you should delete the corresponding element.
|
||||||
|
this.win = null;
|
||||||
|
});
|
||||||
|
|
||||||
|
this.win.on('close', async () => {
|
||||||
|
await this.updateWindowState(mainWindowSizeKey, this.win);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.win.on('maximize', async () => {
|
||||||
|
await this.updateWindowState(mainWindowSizeKey, this.win);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.win.on('unmaximize', async () => {
|
||||||
|
await this.updateWindowState(mainWindowSizeKey, this.win);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.win.on('resize', () => {
|
||||||
|
this.windowStateChangeHandler(mainWindowSizeKey, this.win);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.win.on('move', () => {
|
||||||
|
this.windowStateChangeHandler(mainWindowSizeKey, this.win);
|
||||||
|
});
|
||||||
|
this.win.on('focus', () => {
|
||||||
|
this.win.webContents.send('messagingService', {
|
||||||
|
command: 'windowIsFocused',
|
||||||
|
windowIsFocused: true,
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
if (this.createWindowCallback) {
|
||||||
|
this.createWindowCallback(this.win);
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
this.logService.error(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async toggleAlwaysOnTop() {
|
async toggleAlwaysOnTop() {
|
||||||
this.enableAlwaysOnTop = !this.win.isAlwaysOnTop();
|
this.enableAlwaysOnTop = !this.win.isAlwaysOnTop();
|
||||||
this.win.setAlwaysOnTop(this.enableAlwaysOnTop);
|
this.win.setAlwaysOnTop(this.enableAlwaysOnTop);
|
||||||
await this.storageService.save(ElectronConstants.enableAlwaysOnTopKey, this.enableAlwaysOnTop);
|
await this.stateService.setEnableAlwaysOnTop(this.enableAlwaysOnTop);
|
||||||
}
|
}
|
||||||
|
|
||||||
private windowStateChangeHandler(configKey: string, win: BrowserWindow) {
|
private windowStateChangeHandler(configKey: string, win: BrowserWindow) {
|
||||||
@@ -219,7 +219,7 @@ export class WindowMain {
|
|||||||
const bounds = win.getBounds();
|
const bounds = win.getBounds();
|
||||||
|
|
||||||
if (this.windowStates[configKey] == null) {
|
if (this.windowStates[configKey] == null) {
|
||||||
this.windowStates[configKey] = await this.storageService.get<any>(configKey);
|
this.windowStates[configKey] = (await this.stateService.getWindow()).get(configKey);
|
||||||
if (this.windowStates[configKey] == null) {
|
if (this.windowStates[configKey] == null) {
|
||||||
this.windowStates[configKey] = {};
|
this.windowStates[configKey] = {};
|
||||||
}
|
}
|
||||||
@@ -235,14 +235,19 @@ export class WindowMain {
|
|||||||
this.windowStates[configKey].height = bounds.height;
|
this.windowStates[configKey].height = bounds.height;
|
||||||
}
|
}
|
||||||
|
|
||||||
await this.storageService.save(configKey, this.windowStates[configKey]);
|
const cachedWindow = await this.stateService.getWindow() ?? new Map<string, any>();
|
||||||
|
cachedWindow.set(configKey, this.windowStates[configKey]);
|
||||||
|
await this.stateService.setWindow(cachedWindow);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
this.logService.error(e);
|
this.logService.error(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private async getWindowState(configKey: string, defaultWidth: number, defaultHeight: number) {
|
private async getWindowState(configKey: string, defaultWidth: number, defaultHeight: number) {
|
||||||
let state = await this.storageService.get<any>(configKey);
|
const windowState = await this.stateService.getWindow() ?? new Map<string, any>();
|
||||||
|
let state = windowState.has(configKey) ?
|
||||||
|
windowState.get(configKey) :
|
||||||
|
null;
|
||||||
|
|
||||||
const isValid = state != null && (this.stateHasBounds(state) || state.isMaximized);
|
const isValid = state != null && (this.stateHasBounds(state) || state.isMaximized);
|
||||||
let displayBounds: Electron.Rectangle = null;
|
let displayBounds: Electron.Rectangle = null;
|
||||||
|
|||||||
@@ -1,15 +1,15 @@
|
|||||||
import * as chalk from 'chalk';
|
import * as chalk from 'chalk';
|
||||||
|
|
||||||
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
|
|
||||||
import { Response } from './models/response';
|
import { Response } from './models/response';
|
||||||
import { ListResponse } from './models/response/listResponse';
|
import { ListResponse } from './models/response/listResponse';
|
||||||
import { MessageResponse } from './models/response/messageResponse';
|
import { MessageResponse } from './models/response/messageResponse';
|
||||||
import { StringResponse } from './models/response/stringResponse';
|
import { StringResponse } from './models/response/stringResponse';
|
||||||
|
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
|
|
||||||
export abstract class BaseProgram {
|
export abstract class BaseProgram {
|
||||||
constructor(
|
constructor(
|
||||||
private userService: UserService,
|
private stateService: StateService,
|
||||||
private writeLn: (s: string, finalLine: boolean, error: boolean) => void) { }
|
private writeLn: (s: string, finalLine: boolean, error: boolean) => void) { }
|
||||||
|
|
||||||
protected processResponse(response: Response, exitImmediately = false, dataProcessor: () => string = null) {
|
protected processResponse(response: Response, exitImmediately = false, dataProcessor: () => string = null) {
|
||||||
@@ -92,15 +92,15 @@ export abstract class BaseProgram {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected async exitIfAuthed() {
|
protected async exitIfAuthed() {
|
||||||
const authed = await this.userService.isAuthenticated();
|
const authed = await this.stateService.getIsAuthenticated();
|
||||||
if (authed) {
|
if (authed) {
|
||||||
const email = await this.userService.getEmail();
|
const email = await this.stateService.getEmail();
|
||||||
this.processResponse(Response.error('You are already logged in as ' + email + '.'), true);
|
this.processResponse(Response.error('You are already logged in as ' + email + '.'), true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected async exitIfNotAuthed() {
|
protected async exitIfNotAuthed() {
|
||||||
const authed = await this.userService.isAuthenticated();
|
const authed = await this.stateService.getIsAuthenticated();
|
||||||
if (!authed) {
|
if (!authed) {
|
||||||
this.processResponse(Response.error('You are not logged in.'), true);
|
this.processResponse(Response.error('You are not logged in.'), true);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -17,8 +17,8 @@ import { I18nService } from 'jslib-common/abstractions/i18n.service';
|
|||||||
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service';
|
||||||
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service';
|
||||||
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
import { PolicyService } from 'jslib-common/abstractions/policy.service';
|
||||||
|
import { StateService } from 'jslib-common/abstractions/state.service';
|
||||||
import { SyncService } from 'jslib-common/abstractions/sync.service';
|
import { SyncService } from 'jslib-common/abstractions/sync.service';
|
||||||
import { UserService } from 'jslib-common/abstractions/user.service';
|
|
||||||
|
|
||||||
import { Response } from '../models/response';
|
import { Response } from '../models/response';
|
||||||
|
|
||||||
@@ -47,7 +47,7 @@ export class LoginCommand {
|
|||||||
protected i18nService: I18nService, protected environmentService: EnvironmentService,
|
protected i18nService: I18nService, protected environmentService: EnvironmentService,
|
||||||
protected passwordGenerationService: PasswordGenerationService,
|
protected passwordGenerationService: PasswordGenerationService,
|
||||||
protected cryptoFunctionService: CryptoFunctionService, protected platformUtilsService: PlatformUtilsService,
|
protected cryptoFunctionService: CryptoFunctionService, protected platformUtilsService: PlatformUtilsService,
|
||||||
protected userService: UserService, protected cryptoService: CryptoService,
|
protected stateService: StateService, protected cryptoService: CryptoService,
|
||||||
protected policyService: PolicyService, clientId: string, private syncService: SyncService) {
|
protected policyService: PolicyService, clientId: string, private syncService: SyncService) {
|
||||||
this.clientId = clientId;
|
this.clientId = clientId;
|
||||||
}
|
}
|
||||||
@@ -285,7 +285,7 @@ export class LoginCommand {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (this.email == null || this.email === 'undefined') {
|
if (this.email == null || this.email === 'undefined') {
|
||||||
this.email = await this.userService.getEmail();
|
this.email = await this.stateService.getEmail();
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get New Master Password
|
// Get New Master Password
|
||||||
@@ -335,8 +335,8 @@ export class LoginCommand {
|
|||||||
|
|
||||||
// Retrieve details for key generation
|
// Retrieve details for key generation
|
||||||
const enforcedPolicyOptions = await this.policyService.getMasterPasswordPolicyOptions();
|
const enforcedPolicyOptions = await this.policyService.getMasterPasswordPolicyOptions();
|
||||||
const kdf = await this.userService.getKdf();
|
const kdf = await this.stateService.getKdfType();
|
||||||
const kdfIterations = await this.userService.getKdfIterations();
|
const kdfIterations = await this.stateService.getKdfIterations();
|
||||||
|
|
||||||
if (enforcedPolicyOptions != null &&
|
if (enforcedPolicyOptions != null &&
|
||||||
!this.policyService.evaluateMasterPassword(
|
!this.policyService.evaluateMasterPassword(
|
||||||
|
|||||||
Reference in New Issue
Block a user