Skip to content

Add unit tests for query history and remote queries#1166

Merged
aeisenberg merged 2 commits intomainfrom
aeisenberg/remote-queries-unit-tests
Feb 25, 2022
Merged

Add unit tests for query history and remote queries#1166
aeisenberg merged 2 commits intomainfrom
aeisenberg/remote-queries-unit-tests

Conversation

@aeisenberg
Copy link
Copy Markdown
Contributor

Adds some tests for reading in the history and manipulating.
There are some more tests to come later. Maybe in another PR, maybe in
this one.

Note that this PR uses a new node 16 API String.prototype.replaceAll.
I think this is ok since vscode ships with node 16. If this causes
problems, I can separate to a different PR and we can discuss there.

Checklist

  • [n/a] CHANGELOG.md has been updated to incorporate all user visible changes made by this pull request.
  • Issues have been created for any UI or other user-facing changes made by this pull request.
  • [Maintainers only] If this pull request makes user-facing changes that require documentation changes, open a corresponding docs pull request in the github/codeql repo and add the ready-for-doc-review label there.

@aeisenberg aeisenberg requested review from a team as code owners February 24, 2022 02:53
Copy link
Copy Markdown
Contributor

@charisk charisk left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for adding some much needed tests!

this.analysesResults.set(queryId, resultsForQuery);
void publishResults(resultsForQuery);
void publishResults([...resultsForQuery]);
const pos = resultsForQuery.length - 1;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we rename pos to something more descriptive for the function? e.g. analysisPosition?

Also, just a thought (that should be ignored for this PR!): we could have a better data structure for the query results that deals with stuff like that (replacing an analysis) instead of having to do it here. It'd then make the code a bit more easy to manage.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've always like immutable.js for things like this, but I don't like introducing it into an ongoing project. Maybe it's not such a bad idea in this case.

We do need to be careful. Now that we are saving data across restarts, any change in format will cause error when there is an upgrade. It's not a terrible situation since the worst case is that we need to delete some old queries on upgrade.

I should add version number to each saved artifact and the extension can read this and upgrade it appropriately when we change versions.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd be up for using immutable.js or any other way to enforce immutability.

Agree about versions - we'll need to be careful. Perhaps the overall query history store has a version? We can always deal with it the first time we need a new version I think.

let qhm: QueryHistoryManager;
let rawQueryHistory: any;
let remoteQueryResult0: RemoteQueryResult;
// let remoteQueryResult1: RemoteQueryResult;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should this be removed?

disposables = new DisposableBucket();
rawQueryHistory = fs.readJSONSync(path.join(STORAGE_DIR, 'workspace-query-history.json'));
remoteQueryResult0 = fs.readJSONSync(path.join(STORAGE_DIR, 'queries', rawQueryHistory[0].queryId, 'query-result.json'));
// remoteQueryResult1 = fs.readJSONSync(path.join(STORAGE_DIR, 'queries', rawQueryHistory[1].queryId, 'query-result.json'));
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should this be removed?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll be writing more tests and will likely need this variable.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shall we add it then? Happy either way.

fs.removeSync(STORAGE_DIR);
}

function* walk(dir: string): IterableIterator<string> {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice! At first I was thinking it might be an overkill to have an a generator for tests, but there's no harm in having it and puts us in a good position if we want to test a lot/big files.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I should probably move this to a shared location since it might be useful in other places.

Base automatically changed from aeisenberg/avoid-download to main February 24, 2022 16:11
@aeisenberg aeisenberg marked this pull request as draft February 24, 2022 16:19
@aeisenberg
Copy link
Copy Markdown
Contributor Author

Putting this into draft mode so I can work on it more.

@aeisenberg aeisenberg force-pushed the aeisenberg/remote-queries-unit-tests branch 3 times, most recently from b3fa7f6 to 9792a58 Compare February 25, 2022 00:18
@aeisenberg aeisenberg marked this pull request as ready for review February 25, 2022 00:20
@aeisenberg aeisenberg force-pushed the aeisenberg/remote-queries-unit-tests branch 2 times, most recently from 7c1dff9 to 76d6dfa Compare February 25, 2022 00:43
@aeisenberg aeisenberg changed the base branch from main to aeisenberg/query-history-version February 25, 2022 00:46
"@types/mocha": "^9.0.0",
"@types/nanoid": "^3.0.0",
"@types/node": "^12.14.1",
"@types/node": "^16.11.25",
Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Need to update to v16 to get the replaceAll method.

if (cancellationToken !== undefined) {
cancellationRegistration = cancellationToken.onCancellationRequested(_e => {
tk(child.pid);
tk(child.pid || 0);
Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In v16, pid is potentially undefined.

Comment on lines +680 to +682
if (finalSingleItem.status === QueryStatus.Completed) {
await this._onWillOpenQueryItem.fire(finalSingleItem);
}
Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fix small bug to avoid an error when someone clicks on an in progress item.

@@ -1,11 +0,0 @@
/**
Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

With node 16, this is no longer needed.

* A simple disposable object that does nothing other than contain a list of disposable objects.
* This is useful for implementing a `Disposable` that owns other disposable objects.
*/
export class DisposableBucket extends DisposableObject {
Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Used for tests.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shall we move this to the tests dir?

@aeisenberg aeisenberg force-pushed the aeisenberg/remote-queries-unit-tests branch from ee99427 to 9d17703 Compare February 25, 2022 02:10
Adds some tests for reading in the history and manipulating.
There are some more tests to come later. Maybe in another PR, maybe in
this one.

Note that this PR uses a new node 16 API String.prototype.replaceAll.
I think this is ok since vscode ships with node 16. If this causes
problems, I can separate to a different PR and we can discuss there.
@aeisenberg aeisenberg force-pushed the aeisenberg/remote-queries-unit-tests branch from 9d17703 to 4a928f1 Compare February 25, 2022 07:10
@aeisenberg aeisenberg requested a review from charisk February 25, 2022 14:59
@aeisenberg
Copy link
Copy Markdown
Contributor Author

@charisk can you take another look? I've made a lot of changes.

* A simple disposable object that does nothing other than contain a list of disposable objects.
* This is useful for implementing a `Disposable` that owns other disposable objects.
*/
export class DisposableBucket extends DisposableObject {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shall we move this to the tests dir?

"fileSizeInBytes": 81237,
"downloadLink": {
"id": "171544171",
"urlPath": "/repos/dsp-testing/qc-run2/actions/artifacts/171544171",
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Perhaps shouldn't use dsp-testing testing?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I can change the repo.

expect(qhm.treeDataProvider.allHistory.length).to.eq(2);
});

it('should remove and then a query from history', async () => {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
it('should remove and then a query from history', async () => {
it('should remove and then add query from history', async () => {

);
});

it('should avoid downloading an analysis result', async () => {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
it('should avoid downloading an analysis result', async () => {
it('should avoid re-downloading an analysis result', async () => {

});
});

// Since this test changes the state of the query history manager, we need to copy the original
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This comment doesn't look like it belongs here exactly - should it be near the test?

const result1 = arm.getAnalysesResults(rawQueryHistory[1].queryId);

// Shoule be equal, but not equivalent
expect(result0).to.deep.eq((arm as any).analysesResults.get(rawQueryHistory[0].queryId));
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This looks like it's interrogating the private state of the AnalysisResultsManager which doesn't feel right.

Should we not instead check that what we get back from getAnalysesResults is what we "downloaded"?

Copy link
Copy Markdown
Contributor Author

@aeisenberg aeisenberg Feb 25, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm specifically testing here that the results are an equivalent copy of what is stored by the AnalysesResultsManager. Instead of inspecting private state, I could call arm.getAnalysesResults twice and ensure that the objects returned are equivalent but different.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah I see, I think that would make more sense.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I added these tests because keeping them the same instance created weird race conditions, so just wanted to make sure we don't do this again.

Another reason to use immutable.

@@ -0,0 +1,21 @@
import * as path from 'path';
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can I make a suggestion that we start using more specific util modules? e.g. file-utils.ts rather than test-helpers which could be a bucket for pretty much anything.

Base automatically changed from aeisenberg/query-history-version to main February 25, 2022 16:11
Copy link
Copy Markdown
Contributor

@charisk charisk left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approving since all the comments are actually small suggestions!

- More explicit test helper module names
- Fix unit test names
- Better sanitization of repo names in tests
@aeisenberg aeisenberg enabled auto-merge February 25, 2022 17:58
@aeisenberg
Copy link
Copy Markdown
Contributor Author

All comments addressed.

@aeisenberg aeisenberg merged commit 94a311a into main Feb 25, 2022
@aeisenberg aeisenberg deleted the aeisenberg/remote-queries-unit-tests branch February 25, 2022 18:07
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants