Skip to content

Commit 23bfc5f

Browse files
committed
pr annotations
1 parent ef60977 commit 23bfc5f

File tree

8 files changed

+180
-21
lines changed

8 files changed

+180
-21
lines changed

.github/workflows/validate.yml

Lines changed: 19 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ jobs:
3535
cache: npm
3636
- name: Install dependencies
3737
run: npm ci
38-
- name: Validate
38+
- name: Lint
3939
run: npm run lint
4040

4141
format:
@@ -52,5 +52,22 @@ jobs:
5252
cache: npm
5353
- name: Install dependencies
5454
run: npm ci
55-
- name: Validate
55+
- name: Check format
5656
run: npm run check-format
57+
58+
type-warnings:
59+
runs-on: ubuntu-latest
60+
steps:
61+
- name: Checkout
62+
uses: actions/checkout@v4
63+
with:
64+
persist-credentials: false
65+
- name: Install Node.js
66+
uses: actions/setup-node@v4
67+
with:
68+
node-version: 22
69+
cache: npm
70+
- name: Install dependencies
71+
run: npm ci
72+
- name: Generate type warnings
73+
run: npm run generate-type-warnings

development/ci-commands.js

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
import pathUtil from "node:path";
2+
3+
/**
4+
* @returns {boolean} true if running in GitHub Actions, etc.
5+
*/
6+
export const isCI = () => !!process.env.CI;
7+
8+
/**
9+
* @typedef Annotation
10+
* @property {'notice'|'warning'|'error'} type
11+
* @property {string} file Absolute path to file or relative from repository root
12+
* @property {string} title
13+
* @property {string} message
14+
* @property {number} [line] 1-indexed
15+
* @property {number} [col] 1-indexed
16+
* @property {number} [endLine] 1-indexed
17+
* @property {number} [endCol] 1-indexed
18+
*/
19+
20+
/**
21+
* @param {Annotation} annotation
22+
*/
23+
export const createAnnotation = (annotation) => {
24+
const rootDir = pathUtil.join(import.meta.dirname, "..");
25+
const relativeFileName = pathUtil.relative(rootDir, annotation.file);
26+
27+
let output = "";
28+
output += `::${annotation.type} `;
29+
output += `file=${relativeFileName}`;
30+
31+
if (typeof annotation.line === "number") output += `,line=${annotation.line}`;
32+
if (typeof annotation.col === "number") output += `,col=${annotation.col}`;
33+
if (typeof annotation.endLine === "number")
34+
output += `,endLine=${annotation.endLine}`;
35+
if (typeof annotation.endCol === "number")
36+
output += `,endCol=${annotation.endCol}`;
37+
38+
output += `,title=${annotation.title}::`;
39+
output += annotation.message;
40+
41+
console.log(output);
42+
};

development/colors.js

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,5 +3,8 @@ const color = (i) => (enableColor ? i : "");
33

44
export const RESET = color("\x1b[0m");
55
export const BOLD = color("\x1b[1m");
6+
67
export const RED = color("\x1b[31m");
8+
export const YELLOW = color("\x1b[33m");
79
export const GREEN = color("\x1b[32m");
10+
export const BLUE = color("\x1b[34m");
Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,65 @@
1+
import pathUtil from "node:path";
2+
import ts from "typescript";
3+
import { createAnnotation } from "./ci-commands.js";
4+
5+
/**
6+
* @fileoverview
7+
* tsc command output will be parsed by GitHub Actions as errors.
8+
* We want them to be just warnings.
9+
*/
10+
11+
const check = () => {
12+
const rootDir = pathUtil.join(import.meta.dirname, "..");
13+
const tsconfigPath = pathUtil.join(rootDir, "tsconfig.json");
14+
const commandLine = ts.getParsedCommandLineOfConfigFile(
15+
tsconfigPath,
16+
{},
17+
ts.sys
18+
);
19+
20+
const program = ts.createProgram({
21+
rootNames: commandLine.fileNames,
22+
options: commandLine.options,
23+
});
24+
const emitted = program.emit();
25+
26+
const diagnostics = [
27+
...ts.getPreEmitDiagnostics(program),
28+
...emitted.diagnostics,
29+
];
30+
31+
let numWarnings = 0;
32+
33+
for (const diagnostic of diagnostics) {
34+
numWarnings++;
35+
36+
const startPosition = ts.getLineAndCharacterOfPosition(
37+
diagnostic.file,
38+
diagnostic.start
39+
);
40+
const endPosition = ts.getLineAndCharacterOfPosition(
41+
diagnostic.file,
42+
diagnostic.start
43+
);
44+
const flattened = ts.flattenDiagnosticMessageText(
45+
diagnostic.messageText,
46+
" ",
47+
0
48+
);
49+
50+
createAnnotation({
51+
type: "warning",
52+
file: diagnostic.file.fileName,
53+
title: "Type warning - may indicate a bug - ignore if no bug",
54+
message: flattened,
55+
line: startPosition.line + 1,
56+
col: startPosition.character + 1,
57+
endLine: endPosition.line + 1,
58+
endCol: endPosition.character + 1,
59+
});
60+
}
61+
62+
console.log(`${numWarnings} warnings.`);
63+
};
64+
65+
check();

development/validate.js

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import Builder from "./builder.js";
2+
import { createAnnotation, isCI } from "./ci-commands.js";
23
import * as Colors from "./colors.js";
34

45
const builder = new Builder("production");
@@ -15,10 +16,23 @@ if (errors.length === 0) {
1516
errors.length === 1 ? "file" : "files"
1617
} failed validation.${Colors.RESET}`
1718
);
19+
1820
console.error("");
21+
1922
for (const { fileName, error } of errors) {
2023
console.error(`${Colors.BOLD}${fileName}${Colors.RESET}: ${error}`);
24+
25+
if (isCI()) {
26+
const nameWithoutLeadingSlash = fileName.replace(/^\//, "");
27+
createAnnotation({
28+
type: "error",
29+
file: nameWithoutLeadingSlash,
30+
title: "Validation error",
31+
message: error,
32+
});
33+
}
2134
}
22-
console.error(``);
35+
36+
console.error("");
2337
process.exit(1);
2438
}

globals.d.ts

Lines changed: 34 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -5,15 +5,15 @@
55

66
interface Element {
77
/**
8-
* requestFullscreen() but available in Safari.
9-
*/
8+
* requestFullscreen() but available in Safari.
9+
*/
1010
webkitRequestFullscreen?(): unknown;
1111
}
1212

1313
interface Document {
1414
/**
15-
* exitFullscreen() but available in Safari.
16-
*/
15+
* exitFullscreen() but available in Safari.
16+
*/
1717
webkitExitFullscreen?(): unknown;
1818
/**
1919
* fullscreenElement but available in Safari.
@@ -26,25 +26,35 @@ interface Document {
2626
*/
2727
declare class NDEFReader extends EventTarget {
2828
constructor();
29-
scan(options?: {signal?: AbortSignal}): Promise<void>;
30-
onreading?(event: Event & {message: NDEFMessage}): void;
29+
scan(options?: { signal?: AbortSignal }): Promise<void>;
30+
onreading?(event: Event & { message: NDEFMessage }): void;
3131
onreadingerror?(event: Event): void;
3232
}
3333

34-
type TypedArray = Uint8Array | Int8Array | Uint16Array | Int16Array | Uint32Array | Int32Array | BigUint64Array | BigInt64Array;
34+
type TypedArray =
35+
| Uint8Array
36+
| Int8Array
37+
| Uint16Array
38+
| Int16Array
39+
| Uint32Array
40+
| Int32Array
41+
| BigUint64Array
42+
| BigInt64Array;
3543

3644
/**
3745
* https://developer.mozilla.org/en-US/docs/Web/API/NDEFMessage/NDEFMessage
3846
*/
3947
declare class NDEFMessage {
40-
constructor(records: Array<{
41-
data?: string | ArrayBuffer | TypedArray | DataView | NDEFRecord[],
42-
encoding?: string;
43-
id?: string;
44-
lang?: string;
45-
mediaType?: string;
46-
recordType?: string;
47-
}>);
48+
constructor(
49+
records: Array<{
50+
data?: string | ArrayBuffer | TypedArray | DataView | NDEFRecord[];
51+
encoding?: string;
52+
id?: string;
53+
lang?: string;
54+
mediaType?: string;
55+
recordType?: string;
56+
}>
57+
);
4858
readonly records: NDEFRecord[];
4959
}
5060

@@ -68,7 +78,15 @@ interface NetworkInformation {
6878
effectiveType: string;
6979
rtt: number;
7080
saveData: boolean;
71-
type: 'bluetooth' | 'cellular' | 'ethernet' | 'none' | 'wifi' | 'wimax' | 'other' | 'unknown';
81+
type:
82+
| "bluetooth"
83+
| "cellular"
84+
| "ethernet"
85+
| "none"
86+
| "wifi"
87+
| "wimax"
88+
| "other"
89+
| "unknown";
7290
}
7391

7492
interface Navigator {

images/CST1229/zip.svg

Lines changed: 1 addition & 1 deletion
Loading

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@
1616
"check-format": "prettier . --check",
1717
"upload-translations": "node development/upload-translations.js",
1818
"download-translations": "node development/download-translations.js",
19-
"check-types": "tsc"
19+
"generate-type-warnings": "node development/generate-type-warnings.js"
2020
},
2121
"repository": {
2222
"type": "git",

0 commit comments

Comments
 (0)