Skip to content

Commit

Permalink
chore(ChangeReporter): fix getEnumReport not reporting changes to m…
Browse files Browse the repository at this point in the history
…anually found enums
  • Loading branch information
ryan-0324 committed Aug 26, 2024
1 parent 8f64b43 commit 398cba4
Show file tree
Hide file tree
Showing 12 changed files with 60 additions and 53 deletions.
2 changes: 2 additions & 0 deletions .github/workflows/change-reporter.yml
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ jobs:
env:
CHANNEL: stable
CHROMIUM_BIN: ${{ steps.setup-chrome.outputs.chrome-path }}
CHROMIUM_VERSION: ${{ steps.setup-chrome.outputs.chrome-version }}
DISCORD_TOKEN: ${{ secrets.DISCORD_TOKEN }}
DISCORD_WEBHOOK: ${{ secrets.DISCORD_WEBHOOK }}
VENCORD_DIST: ../../dist/browser.js
Expand All @@ -61,6 +62,7 @@ jobs:
env:
CHANNEL: canary
CHROMIUM_BIN: ${{ steps.setup-chrome.outputs.chrome-path }}
CHROMIUM_VERSION: ${{ steps.setup-chrome.outputs.chrome-version }}
DISCORD_TOKEN: ${{ secrets.DISCORD_TOKEN }}
DISCORD_WEBHOOK: ${{ secrets.DISCORD_WEBHOOK }}
VENCORD_DIST: ../../dist/browser.js
13 changes: 5 additions & 8 deletions packages/discord-types/scripts/changeReporter/finds/classes.mts
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
import type * as Vencord from "../../../../../src/Vencord.ts";
import type { CR } from "../types.mts";

export function autoFindStore(this: typeof Vencord, name: string, source: CR.ClassMembers) {
export function autoFindStore(this: typeof Vencord, source: CR.ClassMembers, name: string) {
const persistKeyRE = new RegExp(`^${name}(?:V\\d+)?$`);

const store: { constructor: CR.Class; } | undefined = this.Webpack.find(exp => {
Expand All @@ -21,7 +21,7 @@ export function autoFindStore(this: typeof Vencord, name: string, source: CR.Cla
});

if (store)
return getClassChanges(store.constructor, source);
return getClassChanges(source, store.constructor);
}

export function autoFindClass(this: typeof Vencord, source: CR.ClassMembers) {
Expand Down Expand Up @@ -49,7 +49,7 @@ export function autoFindClass(this: typeof Vencord, source: CR.ClassMembers) {
if (!checked.has(constructor)) {
checked.add(constructor);

const changes = getClassChanges(constructor, source);
const changes = getClassChanges(source, constructor);
const { changedCount } = changes;
if (changedCount < lowestChangedCount) {
lowestChangedCount = changedCount;
Expand All @@ -72,12 +72,9 @@ export function isValidClass(value: unknown): value is CR.Class {
}

export function getClassChanges(
constructors: [CR.Class, ...CR.Class[]] | CR.Class,
source: CR.ClassMembers
source: CR.ClassMembers,
...constructors: [CR.Class, ...CR.Class[]]
): CR.ClassChanges {
if (!Array.isArray(constructors))
constructors = [constructors];

let hasConstructorDefinition = false;

const constructorKeys = new Set<PropertyKey>();
Expand Down
4 changes: 2 additions & 2 deletions packages/discord-types/scripts/changeReporter/finds/enums.mts
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ export function autoFindEnum(this: typeof Vencord, source: CR.EnumSource) {
if (isValidEnum(exp) && !checked.has(exp)) {
checked.add(exp);

const changes = getEnumChanges(exp, source);
const changes = getEnumChanges(source, exp);
const { changedCount } = changes;
if (
changedCount < lowestChangedCount
Expand All @@ -53,7 +53,7 @@ export function isValidEnum(value: unknown): value is CR.EnumMembers {
&& !Array.isArray(value);
}

export function getEnumChanges(obj: CR.EnumMembers, source: CR.EnumSource): CR.EnumChanges {
export function getEnumChanges(source: CR.EnumSource, obj: CR.EnumMembers): CR.EnumChanges {
const additions: CR.EnumMembers = {};
const removals: CR.EnumMembers = { ...source };
let unchangedCount = 0;
Expand Down
5 changes: 3 additions & 2 deletions packages/discord-types/scripts/changeReporter/index.mts
Original file line number Diff line number Diff line change
Expand Up @@ -26,12 +26,13 @@ process.on("uncaughtExceptionMonitor", error => {
assertEnvValidity(process.env, {
CHANNEL: ["stable", "ptb", "canary"],
CHROMIUM_BIN: true,
CHROMIUM_VERSION: /^\d+(?:\.|$)/,
DISCORD_TOKEN: true,
DISCORD_WEBHOOK: false,
VENCORD_DIST: true,
});

const { CHANNEL, CHROMIUM_BIN, DISCORD_TOKEN, DISCORD_WEBHOOK, VENCORD_DIST } = process.env;
const { CHANNEL, CHROMIUM_BIN, CHROMIUM_VERSION, DISCORD_TOKEN, DISCORD_WEBHOOK, VENCORD_DIST } = process.env;
const CWD = process.cwd();

const browser = await puppeteer.launch({
Expand All @@ -41,7 +42,7 @@ const browser = await puppeteer.launch({
});

const page = await browser.newPage();
await page.setUserAgent("Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36");
await page.setUserAgent(`Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/${CHROMIUM_VERSION.split(".", 1)[0]}.0.0.0 Safari/537.36`);
await page.setBypassCSP(true);

await page.evaluateOnNewDocument(`(() => {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,12 @@

import console from "node:console";
import { writeFile } from "node:fs/promises";
import process from "node:process";

import type { CR } from "../types.mts";
import { capitalize, codeBlock, formatChannel, formatEnumEntryList, formatKeyList, formatWarnList } from "./utils.mjs";

export function logSummary(report: CR.ChangeReport, channel?: string | undefined) {
export function logSummary(report: CR.ChangeReport, channel?: string) {
const { deps, src } = report;

let summary = `# Change Report (${formatChannel(channel)})\n`;
Expand Down
31 changes: 19 additions & 12 deletions packages/discord-types/scripts/changeReporter/logging/utils.mts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@
* SPDX-License-Identifier: GPL-3.0-or-later
*/

import process from "node:process";

export function capitalize(string: string) {
return string.replace(/^./, c => c.toUpperCase());
}
Expand All @@ -13,29 +15,32 @@ export function codeBlock(content?: unknown, indentLevel = 0) {
return `\`\`\`\n${content}\n\`\`\``.replaceAll(/^/gm, indent) + "\n";
}

export function formatWarnList(warns: string[], indentLevel = 0) {
export function formatWarnList(warns: readonly string[], indentLevel = 0) {
return warns.reduce((list, warn) => list + codeBlock(warn, indentLevel), "");
}

export function formatKeyList(keys: string[], indentLevel = 0) {
export function formatKeyList(keys: readonly string[], indentLevel = 0) {
const indent = " ".repeat(indentLevel);
return keys.reduce((list, key) => list + indent + `* \`${key}\`\n`, "");
}

export function formatValue(value?: unknown) {
if (typeof value === "string")
return JSON.stringify(value);
if (typeof value === "bigint")
return value.toString() + "n";
return String(value);
switch (typeof value) {
case "string":
return JSON.stringify(value);
case "bigint":
return value + "n";
default:
return String(value);
}
}

export function formatEnumEntryList(entries: [key: string, value: unknown][], indentLevel = 0) {
export function formatEnumEntryList(entries: readonly (readonly [key: string, value: unknown])[], indentLevel = 0) {
const indent = " ".repeat(indentLevel);
return entries.reduce((list, [key, value]) => list + indent + `* \`${key} = ${formatValue(value)}\`\n`, "");
}

export function formatChannel(channel?: string | undefined) {
export function formatChannel(channel?: string) {
switch (channel) {
case "stable":
case "canary":
Expand All @@ -47,9 +52,11 @@ export function formatChannel(channel?: string | undefined) {
}
}

export function getSummaryURL(channel?: string | undefined) {
export function getSummaryURL(channel?: string) {
const { GITHUB_SERVER_URL, GITHUB_REPOSITORY, GITHUB_RUN_ID, GITHUB_RUN_ATTEMPT } = process.env;
if (GITHUB_SERVER_URL && GITHUB_REPOSITORY && GITHUB_RUN_ID && GITHUB_RUN_ATTEMPT)
return `${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}/attempts/${GITHUB_RUN_ATTEMPT}`
+ `#:~:text=Change%20Report%20%28${formatChannel(channel)}%29`;
return encodeURI(
`${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}/attempts/${GITHUB_RUN_ATTEMPT}`
+ `#:~:text=Change Report (${formatChannel(channel)})`
);
}
12 changes: 2 additions & 10 deletions packages/discord-types/scripts/changeReporter/logging/webhooks.mts
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,7 @@ import console from "node:console";
import type { CR } from "../types.mts";
import { codeBlock, formatChannel, getSummaryURL } from "./utils.mjs";

export async function postError(
error: Error,
webhookURL: string | undefined,
channel?: string | undefined
) {
export async function postError(error: Error, webhookURL?: string, channel?: string) {
if (!webhookURL) return;

const res = await fetch(webhookURL, {
Expand All @@ -34,11 +30,7 @@ export async function postError(
console.error(`Failed to exectute webhook (status '${res.status} ${res.statusText}').`);
}

export async function postReport(
report: CR.ChangeReport,
webhookURL: string,
channel?: string | undefined
) {
export async function postReport(report: CR.ChangeReport, webhookURL: string, channel?: string) {
const { deps, src } = report;

let areChanges = false;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,8 @@ export async function getClassReport(
try {
const changes = await page.evaluate<[CR.ClassMembers], CR.FindFunction<[CR.ClassMembers], CR.ClassChanges>>(
pageAsyncFunction("s", `const c = await ${funcToString(find)}.call(Vencord, s);`
+ "if (Array.isArray(c) ? c.length > 0 && c.every(isValidClass) : isValidClass(c))"
+ "return getClassChanges(c, s);"),
+ "if (Array.isArray(c)) { if (c.length > 0 && c.every(isValidClass)) return getClassChanges(s, ...c); }"
+ "else if (isValidClass(c)) return getClassChanges(s, c);"),
source
);
if (changes) {
Expand All @@ -52,9 +52,9 @@ export async function getClassReport(
if (/Store$/.test(name) && !declaration.abstract) {
try {
const changes = await page.evaluate<Parameters<typeof autoFindStore>, typeof autoFindStore>(
pageFunction("n", "s", "return autoFindStore(n, s);"),
name,
source
pageFunction("s", "n", "return autoFindStore(s, n);"),
source,
name
);
if (changes) {
checkClassIgnores(changes, config, report);
Expand Down Expand Up @@ -94,7 +94,7 @@ export async function getClassReport(
}

function getClassMembers(
members: TSESTree.ClassElement[],
members: readonly TSESTree.ClassElement[],
config: CR.ClassConfig,
report: CR.ClassReport
): CR.ClassMembers {
Expand Down Expand Up @@ -230,14 +230,14 @@ function getClassMemberName(
}

/** Adds ignored additions so as to not affect `changedCount`. */
function applyClassIgnoredAdditions(members: Set<string>, ignored?: string[] | undefined) {
function applyClassIgnoredAdditions(members: Set<string>, ignored?: string[]) {
if (ignored)
for (const key of ignored)
members.add(key);
}

/** Removes ignored removals so as to not affect `changedCount`. */
function applyClassIgnoredRemovals(members: Set<string>, ignored?: string[] | boolean | undefined) {
function applyClassIgnoredRemovals(members: Set<string>, ignored?: string[] | boolean) {
if (Array.isArray(ignored)) {
for (const key of ignored)
members.delete(key);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ export async function getEnumReport(
try {
const changes = await page.evaluate<[CR.EnumSource], CR.FindFunction<[CR.EnumSource], CR.EnumChanges>>(
pageAsyncFunction("s", `const o = await ${funcToString(find)}.call(Vencord, s);`
+ "if (isValidEnum(o)) return getEnumChanges(o);"),
+ "if (isValidEnum(o)) return getEnumChanges(s, o);"),
source
);
if (changes) {
Expand All @@ -50,7 +50,7 @@ export async function getEnumReport(

try {
const changes = await page.evaluate<Parameters<typeof autoFindEnum>, typeof autoFindEnum>(
pageFunction("o", "return autoFindEnum(o);"),
pageFunction("s", "return autoFindEnum(s);"),
source
);
if (changes) {
Expand All @@ -69,7 +69,7 @@ export async function getEnumReport(
}

function getEnumMembers(
members: TSESTree.TSEnumMember[],
members: readonly TSESTree.TSEnumMember[],
config: CR.EnumConfig,
report: CR.EnumReport
) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ export function pageFunction(...args: [string, ...string[]]): any {
return new Function(...args, `"use strict";${body}`);
}

// https://github.com/microsoft/TypeScript/issues/36177
const AsyncFunction: any = async function () {}.constructor;

export function pageAsyncFunction(...args: [string, ...string[]]): any {
Expand Down
16 changes: 11 additions & 5 deletions packages/discord-types/scripts/utils.mts
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,16 @@
* SPDX-License-Identifier: GPL-3.0-or-later
*/

type EnvConfig = Record<string, boolean | [string, ...string[]]>;
type EnvConfig = Record<string, RegExp | [string, ...string[]] | [...string[], string] | boolean>;

type ValidEnv<Config extends EnvConfig> = NodeJS.ProcessEnv & {
[Key in keyof Config as false extends Config[Key] ? never : Key]: Config[Key] extends string[]
[Key in keyof Config as false extends Config[Key]
? never
: Key
]: Config[Key] extends string[]
? Config[Key][number]
: string;
} & { [Key in keyof Config as false extends Config[Key] ? Key : never]?: string; };
} & Partial<Record<keyof Config, string>>;

export function assertEnvValidity<const Config extends EnvConfig>(
env: NodeJS.ProcessEnv,
Expand All @@ -25,8 +28,11 @@ export function assertEnvValidity<const Config extends EnvConfig>(
if (varValue === undefined) {
if (varConfig)
errors.push(`TypeError: A value must be provided for required environment variable '${key}'.`);
} else if (Array.isArray(varConfig) && !varConfig.includes(varValue))
errors.push(`RangeError: The value provided for environment variable '${key}' must be one of ${formatChoices(varConfig)}.`);
} else if (Array.isArray(varConfig)) {
if (!varConfig.includes(varValue))
errors.push(`RangeError: The value provided for environment variable '${key}' must be one of ${formatChoices(varConfig)}.`);
} else if (typeof varConfig === "object" && !varConfig.test(varValue))
errors.push(`RangeError: The value provided for environment variable '${key}' must match ${varConfig}.`);
}

if (errors.length > 0) {
Expand Down
4 changes: 2 additions & 2 deletions packages/discord-types/src/flux/FluxBatchedStoreListener.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@ import type { FluxStore } from "../stores/abstract/FluxStore";
export declare class FluxBatchedStoreListener {
constructor(stores: FluxStore[], changeCallback: () => void);

attatch(debugName?: Stringable): void;
detatch(): void;
attach(debugName?: Stringable): void;
detach(): void;

changeCallback: () => void;
handleStoreChange: () => void;
Expand Down

0 comments on commit 398cba4

Please sign in to comment.