Skip to content

Commit

Permalink
Merge pull request #312 from matepek/streamed-load
Browse files Browse the repository at this point in the history
Streamed load
  • Loading branch information
matepek authored Dec 4, 2021
2 parents 5ceb45b + 208eb38 commit 69badb2
Show file tree
Hide file tree
Showing 16 changed files with 304 additions and 178 deletions.
9 changes: 9 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,15 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).

## [Unreleased]

### Changed

- streamed load of tests

### Fixed

- [issue](https://github.com/matepek/vscode-catch2-test-adapter/issues/304) which caused the test message's location not to be resolved.
- [issue](https://github.com/matepek/vscode-catch2-test-adapter/issues/310) preventing proper load of gtest tests

## [4.0.9] - 2021-12-02

### Fixed
Expand Down
35 changes: 26 additions & 9 deletions src/AbstractExecutable.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import { TaskPool } from './util/TaskPool';
import { WorkspaceShared } from './WorkspaceShared';
import { ExecutableRunResultValue, RunningExecutable } from './RunningExecutable';
import { promisify } from 'util';
import { Version, getAbsolutePath, CancellationToken, CancellationFlag, reindentStr } from './Util';
import { Version, getAbsolutePath, CancellationToken, reindentStr } from './Util';
import {
resolveOSEnvironmentVariables,
createPythonIndexerForPathVariable,
Expand Down Expand Up @@ -487,7 +487,7 @@ export abstract class AbstractExecutable implements Disposable, FilePathResolver
return subsets;
}

protected abstract _reloadChildren(cancellationFlag: CancellationFlag): Promise<void>;
protected abstract _reloadChildren(cancellationToken: CancellationToken): Promise<void>;

protected abstract _getRunParamsInner(childrenToRun: readonly Readonly<AbstractTest>[]): string[];

Expand All @@ -506,13 +506,13 @@ export abstract class AbstractExecutable implements Disposable, FilePathResolver
return this.properties.prependTestRunningArgs.concat(this._getDebugParamsInner(childrenToRun, breakOnFailure));
}

public reloadTests(taskPool: TaskPool, cancellationFlag: CancellationFlag): Promise<void> {
if (cancellationFlag.isCancellationRequested) return Promise.resolve();
public reloadTests(taskPool: TaskPool, cancellationToken: CancellationToken): Promise<void> {
if (cancellationToken.isCancellationRequested) return Promise.resolve();

// mutually exclusive lock
return this._execItem.busy(async () => {
return taskPool.scheduleTask(async () => {
if (cancellationFlag.isCancellationRequested) return Promise.resolve();
if (cancellationToken.isCancellationRequested) return Promise.resolve();

this.shared.log.info('reloadTests', this.frameworkName, this.frameworkVersion, this.properties.path);

Expand All @@ -525,7 +525,7 @@ export abstract class AbstractExecutable implements Disposable, FilePathResolver
this._tests = new Map();
this._execItem.clearError();

await this._reloadChildren(cancellationFlag);
await this._reloadChildren(cancellationToken);

for (const test of prevTests.values()) {
if (!this._getTest(test.id)) this.removeTest(test);
Expand Down Expand Up @@ -742,7 +742,7 @@ export abstract class AbstractExecutable implements Disposable, FilePathResolver

if (hasMissingTest || hasNewTest) {
// exec probably has changed
this.reloadTests(this.shared.taskPool, this.shared.cancellationFlag).catch((reason: Error) => {
this.reloadTests(this.shared.taskPool, this.shared.cancellationToken).catch((reason: Error) => {
// Suite possibly deleted: It is a dead suite but this should have been handled elsewhere
this.shared.log.error('reloading-error: ', reason);
});
Expand Down Expand Up @@ -782,6 +782,23 @@ export abstract class AbstractExecutable implements Disposable, FilePathResolver
}
}

public findSourceFilePath(file: string | undefined): string | undefined {
if (typeof file != 'string') return undefined;

let resolved = file;

for (const m in this.properties.sourceFileMap) {
resolved = resolved.replace(m, this.properties.sourceFileMap[m]); // Note: it just replaces the first occurence
}

resolved = pathlib.normalize(resolved);
resolved = this._findFilePath(resolved);

this.shared.log.debug('findSourceFilePath:', file, '=>', resolved);

return resolved;
}

public async resolveAndFindSourceFilePath(file: string | undefined): Promise<string | undefined> {
if (typeof file != 'string') return undefined;

Expand All @@ -795,7 +812,7 @@ export abstract class AbstractExecutable implements Disposable, FilePathResolver
resolved = pathlib.normalize(resolved);
resolved = this._findFilePath(resolved);

this.shared.log.debug('_resolveSourceFilePath:', file, '=>', resolved);
this.shared.log.debug('resolveAndFindSourceFilePath:', file, '=>', resolved);

return resolved;
}
Expand Down Expand Up @@ -823,7 +840,7 @@ export abstract class AbstractExecutable implements Disposable, FilePathResolver
protected processStdErr(testRun: vscode.TestRun, runPrefix: string, str: string): void {
testRun.appendOutput(runPrefix + '⬇ std::cerr:\r\n');
const indented = reindentStr(0, 2, str);
testRun.appendOutput(indented.map(x => runPrefix + '|' + x + '\r\n').join(''));
testRun.appendOutput(indented.map(x => runPrefix + '> ' + x + '\r\n').join(''));
testRun.appendOutput(runPrefix + '⬆ std::cerr\r\n');
}
}
Expand Down
10 changes: 5 additions & 5 deletions src/ExecutableConfig.ts
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@ export class ExecutableConfig implements vscode.Disposable {
const suite = await factory.create(false);
if (suite) {
try {
await suite.reloadTests(this._shared.taskPool, this._shared.cancellationFlag);
await suite.reloadTests(this._shared.taskPool, this._shared.cancellationToken);
this._executables.set(file, suite);
} catch (reason) {
debugBreak();
Expand Down Expand Up @@ -355,7 +355,7 @@ export class ExecutableConfig implements vscode.Disposable {
private readonly _lastEventArrivedAt: Map<string /*fsPath*/, number /*Date*/> = new Map();

private async _handleEverything(filePath: string): Promise<void> {
if (this._shared.cancellationFlag.isCancellationRequested) return;
if (this._shared.cancellationToken.isCancellationRequested) return;

const isHandlerRunningForFile = this._lastEventArrivedAt.get(filePath) !== undefined;

Expand Down Expand Up @@ -391,7 +391,7 @@ export class ExecutableConfig implements vscode.Disposable {
}

private async _recursiveHandleFile(filePath: string, delay = 1024, tryCount = 1): Promise<void> {
if (this._shared.cancellationFlag.isCancellationRequested) return;
if (this._shared.cancellationToken.isCancellationRequested) return;

const lastEventArrivedAt = this._lastEventArrivedAt.get(filePath);

Expand Down Expand Up @@ -450,7 +450,7 @@ export class ExecutableConfig implements vscode.Disposable {
isFileExistsAndExecutable = false,
delay = 128,
): Promise<void> {
if (this._shared.cancellationFlag.isCancellationRequested) return;
if (this._shared.cancellationToken.isCancellationRequested) return;

const filePath = runnable.properties.path;
const lastEventArrivedAt = this._lastEventArrivedAt.get(filePath);
Expand All @@ -465,7 +465,7 @@ export class ExecutableConfig implements vscode.Disposable {
if (this._waitForBuildProcess) await this._shared.buildProcessChecker.resolveAtFinish();

try {
await runnable.reloadTests(this._shared.taskPool, this._shared.cancellationFlag);
await runnable.reloadTests(this._shared.taskPool, this._shared.cancellationToken);
this._executables.set(filePath, runnable); // it might be set already but we don't care
//TODO:release this._shared.sendRetireEvent([runnable]);
} catch (reason: any /*eslint-disable-line*/) {
Expand Down
1 change: 1 addition & 0 deletions src/Spawner.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ export type SpawnOptionsWithoutStdio = fsw.SpawnOptionsWithoutStdio;

///

//TODO:future, add cancellation flag
export interface Spawner {
spawnAsync(cmd: string, args: string[], options: SpawnOptionsWithoutStdio, timeout?: number): Promise<SpawnReturns>;

Expand Down
1 change: 1 addition & 0 deletions src/TestItemManager.ts
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ export class TestItemManager {
parent.children.delete(item.id);
parent.children.add(item);
} else {
this.controller.items.delete(item.id);
this.controller.items.add(item);
}

Expand Down
19 changes: 19 additions & 0 deletions src/TestResultBuilder.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ export class TestResultBuilder<T extends AbstractTest = AbstractTest> {
private readonly _log: LoggerWrapper;
private readonly _message: vscode.TestMessage[] = [];
private _result: TestResult | undefined = undefined;
//private readonly _outputLines: string[] = [];

public started(): void {
this._log.info('Test', this.test.id, 'has started.');
Expand Down Expand Up @@ -77,6 +78,9 @@ export class TestResultBuilder<T extends AbstractTest = AbstractTest> {
} else {
lines = msgs;
}

//this._outputLines.push(...lines);

this.testRun.appendOutput(lines.map(x => this.runPrefix + x + '\r\n').join(''));
}

Expand Down Expand Up @@ -114,6 +118,7 @@ export class TestResultBuilder<T extends AbstractTest = AbstractTest> {
expected: string,
actual: string,
): void {
file = this.test.executable.findSourceFilePath(file);
const msg = vscode.TestMessage.diff(message, expected, actual);
msg.location = TestResultBuilder._getLocation(file, line);
this._message.push(msg);
Expand All @@ -126,6 +131,7 @@ export class TestResultBuilder<T extends AbstractTest = AbstractTest> {
expanded: string,
_type: string | undefined,
): void {
file = this.test.executable.findSourceFilePath(file);
this.addMessage(file, line, 'Expanded: `' + expanded + '`');

const loc = TestResultBuilder.getLocationAtStr(file, line);
Expand All @@ -140,19 +146,22 @@ export class TestResultBuilder<T extends AbstractTest = AbstractTest> {
title: string,
...message: string[]
): void {
file = this.test.executable.findSourceFilePath(file);
this.addMessage(file, line, [`${title}`, ...message].join('\r\n'));
const loc = TestResultBuilder.getLocationAtStr(file, line);
this.addOutputLine(1, `${title}${loc}`);
this.addOutputLine(2, ...message);
}

public addMessage(file: string | undefined, line: number | string | undefined, ...message: string[]): void {
file = this.test.executable.findSourceFilePath(file);
const msg = new vscode.TestMessage(message.join('\r\n'));
msg.location = TestResultBuilder._getLocation(file, line);
this._message.push(msg);
}

public addMarkdownMsg(file: string | undefined, line: number | string | undefined, ...message: string[]): void {
file = this.test.executable.findSourceFilePath(file);
const msg = new vscode.TestMessage(new vscode.MarkdownString(message.join('\r\n\n')));
msg.location = TestResultBuilder._getLocation(file, line);
this._message.push(msg);
Expand All @@ -164,6 +173,7 @@ export class TestResultBuilder<T extends AbstractTest = AbstractTest> {
title: string,
...message: string[]
): void {
file = this.test.executable.findSourceFilePath(file);
const loc = TestResultBuilder.getLocationAtStr(file, line);
this.addOutputLine(1, `${title}${loc}${message.length ? ':' : ''}`);
this.addOutputLine(2, ...message);
Expand Down Expand Up @@ -215,6 +225,15 @@ export class TestResultBuilder<T extends AbstractTest = AbstractTest> {

this.endMessage();

// {
// const fileOfTest = this.test.file;
// const lineOfTest = this.test.line;
// if (fileOfTest && lineOfTest && (this._result == 'failed' || this._result === 'errored')) {
// const formatted = this._outputLines.map(x => ansi.unstyle(x));
// this.addMessage(fileOfTest, lineOfTest, 'Output', ...formatted);
// }
// }

switch (this._result) {
case undefined:
throw Error('result is not finalized');
Expand Down
13 changes: 5 additions & 8 deletions src/WorkspaceShared.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { TaskPool } from './util/TaskPool';
import { ResolveRuleAsync } from './util/ResolveRule';
import { BuildProcessChecker } from './util/BuildProcessChecker';
import { SharedWithTest } from './AbstractTest';
import { CancellationFlag } from './Util';
import { CancellationToken } from './Util';
import { TestItemManager } from './TestItemManager';

export class WorkspaceShared implements SharedWithTest {
Expand All @@ -15,7 +15,7 @@ export class WorkspaceShared implements SharedWithTest {
public readonly executeTask: (
taskName: string,
varsToResolve: readonly ResolveRuleAsync[],
cancellationToken: vscode.CancellationToken,
cancellationToken: CancellationToken,
) => Promise<number | undefined>,
public readonly varToValue: readonly Readonly<ResolveRuleAsync>[],
public rngSeed: 'time' | number | null,
Expand All @@ -36,19 +36,16 @@ export class WorkspaceShared implements SharedWithTest {
public readonly taskPool: TaskPool;
public readonly buildProcessChecker: BuildProcessChecker;
private readonly _execRunningTimeoutChangeEmitter = new vscode.EventEmitter<void>();
private readonly _cancellationFlag = { isCancellationRequested: false };
private readonly _cancellationTokenSource: vscode.CancellationTokenSource = new vscode.CancellationTokenSource();
public readonly cancellationToken: CancellationToken = this._cancellationTokenSource.token;

public dispose(): void {
this._cancellationFlag.isCancellationRequested = true;
this._cancellationTokenSource.cancel();
this.buildProcessChecker.dispose();
this._execRunningTimeoutChangeEmitter.dispose();
this.log.dispose();
}

public get cancellationFlag(): CancellationFlag {
return this._cancellationFlag;
}

public get execRunningTimeout(): number | null {
return this._execRunningTimeout;
}
Expand Down
Loading

0 comments on commit 69badb2

Please sign in to comment.