Skip to content

Commit 72a70a5

Browse files
authored
E2E test: cleanup test files (#7144)
Cleanup of test files, including undoing github actions using a new fixture called `cleanup`. ### QA Notes @:web @:win @:plots @:notebooks @:scm @:top-action-bar
1 parent 759c0e5 commit 72a70a5

File tree

7 files changed

+68
-2
lines changed

7 files changed

+68
-2
lines changed

test/e2e/infra/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ export * from './logger';
99
export * from './workbench';
1010
export * from './keyboard';
1111
export * from './test-runner';
12+
export * from './test-teardown.js';
1213

1314
// pages
1415
export * from '../pages/console';

test/e2e/infra/test-teardown.ts

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
/*---------------------------------------------------------------------------------------------
2+
* Copyright (C) 2025 Posit Software, PBC. All rights reserved.
3+
* Licensed under the Elastic License 2.0. See LICENSE.txt for license information.
4+
*--------------------------------------------------------------------------------------------*/
5+
6+
import * as fs from 'fs';
7+
import { execSync } from 'child_process';
8+
9+
export class TestTeardown {
10+
11+
constructor(private _workspacePathOrFolder: string) { }
12+
13+
async removeTestFiles(files: string[]): Promise<void> {
14+
for (const file of files) {
15+
const filePath = this._workspacePathOrFolder + '/' + file;
16+
if (fs.existsSync(filePath)) {
17+
fs.rmSync(filePath, { recursive: true, force: true });
18+
}
19+
}
20+
}
21+
22+
async removeTestFolder(folder: string): Promise<void> {
23+
const folderPath = this._workspacePathOrFolder + '/' + folder;
24+
if (fs.existsSync(folderPath)) {
25+
fs.rmSync(folderPath, { recursive: true, force: true });
26+
}
27+
}
28+
29+
async discardAllChanges(): Promise<void> {
30+
try {
31+
execSync('git reset --hard $(git rev-list --max-parents=0 HEAD)', { cwd: this._workspacePathOrFolder });
32+
execSync('git clean -fd', { cwd: this._workspacePathOrFolder });
33+
} catch (error) {
34+
console.error('Failed to discard changes:', error);
35+
}
36+
}
37+
}

test/e2e/tests/_test.setup.ts

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ import { randomUUID } from 'crypto';
2121
import archiver from 'archiver';
2222

2323
// Local imports
24-
import { Application, Logger, UserSetting, UserSettingsFixtures, createLogger, createApp, TestTags, Sessions, HotKeys } from '../infra';
24+
import { Application, Logger, UserSetting, UserSettingsFixtures, createLogger, createApp, TestTags, Sessions, HotKeys, TestTeardown } from '../infra';
2525
import { PackageManager } from '../pages/utils/packageManager';
2626

2727
// Constants
@@ -361,6 +361,11 @@ export const test = base.extend<TestFixtures & CurrentsFixtures, WorkerFixtures
361361
logger.log(endLog);
362362
logger.log('');
363363
}, { scope: 'test', auto: true }],
364+
365+
cleanup: async ({ app }, use) => {
366+
const cleanup = new TestTeardown(app.workspacePathOrFolder);
367+
await use(cleanup);
368+
},
364369
});
365370

366371
// Runs once per worker. If a worker handles multiple specs, these hooks only run for the first spec.
@@ -439,6 +444,7 @@ interface TestFixtures {
439444
runCommand: (command: string, options?: { keepOpen?: boolean; exactMatch?: boolean }) => Promise<void>;
440445
executeCode: (language: 'Python' | 'R', code: string) => Promise<void>;
441446
hotKeys: HotKeys;
447+
cleanup: TestTeardown;
442448
}
443449

444450
interface WorkerFixtures {

test/e2e/tests/notebook/notebook-create.test.ts

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@ test.use({
1111
suiteId: __filename
1212
});
1313

14+
let newFileName: string;
15+
1416
test.describe('Notebooks', {
1517
tag: [tags.CRITICAL, tags.WEB, tags.WIN, tags.NOTEBOOKS]
1618
}, () => {
@@ -31,6 +33,10 @@ test.describe('Notebooks', {
3133
await app.workbench.notebooks.closeNotebookWithoutSaving();
3234
});
3335

36+
test.afterAll(async function ({ cleanup }) {
37+
await cleanup.removeTestFiles([newFileName]);
38+
});
39+
3440
test('Python - Verify code cell execution in notebook', async function ({ app }) {
3541
await app.workbench.notebooks.addCodeToCellAtIndex('eval("8**2")');
3642
await app.workbench.notebooks.executeCodeInCell();
@@ -68,7 +74,7 @@ test.describe('Notebooks', {
6874
await app.workbench.quickaccess.runCommand('workbench.action.files.saveAs', { keepOpen: true });
6975
await app.workbench.quickInput.waitForQuickInputOpened();
7076
// Generate a random filename
71-
const newFileName = `saved-session-test-${Math.random().toString(36).substring(7)}.ipynb`;
77+
newFileName = `saved-session-test-${Math.random().toString(36).substring(7)}.ipynb`;
7278

7379
await app.workbench.quickInput.type(path.join(app.workspacePathOrFolder, newFileName));
7480
await app.workbench.quickInput.clickOkButton();

test/e2e/tests/plots/plots.test.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,10 @@ test.describe('Plots', { tag: [tags.PLOTS, tags.EDITOR] }, () => {
3030
await app.workbench.plots.waitForNoPlots();
3131
});
3232

33+
test.afterAll(async function ({ cleanup }) {
34+
await cleanup.removeTestFiles(['Python-scatter.jpeg', 'Python-scatter-editor.jpeg']);
35+
});
36+
3337
test('Python - Verify basic plot functionality - Dynamic Plot', {
3438
tag: [tags.CRITICAL, tags.WEB, tags.WIN]
3539
}, async function ({ app, logger, headless, logsPath }, testInfo) {
@@ -283,6 +287,10 @@ test.describe('Plots', { tag: [tags.PLOTS, tags.EDITOR] }, () => {
283287
await app.workbench.plots.waitForNoPlots();
284288
});
285289

290+
test.afterAll(async function ({ cleanup }) {
291+
await cleanup.removeTestFiles(['r-cars.svg', 'r-cars.jpeg', 'plot.png']);
292+
});
293+
286294
test('R - Verify basic plot functionality', {
287295
tag: [tags.CRITICAL, tags.WEB, tags.WIN],
288296
annotation: [{ type: 'issue', description: 'https://github.com/posit-dev/positron/issues/5954 (see comment)' }]

test/e2e/tests/scm/scm.test.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,10 @@ test.describe('Source Content Management', {
1414
tag: [tags.SCM, tags.WEB, tags.WIN]
1515
}, () => {
1616

17+
test.afterAll(async function ({ cleanup }) {
18+
await cleanup.discardAllChanges();
19+
});
20+
1721
test('Verify SCM Tracks File Modifications, Staging, and Commit Actions', async function ({ app, openFile }) {
1822

1923
const file = 'chinook-sqlite.py';

test/e2e/tests/top-action-bar/top-action-bar-save.test.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,10 @@ test.describe('Top Action Bar - Save Actions', {
2020
}
2121
});
2222

23+
test.afterAll(async function ({ cleanup }) {
24+
await cleanup.discardAllChanges();
25+
});
26+
2327
test('Verify `Save` and `Save All` are disabled when no unsaved editors are open', async function ({ app }) {
2428
await app.workbench.quickaccess.runCommand('workbench.action.closeAllEditors', { keepOpen: false });
2529
await expect(app.workbench.topActionBar.saveButton).not.toBeEnabled();

0 commit comments

Comments
 (0)