Skip to content

Commit 24e4708

Browse files
Merge pull request #2017 from github/robertbrignull/logged_error_telemetry
Introduce showAndLogExceptionWithTelemetry
2 parents 4f0032d + 420fd8d commit 24e4708

27 files changed

Lines changed: 480 additions & 129 deletions

extensions/ql-vscode/src/astViewer.ts

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,9 @@ import {
2525
} from "./pure/bqrs-utils";
2626
import { commandRunner } from "./commandRunner";
2727
import { DisposableObject } from "./pure/disposable-object";
28-
import { showAndLogErrorMessage } from "./helpers";
28+
import { showAndLogExceptionWithTelemetry } from "./helpers";
29+
import { asError, getErrorMessage } from "./pure/helpers-pure";
30+
import { redactableError } from "./pure/errors";
2931

3032
export interface AstItem {
3133
id: BqrsId;
@@ -146,7 +148,12 @@ export class AstViewer extends DisposableObject {
146148
() => {
147149
/**/
148150
},
149-
(err) => showAndLogErrorMessage(err),
151+
(error: unknown) =>
152+
showAndLogExceptionWithTelemetry(
153+
redactableError(
154+
asError(error),
155+
)`Failed to reveal AST: ${getErrorMessage(error)}`,
156+
),
150157
);
151158
}
152159

@@ -204,7 +211,12 @@ export class AstViewer extends DisposableObject {
204211
() => {
205212
/**/
206213
},
207-
(err) => showAndLogErrorMessage(err),
214+
(error: unknown) =>
215+
showAndLogExceptionWithTelemetry(
216+
redactableError(
217+
asError(error),
218+
)`Failed to reveal AST: ${getErrorMessage(error)}`,
219+
),
208220
);
209221
}
210222
}

extensions/ql-vscode/src/commandRunner.ts

Lines changed: 29 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,14 @@ import {
66
Disposable,
77
ProgressLocation,
88
} from "vscode";
9-
import { showAndLogErrorMessage, showAndLogWarningMessage } from "./helpers";
9+
import {
10+
showAndLogExceptionWithTelemetry,
11+
showAndLogWarningMessage,
12+
} from "./helpers";
1013
import { extLogger } from "./common";
1114
import { asError, getErrorMessage, getErrorStack } from "./pure/helpers-pure";
1215
import { telemetryListener } from "./telemetry";
16+
import { redactableError } from "./pure/errors";
1317

1418
export class UserCancellationException extends Error {
1519
/**
@@ -125,23 +129,28 @@ export function commandRunner(
125129
try {
126130
return await task(...args);
127131
} catch (e) {
128-
const errorMessage = `${getErrorMessage(e) || e} (${commandId})`;
129132
error = asError(e);
133+
const errorMessage = redactableError(error)`${
134+
getErrorMessage(e) || e
135+
} (${commandId})`;
130136
const errorStack = getErrorStack(e);
131137
if (e instanceof UserCancellationException) {
132138
// User has cancelled this action manually
133139
if (e.silent) {
134-
void extLogger.log(errorMessage);
140+
void extLogger.log(errorMessage.fullMessage);
135141
} else {
136-
void showAndLogWarningMessage(errorMessage);
142+
void showAndLogWarningMessage(errorMessage.fullMessage);
137143
}
138144
} else {
139145
// Include the full stack in the error log only.
140146
const fullMessage = errorStack
141-
? `${errorMessage}\n${errorStack}`
142-
: errorMessage;
143-
void showAndLogErrorMessage(errorMessage, {
147+
? `${errorMessage.fullMessage}\n${errorStack}`
148+
: errorMessage.fullMessage;
149+
void showAndLogExceptionWithTelemetry(errorMessage, {
144150
fullMessage,
151+
extraTelemetryProperties: {
152+
command: commandId,
153+
},
145154
});
146155
}
147156
return undefined;
@@ -178,24 +187,31 @@ export function commandRunnerWithProgress<R>(
178187
try {
179188
return await withProgress(progressOptionsWithDefaults, task, ...args);
180189
} catch (e) {
181-
const errorMessage = `${getErrorMessage(e) || e} (${commandId})`;
182190
error = asError(e);
191+
const errorMessage = redactableError`${
192+
getErrorMessage(e) || e
193+
} (${commandId})`;
183194
const errorStack = getErrorStack(e);
184195
if (e instanceof UserCancellationException) {
185196
// User has cancelled this action manually
186197
if (e.silent) {
187-
void outputLogger.log(errorMessage);
198+
void outputLogger.log(errorMessage.fullMessage);
188199
} else {
189-
void showAndLogWarningMessage(errorMessage, { outputLogger });
200+
void showAndLogWarningMessage(errorMessage.fullMessage, {
201+
outputLogger,
202+
});
190203
}
191204
} else {
192205
// Include the full stack in the error log only.
193206
const fullMessage = errorStack
194-
? `${errorMessage}\n${errorStack}`
195-
: errorMessage;
196-
void showAndLogErrorMessage(errorMessage, {
207+
? `${errorMessage.fullMessage}\n${errorStack}`
208+
: errorMessage.fullMessage;
209+
void showAndLogExceptionWithTelemetry(errorMessage, {
197210
outputLogger,
198211
fullMessage,
212+
extraTelemetryProperties: {
213+
command: commandId,
214+
},
199215
});
200216
}
201217
return undefined;

extensions/ql-vscode/src/contextual/queryResolver.ts

Lines changed: 11 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,8 @@ import {
77
getPrimaryDbscheme,
88
getQlPackForDbscheme,
99
getOnDiskWorkspaceFolders,
10-
showAndLogErrorMessage,
1110
QlPacksForLanguage,
11+
showAndLogExceptionWithTelemetry,
1212
} from "../helpers";
1313
import { KeyType, kindOfKeyType, nameOfKeyType, tagOfKeyType } from "./keyType";
1414
import { CodeQLCliServer } from "../cli";
@@ -18,6 +18,7 @@ import { createInitialQueryInfo } from "../run-queries-shared";
1818
import { CancellationToken, Uri } from "vscode";
1919
import { ProgressCallback } from "../commandRunner";
2020
import { QueryRunner } from "../queryRunner";
21+
import { redactableError } from "../pure/errors";
2122

2223
export async function qlpackOfDatabase(
2324
cli: CodeQLCliServer,
@@ -88,22 +89,16 @@ export async function resolveQueries(
8889
}
8990

9091
// No queries found. Determine the correct error message for the various scenarios.
91-
const errorMessage = `No ${nameOfKeyType(
92-
keyType,
93-
)} queries (tagged "${tagOfKeyType(
94-
keyType,
95-
)}") could be found in the current library path. \
96-
Try upgrading the CodeQL libraries. If that doesn't work, then ${nameOfKeyType(
97-
keyType,
98-
)} queries are not yet available \
99-
for this language.`;
92+
const keyTypeName = nameOfKeyType(keyType);
93+
const keyTypeTag = tagOfKeyType(keyType);
94+
const joinedPacksToSearch = packsToSearch.join(", ");
95+
const error = redactableError`No ${keyTypeName} queries (tagged "${keyTypeTag}") could be found in the \
96+
current library path (tried searching the following packs: ${joinedPacksToSearch}). \
97+
Try upgrading the CodeQL libraries. If that doesn't work, then ${keyTypeName} queries are not yet available \
98+
for this language.`;
10099

101-
void showAndLogErrorMessage(errorMessage);
102-
throw new Error(
103-
`Couldn't find any queries tagged ${tagOfKeyType(
104-
keyType,
105-
)} in any of the following packs: ${packsToSearch.join(", ")}.`,
106-
);
100+
void showAndLogExceptionWithTelemetry(error);
101+
throw error;
107102
}
108103

109104
async function resolveContextualQuery(

extensions/ql-vscode/src/databases-ui.ts

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -30,18 +30,20 @@ import {
3030
isLikelyDatabaseRoot,
3131
isLikelyDbLanguageFolder,
3232
showAndLogErrorMessage,
33+
showAndLogExceptionWithTelemetry,
3334
} from "./helpers";
3435
import { extLogger } from "./common";
3536
import {
3637
importArchiveDatabase,
3738
promptImportGithubDatabase,
3839
promptImportInternetDatabase,
3940
} from "./databaseFetcher";
40-
import { asyncFilter, getErrorMessage } from "./pure/helpers-pure";
41+
import { asError, asyncFilter, getErrorMessage } from "./pure/helpers-pure";
4142
import { QueryRunner } from "./queryRunner";
4243
import { isCanary } from "./config";
4344
import { App } from "./common/app";
4445
import { Credentials } from "./common/authentication";
46+
import { redactableError } from "./pure/errors";
4547

4648
enum SortOrder {
4749
NameAsc = "NameAsc",
@@ -354,7 +356,11 @@ export class DatabaseUI extends DisposableObject {
354356
try {
355357
await this.chooseAndSetDatabase(true, progress, token);
356358
} catch (e) {
357-
void showAndLogErrorMessage(getErrorMessage(e));
359+
void showAndLogExceptionWithTelemetry(
360+
redactableError(
361+
asError(e),
362+
)`Failed to choose and set database: ${getErrorMessage(e)}`,
363+
);
358364
}
359365
};
360366

@@ -437,6 +443,11 @@ export class DatabaseUI extends DisposableObject {
437443
void extLogger.log(`Deleting orphaned database '${dbDir}'.`);
438444
await remove(dbDir);
439445
} catch (e) {
446+
void showAndLogExceptionWithTelemetry(
447+
redactableError(
448+
asError(e),
449+
)`Failed to delete orphaned database: ${getErrorMessage(e)}`,
450+
);
440451
failures.push(`${basename(dbDir)}`);
441452
}
442453
}),
@@ -458,8 +469,12 @@ export class DatabaseUI extends DisposableObject {
458469
): Promise<void> => {
459470
try {
460471
await this.chooseAndSetDatabase(false, progress, token);
461-
} catch (e) {
462-
void showAndLogErrorMessage(getErrorMessage(e));
472+
} catch (e: unknown) {
473+
void showAndLogExceptionWithTelemetry(
474+
redactableError(
475+
asError(e),
476+
)`Failed to choose and set database: ${getErrorMessage(e)}`,
477+
);
463478
}
464479
};
465480

extensions/ql-vscode/src/databases.ts

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,10 @@ import * as vscode from "vscode";
55
import * as cli from "./cli";
66
import { ExtensionContext } from "vscode";
77
import {
8-
showAndLogErrorMessage,
98
showAndLogWarningMessage,
109
showAndLogInformationMessage,
1110
isLikelyDatabaseRoot,
11+
showAndLogExceptionWithTelemetry,
1212
} from "./helpers";
1313
import { ProgressCallback, withProgress } from "./commandRunner";
1414
import {
@@ -22,6 +22,7 @@ import { Logger, extLogger } from "./common";
2222
import { asError, getErrorMessage } from "./pure/helpers-pure";
2323
import { QueryRunner } from "./queryRunner";
2424
import { pathsEqual } from "./pure/files";
25+
import { redactableError } from "./pure/errors";
2526

2627
/**
2728
* databases.ts
@@ -794,8 +795,10 @@ export class DatabaseManager extends DisposableObject {
794795
await this.updatePersistedDatabaseList();
795796
} catch (e) {
796797
// database list had an unexpected type - nothing to be done?
797-
void showAndLogErrorMessage(
798-
`Database list loading failed: ${getErrorMessage(e)}`,
798+
void showAndLogExceptionWithTelemetry(
799+
redactableError(
800+
asError(e),
801+
)`Database list loading failed: ${getErrorMessage(e)}`,
799802
);
800803
}
801804

extensions/ql-vscode/src/eval-log-viewer.ts

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,9 @@ import {
1010
} from "vscode";
1111
import { commandRunner } from "./commandRunner";
1212
import { DisposableObject } from "./pure/disposable-object";
13-
import { showAndLogErrorMessage } from "./helpers";
13+
import { showAndLogExceptionWithTelemetry } from "./helpers";
14+
import { asError, getErrorMessage } from "./pure/helpers-pure";
15+
import { redactableError } from "./pure/errors";
1416

1517
export interface EvalLogTreeItem {
1618
label?: string;
@@ -104,7 +106,12 @@ export class EvalLogViewer extends DisposableObject {
104106
() => {
105107
/**/
106108
},
107-
(err) => showAndLogErrorMessage(err),
109+
(err: unknown) =>
110+
showAndLogExceptionWithTelemetry(
111+
redactableError(
112+
asError(err),
113+
)`Failed to reveal tree view: ${getErrorMessage(err)}`,
114+
),
108115
);
109116
}
110117
}

extensions/ql-vscode/src/extension.ts

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,7 @@ import {
7272
showAndLogInformationMessage,
7373
showInformationMessageWithAction,
7474
tmpDir,
75+
showAndLogExceptionWithTelemetry,
7576
} from "./helpers";
7677
import { asError, assertNever, getErrorMessage } from "./pure/helpers-pure";
7778
import { spawnIdeServer } from "./ide-server";
@@ -137,6 +138,7 @@ import { VariantAnalysisResultsManager } from "./remote-queries/variant-analysis
137138
import { ExtensionApp } from "./common/vscode/vscode-app";
138139
import { RepositoriesFilterSortStateWithIds } from "./pure/variant-analysis-filter-sort";
139140
import { DbModule } from "./databases/db-module";
141+
import { redactableError } from "./pure/errors";
140142

141143
/**
142144
* extension.ts
@@ -713,7 +715,11 @@ async function activateWithInstalledDistribution(
713715
try {
714716
await compareView.showResults(from, to);
715717
} catch (e) {
716-
void showAndLogErrorMessage(getErrorMessage(e));
718+
void showAndLogExceptionWithTelemetry(
719+
redactableError(asError(e))`Failed to show results: ${getErrorMessage(
720+
e,
721+
)}`,
722+
);
717723
}
718724
}
719725

@@ -809,10 +815,10 @@ async function activateWithInstalledDistribution(
809815
const errorMessage = getErrorMessage(e).includes(
810816
"Generating qhelp in markdown",
811817
)
812-
? `Could not generate markdown from ${pathToQhelp}: Bad formatting in .qhelp file.`
813-
: `Could not open a preview of the generated file (${absolutePathToMd}).`;
814-
void showAndLogErrorMessage(errorMessage, {
815-
fullMessage: `${errorMessage}\n${e}`,
818+
? redactableError`Could not generate markdown from ${pathToQhelp}: Bad formatting in .qhelp file.`
819+
: redactableError`Could not open a preview of the generated file (${absolutePathToMd}).`;
820+
void showAndLogExceptionWithTelemetry(errorMessage, {
821+
fullMessage: `${errorMessage}\n${getErrorMessage(e)}`,
816822
});
817823
}
818824
}

0 commit comments

Comments
 (0)