Merge branch 'dev' into stickercopy

This commit is contained in:
byeoon 2025-02-18 13:32:01 -05:00 committed by GitHub
commit eab586ae9a
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
27 changed files with 777 additions and 1221 deletions

View file

@ -2,30 +2,24 @@ name: Blank Issue
description: Create a blank issue. ALWAYS FIRST USE OUR SUPPORT CHANNEL! ONLY USE THIS FORM IF YOU ARE A CONTRIBUTOR OR WERE TOLD TO DO SO IN THE SUPPORT CHANNEL.
body:
- type: markdown
attributes:
value: |
# READ THIS BEFORE OPENING AN ISSUE
- type: markdown
attributes:
value: |
![Are you a developer? No? This form is not for you!](https://github.com/Vendicated/Vencord/blob/main/.github/ISSUE_TEMPLATE/developer-banner.png?raw=true)
This form is ONLY FOR DEVELOPERS. YOUR ISSUE WILL BE CLOSED AND YOU WILL POSSIBLY BE BLOCKED FROM THE REPOSITORY IF YOU IGNORE THIS.
DO NOT USE THIS FORM, unless
- you are a vencord contributor
- you were given explicit permission to use this form by a moderator in our support server
DO NOT USE THIS FORM FOR SECURITY RELATED ISSUES. [CREATE A SECURITY ADVISORY INSTEAD.](https://github.com/Vendicated/Vencord/security/advisories/new)
GitHub Issues are for development, not support! Please use our [support server](https://vencord.dev/discord) unless you are a Vencord Developer.
- type: textarea
id: content
attributes:
label: Content
validations:
required: true
- type: checkboxes
id: agreement-check
attributes:
label: Request Agreement
options:
- label: I have read the requirements for opening an issue above
- type: textarea
id: content
attributes:
label: Content
validations:
required: true
- type: checkboxes
id: agreement-check
attributes:
label: Request Agreement
options:
- label: I have read the requirements for opening an issue above
required: true

View file

@ -4,78 +4,63 @@ labels: [bug]
title: "[Bug] <title>"
body:
- type: markdown
attributes:
value: |
# READ THIS BEFORE OPENING AN ISSUE
- type: markdown
attributes:
value: |
![Are you a developer? No? This form is not for you!](https://github.com/Vendicated/Vencord/blob/main/.github/ISSUE_TEMPLATE/developer-banner.png?raw=true)
This form is ONLY FOR DEVELOPERS. YOUR ISSUE WILL BE CLOSED AND YOU WILL POSSIBLY BE BLOCKED FROM THE REPOSITORY IF YOU IGNORE THIS.
DO NOT USE THIS FORM, unless
- you are a vencord contributor
- you were given explicit permission to use this form by a moderator in our support server
DO NOT USE THIS FORM FOR SECURITY RELATED ISSUES. [CREATE A SECURITY ADVISORY INSTEAD.](https://github.com/Vendicated/Vencord/security/advisories/new)
- type: input
id: discord
attributes:
label: Discord Account
description: Who on Discord is making this request? Not required but encouraged for easier follow-up
placeholder: username#0000
validations:
required: false
GitHub Issues are for development, not support! Please use our [support server](https://vencord.dev/discord) unless you are a Vencord Developer.
- type: textarea
id: bug-description
attributes:
label: What happens when the bug or crash occurs?
description: Where does this bug or crash occur, when does it occur, etc.
placeholder: The bug/crash happens sometimes when I do ..., causing this to not work/the app to crash. I think it happens because of ...
validations:
required: true
- type: textarea
id: expected-behaviour
attributes:
label: What is the expected behaviour?
description: Simply detail what the expected behaviour is.
placeholder: I expect Vencord/Discord to open the ... page instead of ..., it prevents me from doing ...
validations:
required: true
- type: textarea
id: steps-to-take
attributes:
label: How do you recreate this bug or crash?
description: Give us a list of steps in order to recreate the bug or crash.
placeholder: |
1. Do ...
2. Then ...
3. Do this ..., ... and then ...
4. Observe "the bug" or "the crash"
validations:
required: true
- type: textarea
id: crash-log
attributes:
label: Errors
description: Open the Developer Console with Ctrl/Cmd + Shift + i. Then look for any red errors (Ignore network errors like Failed to load resource) and paste them between the "```".
value: |
```
Replace this text with your crash-log.
```
validations:
required: false
- type: checkboxes
id: agreement-check
attributes:
label: Request Agreement
description: We only accept reports for bugs that happen on Discord Stable. Canary and PTB are Development branches and may be unstable
options:
- label: I am using Discord Stable or tried on Stable and this bug happens there as well
- type: textarea
id: bug-description
attributes:
label: What happens when the bug or crash occurs?
description: Where does this bug or crash occur, when does it occur, etc.
placeholder: The bug/crash happens sometimes when I do ..., causing this to not work/the app to crash. I think it happens because of ...
validations:
required: true
- label: I have read the requirements for opening an issue above
- type: textarea
id: expected-behaviour
attributes:
label: What is the expected behaviour?
description: Simply detail what the expected behaviour is.
placeholder: I expect Vencord/Discord to open the ... page instead of ..., it prevents me from doing ...
validations:
required: true
- type: textarea
id: steps-to-take
attributes:
label: How do you recreate this bug or crash?
description: Give us a list of steps in order to recreate the bug or crash.
placeholder: |
1. Do ...
2. Then ...
3. Do this ..., ... and then ...
4. Observe "the bug" or "the crash"
validations:
required: true
- type: textarea
id: crash-log
attributes:
label: Errors
description: Open the Developer Console with Ctrl/Cmd + Shift + i. Then look for any red errors (Ignore network errors like Failed to load resource) and paste them between the "```".
value: |
```
Replace this text with your crash-log.
```
validations:
required: false
- type: checkboxes
id: agreement-check
attributes:
label: Request Agreement
description: We only accept reports for bugs that happen on Discord Stable. Canary and PTB are Development branches and may be unstable
options:
- label: I am using Discord Stable or tried on Stable and this bug happens there as well
required: true
- label: I am a Vencord Developer
required: true

Binary file not shown.

After

Width:  |  Height:  |  Size: 31 KiB

View file

@ -42,7 +42,7 @@ jobs:
- name: Clean up obsolete files
run: |
rm -rf dist/*-unpacked dist/monaco Vencord.user.css vencordDesktopRenderer.css vencordDesktopRenderer.css.map
rm -rf dist/*-unpacked dist/vendor Vencord.user.css vencordDesktopRenderer.css vencordDesktopRenderer.css.map
- name: Get some values needed for the release
id: release_values

View file

@ -1,7 +1,7 @@
{
"name": "vencord",
"private": "true",
"version": "1.11.4",
"version": "1.11.5",
"description": "The cutest Discord client mod",
"homepage": "https://github.com/Vendicated/Vencord#readme",
"bugs": {
@ -24,7 +24,7 @@
"dev": "pnpm watch",
"watchWeb": "pnpm buildWeb --watch",
"generatePluginJson": "tsx scripts/generatePluginList.ts",
"generateTypes": "tspc --emitDeclarationOnly --declaration --outDir packages/vencord-types",
"generateTypes": "tspc --emitDeclarationOnly --declaration --outDir packages/vencord-types --allowJs false",
"inject": "node scripts/runInstaller.mjs",
"uninject": "node scripts/runInstaller.mjs",
"lint": "eslint",
@ -45,31 +45,31 @@
"virtual-merge": "^1.0.1"
},
"devDependencies": {
"@stylistic/eslint-plugin": "^2.12.1",
"@types/chrome": "^0.0.287",
"@types/diff": "^6.0.0",
"@stylistic/eslint-plugin": "^4.0.0",
"@types/chrome": "^0.0.304",
"@types/diff": "^7.0.1",
"@types/lodash": "^4.17.14",
"@types/node": "^22.10.5",
"@types/react": "^19.0.2",
"@types/react-dom": "^19.0.2",
"@types/react": "^19.0.10",
"@types/react-dom": "^19.0.4",
"@types/yazl": "^2.4.5",
"diff": "^7.0.0",
"discord-types": "^1.3.26",
"esbuild": "^0.25.0",
"eslint": "^9.17.0",
"eslint": "^9.20.1",
"eslint-import-resolver-alias": "^1.1.2",
"eslint-plugin-path-alias": "2.1.0",
"eslint-plugin-react": "^7.37.3",
"eslint-plugin-simple-header": "^1.2.1",
"eslint-plugin-simple-import-sort": "^12.1.1",
"eslint-plugin-unused-imports": "^4.1.4",
"highlight.js": "11.7.0",
"highlight.js": "11.11.1",
"html-minifier-terser": "^7.2.0",
"moment": "^2.22.2",
"puppeteer-core": "^23.11.1",
"standalone-electron-types": "^1.0.0",
"puppeteer-core": "^24.2.1",
"standalone-electron-types": "^34.2.0",
"stylelint": "^16.12.0",
"stylelint-config-standard": "^36.0.1",
"stylelint-config-standard": "^37.0.0",
"ts-patch": "^3.3.0",
"ts-pattern": "^5.6.0",
"tsx": "^4.19.2",
@ -82,7 +82,7 @@
"packageManager": "pnpm@9.1.0",
"pnpm": {
"patchedDependencies": {
"eslint@9.17.0": "patches/eslint@9.17.0.patch",
"eslint@9.20.1": "patches/eslint@9.20.1.patch",
"eslint-plugin-path-alias@2.1.0": "patches/eslint-plugin-path-alias@2.1.0.patch"
},
"peerDependencyRules": {

View file

@ -1,7 +1,7 @@
{
"name": "@vencord/types",
"private": false,
"version": "0.1.3",
"version": "1.11.5",
"description": "",
"types": "index.d.ts",
"scripts": {
@ -13,16 +13,16 @@
"license": "GPL-3.0",
"devDependencies": {
"@types/fs-extra": "^11.0.4",
"fs-extra": "^11.2.0",
"tsx": "^3.12.6"
"fs-extra": "^11.3.0",
"tsx": "^4.19.2"
},
"dependencies": {
"@types/lodash": "^4.14.191",
"@types/node": "^18.11.18",
"@types/react": "^18.2.0",
"@types/react-dom": "^18.0.10",
"@types/lodash": "4.17.15",
"@types/node": "^22.13.4",
"@types/react": "18.3.1",
"@types/react-dom": "18.3.1",
"discord-types": "^1.3.26",
"standalone-electron-types": "^1.0.0",
"type-fest": "^3.5.3"
"standalone-electron-types": "^34.2.0",
"type-fest": "^4.35.0"
}
}

1588
pnpm-lock.yaml generated

File diff suppressed because it is too large Load diff

View file

@ -4,11 +4,11 @@
* SPDX-License-Identifier: GPL-3.0-or-later
*/
import type { Settings } from "@api/Settings";
import { PluginIpcMappings } from "@main/ipcPlugins";
import type { UserThemeHeader } from "@main/themes";
import { IpcEvents } from "@shared/IpcEvents";
import { IpcRes } from "@utils/types";
import type { Settings } from "api/Settings";
import { ipcRenderer } from "electron";
function invoke<T = any>(event: IpcEvents, ...args: any[]) {

View file

@ -78,9 +78,9 @@ async function runReporter() {
result = await Webpack.extractAndLoadChunks(code, matcher);
if (result === false) result = null;
} else if (method === "mapMangledModule") {
const [code, mapper] = args;
const [code, mapper, includeBlacklistedExports] = args;
result = Webpack.mapMangledModule(code, mapper);
result = Webpack.mapMangledModule(code, mapper, includeBlacklistedExports);
if (Object.keys(result).length !== Object.keys(mapper).length) throw new Error("Webpack Find Fail");
} else {
// @ts-ignore

View file

@ -158,6 +158,9 @@ export default definePlugin({
aboveActivity: getIntlMessage("ACTIVITY_SETTINGS")
};
if (!names[settingsLocation] || names[settingsLocation].endsWith("_SETTINGS"))
return firstChild === "PREMIUM";
return header === names[settingsLocation];
} catch {
return firstChild === "PREMIUM";

View file

@ -5,7 +5,7 @@
*/
import { CopyIcon, DeleteIcon } from "@components/Icons";
import { Alerts, Clipboard, ContextMenuApi, Menu, UserStore } from "webpack/common";
import { Alerts, Clipboard, ContextMenuApi, Menu, UserStore } from "@webpack/common";
import { Decoration } from "../../lib/api";
import { useCurrentUserDecorationsStore } from "../../lib/stores/CurrentUserDecorationsStore";

View file

@ -9,7 +9,7 @@ import { app } from "electron";
app.on("browser-window-created", (_, win) => {
win.webContents.on("frame-created", (_, { frame }) => {
frame.once("dom-ready", () => {
frame?.once("dom-ready", () => {
if (frame.url.startsWith("https://open.spotify.com/embed/")) {
const settings = RendererSettings.store.plugins?.FixSpotifyEmbeds;
if (!settings?.enabled) return;

View file

@ -9,7 +9,7 @@ import { app } from "electron";
app.on("browser-window-created", (_, win) => {
win.webContents.on("frame-created", (_, { frame }) => {
frame.once("dom-ready", () => {
frame?.once("dom-ready", () => {
if (frame.url.startsWith("https://www.youtube.com/")) {
const settings = RendererSettings.store.plugins?.FixYoutubeEmbeds;
if (!settings?.enabled) return;

View file

@ -12,7 +12,7 @@ import { Devs } from "@utils/constants";
import { Margins } from "@utils/margins";
import definePlugin, { OptionType } from "@utils/types";
import { findStoreLazy } from "@webpack";
import { Button, Forms, showToast, TextInput, Toasts, Tooltip, useEffect, useState } from "webpack/common";
import { Button, Forms, showToast, TextInput, Toasts, Tooltip, useEffect, useState } from "@webpack/common";
const enum ActivitiesTypes {
Game,

View file

@ -96,6 +96,6 @@
.vc-shiki-root .vc-shiki-table-cell:last-child {
padding-left: 8px;
word-break: break-word;
overflow-wrap: break-word;
width: 100%;
}

View file

@ -77,7 +77,7 @@ export const SpotifyStore = proxyLazyWebpack(() => {
class SpotifyStore extends Store {
public mPosition = 0;
private start = 0;
public _start = 0;
public track: Track | null = null;
public device: Device | null = null;
@ -100,26 +100,26 @@ export const SpotifyStore = proxyLazyWebpack(() => {
public get position(): number {
let pos = this.mPosition;
if (this.isPlaying) {
pos += Date.now() - this.start;
pos += Date.now() - this._start;
}
return pos;
}
public set position(p: number) {
this.mPosition = p;
this.start = Date.now();
this._start = Date.now();
}
prev() {
this.req("post", "/previous");
this._req("post", "/previous");
}
next() {
this.req("post", "/next");
this._req("post", "/next");
}
setVolume(percent: number) {
this.req("put", "/volume", {
this._req("put", "/volume", {
query: {
volume_percent: Math.round(percent)
}
@ -131,17 +131,17 @@ export const SpotifyStore = proxyLazyWebpack(() => {
}
setPlaying(playing: boolean) {
this.req("put", playing ? "/play" : "/pause");
this._req("put", playing ? "/play" : "/pause");
}
setRepeat(state: Repeat) {
this.req("put", "/repeat", {
this._req("put", "/repeat", {
query: { state }
});
}
setShuffle(state: boolean) {
this.req("put", "/shuffle", {
this._req("put", "/shuffle", {
query: { state }
}).then(() => {
this.shuffle = state;
@ -154,7 +154,7 @@ export const SpotifyStore = proxyLazyWebpack(() => {
this.isSettingPosition = true;
return this.req("put", "/seek", {
return this._req("put", "/seek", {
query: {
position_ms: Math.round(ms)
}
@ -164,7 +164,7 @@ export const SpotifyStore = proxyLazyWebpack(() => {
});
}
private req(method: "post" | "get" | "put", route: string, data: any = {}) {
_req(method: "post" | "get" | "put", route: string, data: any = {}) {
if (this.device?.is_active)
(data.query ??= {}).device_id = this.device.id;

View file

@ -128,7 +128,7 @@ function VoiceChannelTooltip({ channel, isLocked }: VoiceChannelTooltipProps) {
);
}
interface VoiceChannelIndicatorProps {
export interface VoiceChannelIndicatorProps {
userId: string;
isActionButton?: boolean;
shouldHighlight?: boolean;

View file

@ -10,7 +10,7 @@ import adguard from "file://adguard.js?minify";
app.on("browser-window-created", (_, win) => {
win.webContents.on("frame-created", (_, { frame }) => {
frame.once("dom-ready", () => {
frame?.once("dom-ready", () => {
if (!RendererSettings.store.plugins?.YoutubeAdblock?.enabled) return;
if (frame.url.includes("youtube.com/embed/") || (frame.url.includes("discordsays") && frame.url.includes("youtube.com"))) {

View file

@ -17,7 +17,6 @@
@media(width <= 485px) {
.vc-image-modal {
display: relative;
overflow: visible;
overflow: initial;
}

View file

@ -29,7 +29,7 @@ export type GenericStore = t.FluxStore & Record<string, any>;
export const DraftType = findByPropsLazy("ChannelMessage", "SlashCommand");
export let MessageStore: Omit<Stores.MessageStore, "getMessages"> & {
export let MessageStore: Omit<Stores.MessageStore, "getMessages"> & GenericStore & {
getMessages(chanId: string): any;
};

View file

@ -496,7 +496,7 @@ export type Avatar = ComponentType<PropsWithChildren<{
}>>;
type FocusLock = ComponentType<PropsWithChildren<{
containerRef: RefObject<HTMLElement>;
containerRef: Ref<HTMLElement>;
}>>;
export type Icon = ComponentType<JSX.IntrinsicElements["svg"] & {

View file

@ -16,7 +16,6 @@
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
import { DraftType } from "@webpack/common";
import { Channel, Guild, Role } from "discord-types/general";
import { FluxDispatcher, FluxEvents } from "./utils";
@ -229,7 +228,7 @@ export class ThemeStore extends FluxStore {
}
export type useStateFromStores = <T>(
stores: t.FluxStore[],
stores: any[],
mapper: () => T,
dependencies?: any,
isEqual?: (old: T, newer: T) => boolean

View file

@ -58,9 +58,9 @@ export const { match, P }: Pick<typeof import("ts-pattern"), "match" | "P"> = ma
export const lodash: typeof import("lodash") = findByPropsLazy("debounce", "cloneDeep");
export const i18n = mapMangledModuleLazy('defaultLocale:"en-US"', {
t: filters.byProps(runtimeHashMessageKey("DISCORD")),
intl: filters.byProps("string", "format"),
t: filters.byProps(runtimeHashMessageKey("DISCORD"))
});
}, true);
export let SnowflakeUtils: t.SnowflakeUtils;
waitFor(["fromTimestamp", "extractTimestamp"], m => SnowflakeUtils = m);

View file

@ -12,7 +12,7 @@ import { canonicalizeReplacement } from "@utils/patches";
import { Patch, PatchReplacement } from "@utils/types";
import { traceFunctionWithResults } from "../debug/Tracer";
import { _initWebpack, _shouldIgnoreModule, factoryListeners, findModuleId, moduleListeners, waitForSubscriptions, wreq } from "./webpack";
import { _blacklistBadModules, _initWebpack, factoryListeners, findModuleId, moduleListeners, waitForSubscriptions, wreq } from "./webpack";
import { AnyModuleFactory, AnyWebpackRequire, MaybePatchedModuleFactory, ModuleExports, PatchedModuleFactory, WebpackRequire } from "./wreq.d";
export const patches = [] as Patch[];
@ -190,6 +190,20 @@ define(Function.prototype, "m", {
*/
define(this, "m", { value: proxiedModuleFactories });
// Overwrite Webpack's defineExports function to define the export descriptors configurable.
// This is needed so we can later blacklist specific exports from Webpack search by making them non-enumerable
this.d = function (exports, definition) {
for (const key in definition) {
if (Object.hasOwn(definition, key) && !Object.hasOwn(exports, key)) {
Object.defineProperty(exports, key, {
enumerable: true,
configurable: true,
get: definition[key],
});
}
}
};
};
}
});
@ -403,27 +417,17 @@ function runFactoryWithWrap(patchedFactory: PatchedModuleFactory, thisArg: unkno
}
exports = module.exports;
if (exports == null) {
return factoryReturn;
}
if (typeof require === "function") {
const shouldIgnoreModule = _shouldIgnoreModule(exports);
if (shouldIgnoreModule) {
if (require.c != null) {
Object.defineProperty(require.c, module.id, {
value: require.c[module.id],
enumerable: false,
configurable: true,
writable: true
});
}
if (typeof require === "function" && require.c) {
if (_blacklistBadModules(require.c, exports, module.id)) {
return factoryReturn;
}
}
if (exports == null) {
return factoryReturn;
}
for (const callback of moduleListeners) {
try {
callback(exports, module.id);

View file

@ -22,7 +22,8 @@ import { Logger } from "@utils/Logger";
import { canonicalizeMatch } from "@utils/patches";
import { traceFunction } from "../debug/Tracer";
import { AnyModuleFactory, ModuleExports, WebpackRequire } from "./wreq";
import { Flux } from "./common";
import { AnyModuleFactory, AnyWebpackRequire, ModuleExports, WebpackRequire } from "./wreq";
const logger = new Logger("Webpack");
@ -111,18 +112,38 @@ export function _initWebpack(webpackRequire: WebpackRequire) {
// Credits to Zerebos for implementing this in BD, thus giving the idea for us to implement it too
const TypedArray = Object.getPrototypeOf(Int8Array);
function _shouldIgnoreValue(value: any) {
const PROXY_CHECK = "is this a proxy that returns values for any key?";
function shouldIgnoreValue(value: any) {
if (value == null) return true;
if (value === window) return true;
if (value === document || value === document.documentElement) return true;
if (value[Symbol.toStringTag] === "DOMTokenList") return true;
if (value[Symbol.toStringTag] === "DOMTokenList" || value[Symbol.toStringTag] === "IntlMessagesProxy") return true;
// Discord might export a Proxy that returns non-null values for any property key which would pass all findByProps filters.
// One example of this is their i18n Proxy. However, that is already covered by the IntlMessagesProxy check above.
// As a fallback if they ever change the name or add a new Proxy, use a unique string to detect such proxies and ignore them
if (value[PROXY_CHECK] !== void 0) {
// their i18n Proxy "caches" by setting each accessed property to the return, so try to delete
Reflect.deleteProperty(value, PROXY_CHECK);
return true;
}
if (value instanceof TypedArray) return true;
return false;
}
export function _shouldIgnoreModule(exports: any) {
if (_shouldIgnoreValue(exports)) {
function makePropertyNonEnumerable(target: Record<PropertyKey, any>, key: PropertyKey) {
const descriptor = Object.getOwnPropertyDescriptor(target, key);
if (descriptor == null) return;
Reflect.defineProperty(target, key, {
...descriptor,
enumerable: false
});
}
export function _blacklistBadModules(requireCache: NonNullable<AnyWebpackRequire["c"]>, exports: ModuleExports, moduleId: PropertyKey) {
if (shouldIgnoreValue(exports)) {
makePropertyNonEnumerable(requireCache, moduleId);
return true;
}
@ -130,14 +151,16 @@ export function _shouldIgnoreModule(exports: any) {
return false;
}
let allNonEnumerable = true;
let hasOnlyBadProperties = true;
for (const exportKey in exports) {
if (!_shouldIgnoreValue(exports[exportKey])) {
allNonEnumerable = false;
if (shouldIgnoreValue(exports[exportKey])) {
makePropertyNonEnumerable(exports, exportKey);
} else {
hasOnlyBadProperties = false;
}
}
return allNonEnumerable;
return hasOnlyBadProperties;
}
let devToolsOpen = false;
@ -405,7 +428,10 @@ export function findByCodeLazy(...code: CodeFilter) {
* Find a store by its displayName
*/
export function findStore(name: StoreNameFilter) {
const res = find(filters.byStoreName(name), { isIndirect: true });
const res = Flux.Store.getAll
? Flux.Store.getAll().find(filters.byStoreName(name))
: find(filters.byStoreName(name), { isIndirect: true });
if (!res)
handleModuleNotFound("findStore", name);
return res;
@ -473,12 +499,27 @@ export function findExportedComponentLazy<T extends object = any>(...props: Prop
});
}
function getAllPropertyNames(object: Record<PropertyKey, any>, includeNonEnumerable: boolean) {
const names = new Set<PropertyKey>();
const getKeys = includeNonEnumerable ? Object.getOwnPropertyNames : Object.keys;
do {
getKeys(object).forEach(name => names.add(name));
object = Object.getPrototypeOf(object);
} while (object != null);
return names;
}
/**
* Finds a mangled module by the provided code "code" (must be unique and can be anywhere in the module)
* then maps it into an easily usable module via the specified mappers.
*
* @param code The code to look for
* @param mappers Mappers to create the non mangled exports
* @param includeBlacklistedExports Whether to include blacklisted exports in the search.
* These exports are dangerous. Accessing properties on them may throw errors
* or always return values (so a byProps filter will always return true)
* @returns Unmangled exports as specified in mappers
*
* @example mapMangledModule("headerIdIsManaged:", {
@ -486,7 +527,7 @@ export function findExportedComponentLazy<T extends object = any>(...props: Prop
* closeModal: filters.byCode("key==")
* })
*/
export const mapMangledModule = traceFunction("mapMangledModule", function mapMangledModule<S extends string>(code: string | RegExp | CodeFilter, mappers: Record<S, FilterFn>): Record<S, any> {
export const mapMangledModule = traceFunction("mapMangledModule", function mapMangledModule<S extends string>(code: string | RegExp | CodeFilter, mappers: Record<S, FilterFn>, includeBlacklistedExports = false): Record<S, any> {
const exports = {} as Record<S, any>;
const id = findModuleId(...Array.isArray(code) ? code : [code]);
@ -494,8 +535,9 @@ export const mapMangledModule = traceFunction("mapMangledModule", function mapMa
return exports;
const mod = wreq(id as any);
const keys = getAllPropertyNames(mod, includeBlacklistedExports);
outer:
for (const key in mod) {
for (const key of keys) {
const member = mod[key];
for (const newName in mappers) {
// if the current mapper matches this module
@ -509,24 +551,13 @@ export const mapMangledModule = traceFunction("mapMangledModule", function mapMa
});
/**
* {@link mapMangledModule}, lazy.
* Finds a mangled module by the provided code "code" (must be unique and can be anywhere in the module)
* then maps it into an easily usable module via the specified mappers.
*
* @param code The code to look for
* @param mappers Mappers to create the non mangled exports
* @returns Unmangled exports as specified in mappers
*
* @example mapMangledModule("headerIdIsManaged:", {
* openModal: filters.byCode("headerIdIsManaged:"),
* closeModal: filters.byCode("key==")
* })
* lazy mapMangledModule
* @see {@link mapMangledModule}
*/
export function mapMangledModuleLazy<S extends string>(code: string | RegExp | CodeFilter, mappers: Record<S, FilterFn>): Record<S, any> {
if (IS_REPORTER) lazyWebpackSearchHistory.push(["mapMangledModule", [code, mappers]]);
export function mapMangledModuleLazy<S extends string>(code: string | RegExp | CodeFilter, mappers: Record<S, FilterFn>, includeBlacklistedExports = false): Record<S, any> {
if (IS_REPORTER) lazyWebpackSearchHistory.push(["mapMangledModule", [code, mappers, includeBlacklistedExports]]);
return proxyLazy(() => mapMangledModule(code, mappers));
return proxyLazy(() => mapMangledModule(code, mappers, includeBlacklistedExports));
}
export const DefaultExtractAndLoadChunksRegex = /(?:(?:Promise\.all\(\[)?(\i\.e\("?[^)]+?"?\)[^\]]*?)(?:\]\))?|Promise\.resolve\(\))\.then\(\i\.bind\(\i,"?([^)]+?)"?\)\)/;

13
src/webpack/wreq.d.ts vendored
View file

@ -17,14 +17,11 @@ export type Module = {
/** exports can be anything, however initially it is always an empty object */
export type ModuleFactory = (this: ModuleExports, module: Module, exports: ModuleExports, require: WebpackRequire) => void;
export type WebpackQueues = unique symbol | "__webpack_queues__";
export type WebpackExports = unique symbol | "__webpack_exports__";
export type WebpackError = unique symbol | "__webpack_error__";
/** Keys here can be symbols too, but we can't properly type them */
export type AsyncModulePromise = Promise<ModuleExports> & {
[WebpackQueues]: (fnQueue: ((queue: any[]) => any)) => any;
[WebpackExports]: ModuleExports;
[WebpackError]?: any;
"__webpack_queues__": (fnQueue: ((queue: any[]) => any)) => any;
"__webpack_exports__": ModuleExports;
"__webpack_error__"?: any;
};
export type AsyncModuleBody = (
@ -152,7 +149,7 @@ export type WebpackRequire = ((moduleId: PropertyKey) => ModuleExports) & {
* }
* // exports is now { exportName: someExportedValue } (but each value is actually a getter)
*/
d: (this: WebpackRequire, exports: AnyRecord, definiton: AnyRecord) => void;
d: (this: WebpackRequire, exports: Record<PropertyKey, any>, definiton: Record<PropertyKey, () => ModuleExports>) => void;
/** The ensure chunk handlers, which are used to ensure the files of the chunks are loaded, or load if necessary */
f: EnsureChunkHandlers;
/**