-
Notifications
You must be signed in to change notification settings - Fork 29.8k
/
encryptionMainService.ts
109 lines (95 loc) · 4.13 KB
/
encryptionMainService.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
/*---------------------------------------------------------------------------------------------
* Copyright (c) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License. See License.txt in the project root for license information.
*--------------------------------------------------------------------------------------------*/
import { safeStorage as safeStorageElectron, app } from 'electron';
import { isMacintosh, isWindows } from '../../../base/common/platform.js';
import { KnownStorageProvider, IEncryptionMainService, PasswordStoreCLIOption } from '../common/encryptionService.js';
import { ILogService } from '../../log/common/log.js';
// These APIs are currently only supported in our custom build of electron so
// we need to guard against them not being available.
interface ISafeStorageAdditionalAPIs {
setUsePlainTextEncryption(usePlainText: boolean): void;
getSelectedStorageBackend(): string;
}
const safeStorage: typeof import('electron').safeStorage & Partial<ISafeStorageAdditionalAPIs> = safeStorageElectron;
export class EncryptionMainService implements IEncryptionMainService {
_serviceBrand: undefined;
constructor(
@ILogService private readonly logService: ILogService
) {
// if this commandLine switch is set, the user has opted in to using basic text encryption
if (app.commandLine.getSwitchValue('password-store') === PasswordStoreCLIOption.basic) {
this.logService.trace('[EncryptionMainService] setting usePlainTextEncryption to true...');
safeStorage.setUsePlainTextEncryption?.(true);
this.logService.trace('[EncryptionMainService] set usePlainTextEncryption to true');
}
}
async encrypt(value: string): Promise<string> {
this.logService.trace('[EncryptionMainService] Encrypting value...');
try {
const result = JSON.stringify(safeStorage.encryptString(value));
this.logService.trace('[EncryptionMainService] Encrypted value.');
return result;
} catch (e) {
this.logService.error(e);
throw e;
}
}
async decrypt(value: string): Promise<string> {
let parsedValue: { data: string };
try {
parsedValue = JSON.parse(value);
if (!parsedValue.data) {
throw new Error(`[EncryptionMainService] Invalid encrypted value: ${value}`);
}
const bufferToDecrypt = Buffer.from(parsedValue.data);
this.logService.trace('[EncryptionMainService] Decrypting value...');
const result = safeStorage.decryptString(bufferToDecrypt);
this.logService.trace('[EncryptionMainService] Decrypted value.');
return result;
} catch (e) {
this.logService.error(e);
throw e;
}
}
isEncryptionAvailable(): Promise<boolean> {
this.logService.trace('[EncryptionMainService] Checking if encryption is available...');
const result = safeStorage.isEncryptionAvailable();
this.logService.trace('[EncryptionMainService] Encryption is available: ', result);
return Promise.resolve(result);
}
getKeyStorageProvider(): Promise<KnownStorageProvider> {
if (isWindows) {
return Promise.resolve(KnownStorageProvider.dplib);
}
if (isMacintosh) {
return Promise.resolve(KnownStorageProvider.keychainAccess);
}
if (safeStorage.getSelectedStorageBackend) {
try {
this.logService.trace('[EncryptionMainService] Getting selected storage backend...');
const result = safeStorage.getSelectedStorageBackend() as KnownStorageProvider;
this.logService.trace('[EncryptionMainService] Selected storage backend: ', result);
return Promise.resolve(result);
} catch (e) {
this.logService.error(e);
}
}
return Promise.resolve(KnownStorageProvider.unknown);
}
async setUsePlainTextEncryption(): Promise<void> {
if (isWindows) {
throw new Error('Setting plain text encryption is not supported on Windows.');
}
if (isMacintosh) {
throw new Error('Setting plain text encryption is not supported on macOS.');
}
if (!safeStorage.setUsePlainTextEncryption) {
throw new Error('Setting plain text encryption is not supported.');
}
this.logService.trace('[EncryptionMainService] Setting usePlainTextEncryption to true...');
safeStorage.setUsePlainTextEncryption(true);
this.logService.trace('[EncryptionMainService] Set usePlainTextEncryption to true');
}
}