diff --git a/src/vs/platform/backup/electron-main/backupMainService.ts b/src/vs/platform/backup/electron-main/backupMainService.ts index be03ef9f72490cc456a1016ada9a6dafdc2ea282..398ccc5771f2832f65e18858a3d0df96f67ae13b 100644 --- a/src/vs/platform/backup/electron-main/backupMainService.ts +++ b/src/vs/platform/backup/electron-main/backupMainService.ts @@ -52,7 +52,7 @@ export class BackupMainService implements IBackupMainService { public registerWindowForBackups(windowId: number, isEmptyWorkspace: boolean, backupFolder?: string, workspacePath?: string): void { // Generate a new folder if this is a new empty workspace - if (!backupFolder) { + if (isEmptyWorkspace && !backupFolder) { backupFolder = Date.now().toString(); } @@ -60,7 +60,7 @@ export class BackupMainService implements IBackupMainService { this.pushBackupPathsSync(isEmptyWorkspace ? backupFolder : this.sanitizePath(workspacePath), isEmptyWorkspace); } - protected pushBackupPathsSync(workspaceIdentifier: string, isEmptyWorkspace?: boolean): void { + protected pushBackupPathsSync(workspaceIdentifier: string, isEmptyWorkspace: boolean): void { if (!isEmptyWorkspace) { workspaceIdentifier = this.sanitizePath(workspaceIdentifier); } @@ -131,20 +131,31 @@ export class BackupMainService implements IBackupMainService { } private validateBackupWorkspaces(backups: IBackupWorkspacesFormat): void { + const staleBackupWorkspaces: { workspaceIdentifier: string; backupPath: string; isEmptyWorkspace: boolean }[] = []; + backups.folderWorkspaces.forEach(workspacePath => { const backupPath = path.join(this.backupHome, this.getWorkspaceHash(workspacePath)); + console.log('this.hasBackupsSync(backupPath) for ' + workspacePath + ' : ' + this.hasBackupsSync(backupPath)); if (!this.hasBackupsSync(backupPath)) { - extfs.delSync(backupPath); - const backupWorkspace = Uri.file(this.sanitizePath(workspacePath)); - this.removeWorkspaceBackupPathSync(backupWorkspace); + const backupWorkspace = this.sanitizePath(workspacePath); + staleBackupWorkspaces.push({ workspaceIdentifier: backupWorkspace, backupPath, isEmptyWorkspace: false }); } }); backups.emptyWorkspaces.forEach(backupFolder => { const backupPath = path.join(this.backupHome, backupFolder); if (!this.hasBackupsSync(backupPath)) { - extfs.delSync(backupPath); - this.removeEmptyWorkspaceBackupFolder(backupFolder); + staleBackupWorkspaces.push({ workspaceIdentifier: backupFolder, backupPath, isEmptyWorkspace: true }); + } + }); + + staleBackupWorkspaces.forEach(staleBackupWorkspace => { + const {backupPath, workspaceIdentifier, isEmptyWorkspace} = staleBackupWorkspace; + extfs.delSync(backupPath); + if (isEmptyWorkspace) { + this.removeEmptyWorkspaceBackupFolder(workspaceIdentifier); + } else { + this.removeWorkspaceBackupPathSync(Uri.file(workspaceIdentifier)); } }); } @@ -184,7 +195,7 @@ export class BackupMainService implements IBackupMainService { return platform.isLinux ? p : p.toLowerCase(); } - private getWorkspaceHash(workspacePath: string): string { + protected getWorkspaceHash(workspacePath: string): string { return crypto.createHash('md5').update(this.sanitizePath(workspacePath)).digest('hex'); } } diff --git a/src/vs/platform/backup/test/electron-main/backupMainService.test.ts b/src/vs/platform/backup/test/electron-main/backupMainService.test.ts index 1fba683642c682b604bda888576fdef58578294a..e1479ba88e6803af5eb34b5ce4bc3dcc812dcaa8 100644 --- a/src/vs/platform/backup/test/electron-main/backupMainService.test.ts +++ b/src/vs/platform/backup/test/electron-main/backupMainService.test.ts @@ -37,7 +37,7 @@ class TestBackupMainService extends BackupMainService { } public toBackupPath(workspacePath: string): string { - return super.toBackupPath(workspacePath); + return path.join(this.backupHome, super.getWorkspaceHash(workspacePath)); } } @@ -100,12 +100,14 @@ suite('BackupMainService', () => { }); test('pushWorkspaceBackupPathsSync should persist paths to workspaces.json', () => { - service.pushWorkspaceBackupPathsSync([fooFile, barFile]); + service.registerWindowForBackups(1, false, null, fooFile.fsPath); + service.registerWindowForBackups(2, false, null, barFile.fsPath); assert.deepEqual(service.workspaceBackupPaths, [fooFile.fsPath, barFile.fsPath]); }); test('removeWorkspaceBackupPath should remove workspaces from workspaces.json', done => { - service.pushWorkspaceBackupPathsSync([fooFile, barFile]); + service.registerWindowForBackups(1, false, null, fooFile.fsPath); + service.registerWindowForBackups(2, false, null, barFile.fsPath); service.removeWorkspaceBackupPathSync(fooFile); pfs.readFile(backupWorkspacesPath, 'utf-8').then(buffer => { const json = JSON.parse(buffer); @@ -134,16 +136,20 @@ suite('BackupMainService', () => { test('service validates backup workspaces on startup and cleans up', done => { // 1) backup workspace path does not exist - service.pushWorkspaceBackupPathsSync([fooFile, barFile]); + console.log('fooFile :' + fooFile.fsPath); + console.log('barFile :' + barFile.fsPath); + service.registerWindowForBackups(1, false, null, fooFile.fsPath); + service.registerWindowForBackups(2, false, null, barFile.fsPath); service.loadSync(); - assert.equal(service.workspaceBackupPaths.length, 0); + assert.deepEqual(service.workspaceBackupPaths, []); // 2) backup workspace path exists with empty contents within fs.mkdirSync(service.toBackupPath(fooFile.fsPath)); fs.mkdirSync(service.toBackupPath(barFile.fsPath)); - service.pushWorkspaceBackupPathsSync([fooFile, barFile]); + service.registerWindowForBackups(1, false, null, fooFile.fsPath); + service.registerWindowForBackups(2, false, null, barFile.fsPath); service.loadSync(); - assert.equal(service.workspaceBackupPaths.length, 0); + assert.deepEqual(service.workspaceBackupPaths, []); assert.ok(!fs.exists(service.toBackupPath(fooFile.fsPath))); assert.ok(!fs.exists(service.toBackupPath(barFile.fsPath))); @@ -152,9 +158,10 @@ suite('BackupMainService', () => { fs.mkdirSync(service.toBackupPath(barFile.fsPath)); fs.mkdirSync(path.join(service.toBackupPath(fooFile.fsPath), 'file')); fs.mkdirSync(path.join(service.toBackupPath(barFile.fsPath), 'untitled')); - service.pushWorkspaceBackupPathsSync([fooFile, barFile]); + service.registerWindowForBackups(1, false, null, fooFile.fsPath); + service.registerWindowForBackups(2, false, null, barFile.fsPath); service.loadSync(); - assert.equal(service.workspaceBackupPaths.length, 0); + assert.deepEqual(service.workspaceBackupPaths, []); assert.ok(!fs.exists(service.toBackupPath(fooFile.fsPath))); assert.ok(!fs.exists(service.toBackupPath(barFile.fsPath)));