diff --git a/src/vs/platform/credentials/common/credentialsMainService.ts b/src/vs/platform/credentials/common/credentialsMainService.ts index a2cc48570c..7764a1ee9e 100644 --- a/src/vs/platform/credentials/common/credentialsMainService.ts +++ b/src/vs/platform/credentials/common/credentialsMainService.ts @@ -150,19 +150,28 @@ export abstract class BaseCredentialsMainService extends Disposable implements I return false; } const didDelete = await keytar.deletePassword(service, account); - let { content, hasNextChunk }: ChunkedPassword = JSON.parse(password); - if (content && hasNextChunk) { - // need to delete additional chunks - let index = 1; - while (hasNextChunk) { - const accountWithIndex = `${account}-${index}`; - const nextChunk = await keytar.getPassword(service, accountWithIndex); - await keytar.deletePassword(service, accountWithIndex); + try { + let { content, hasNextChunk }: ChunkedPassword = JSON.parse(password); + if (content && hasNextChunk) { + // need to delete additional chunks + let index = 1; + while (hasNextChunk) { + const accountWithIndex = `${account}-${index}`; + const nextChunk = await keytar.getPassword(service, accountWithIndex); + await keytar.deletePassword(service, accountWithIndex); - const result: ChunkedPassword = JSON.parse(nextChunk!); - hasNextChunk = result.hasNextChunk; - index++; + const result: ChunkedPassword = JSON.parse(nextChunk!); + hasNextChunk = result.hasNextChunk; + index++; + } } + } catch { + // When the password is saved the entire JSON payload is encrypted then stored, thus the result from getPassword might not be valid JSON + // https://github.com/microsoft/vscode/blob/c22cb87311b5eb1a3bf5600d18733f7485355dc0/src/vs/workbench/api/browser/mainThreadSecretState.ts#L83 + // However in the chunked case we JSONify each chunk after encryption so for the chunked case we do expect valid JSON here + // https://github.com/microsoft/vscode/blob/708cb0c507d656b760f9d08115b8ebaf8964fd73/src/vs/platform/credentials/common/credentialsMainService.ts#L128 + // Empty catch here just as in getPassword because we expect to handle both JSON cases and non JSON cases here it's not an error case to fail to parse + // https://github.com/microsoft/vscode/blob/708cb0c507d656b760f9d08115b8ebaf8964fd73/src/vs/platform/credentials/common/credentialsMainService.ts#L76 } if (didDelete) {