Skip to content
This repository was archived by the owner on Mar 25, 2026. It is now read-only.

Commit 3af732b

Browse files
committed
fix(linux): use HAK build system for venmic to support cross-compilation
Move venmic native addon handling from copy-res.ts (which checks process.platform) to the HAK build system (which checks target platform). This allows building Linux packages from Windows or macOS hosts.
1 parent d1a81c6 commit 3af732b

File tree

6 files changed

+96
-30
lines changed

6 files changed

+96
-30
lines changed

hak/@vencord/venmic/build.ts

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
/*
2+
Copyright 2025 New Vector Ltd.
3+
4+
SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial
5+
Please see LICENSE files in the repository root for full details.
6+
*/
7+
8+
import path from "node:path";
9+
import fsProm from "node:fs/promises";
10+
11+
import type HakEnv from "../../../scripts/hak/hakEnv.js";
12+
import type { DependencyInfo } from "../../../scripts/hak/dep.js";
13+
14+
export default async function (hakEnv: HakEnv, moduleInfo: DependencyInfo): Promise<void> {
15+
// venmic is Linux-only
16+
if (!hakEnv.isLinux()) {
17+
console.log("Skipping venmic build: not targeting Linux");
18+
return;
19+
}
20+
21+
const arch = hakEnv.getTargetArch();
22+
23+
// venmic only has x64 and arm64 prebuilds
24+
if (arch !== "x64" && arch !== "arm64") {
25+
console.log(`Skipping venmic build: no prebuild for architecture ${arch}`);
26+
return;
27+
}
28+
29+
const venmicSource = path.join(
30+
hakEnv.projectRoot,
31+
"node_modules",
32+
"@vencord",
33+
"venmic",
34+
"prebuilds",
35+
`venmic-addon-linux-${arch}`,
36+
"node-napi-v7.node",
37+
);
38+
39+
// Check if venmic is installed (it's optional)
40+
try {
41+
await fsProm.access(venmicSource);
42+
} catch {
43+
console.log("venmic prebuilds not found, skipping (optional dependency)");
44+
return;
45+
}
46+
47+
// Ensure build directory exists
48+
await fsProm.mkdir(moduleInfo.moduleBuildDir, { recursive: true });
49+
50+
// Copy prebuild to build dir
51+
const dest = path.join(moduleInfo.moduleBuildDir, "venmic.node");
52+
await fsProm.copyFile(venmicSource, dest);
53+
console.log(`Copied venmic ${arch} prebuild to ${dest}`);
54+
}

hak/@vencord/venmic/check.ts

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
/*
2+
Copyright 2025 New Vector Ltd.
3+
4+
SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial
5+
Please see LICENSE files in the repository root for full details.
6+
*/
7+
8+
import type HakEnv from "../../../scripts/hak/hakEnv.js";
9+
import type { DependencyInfo } from "../../../scripts/hak/dep.js";
10+
11+
export default async function (hakEnv: HakEnv, moduleInfo: DependencyInfo): Promise<void> {
12+
// venmic is Linux-only
13+
if (!hakEnv.isLinux()) {
14+
console.log(`Skipping venmic: only supported on Linux (target: ${hakEnv.getTargetId()})`);
15+
return;
16+
}
17+
18+
// venmic only provides x64 and arm64 prebuilds
19+
const arch = hakEnv.getTargetArch();
20+
if (arch !== "x64" && arch !== "arm64") {
21+
throw new Error(`venmic does not provide prebuilds for architecture: ${arch}`);
22+
}
23+
}

hak/@vencord/venmic/hak.json

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
{
2+
"scripts": {
3+
"check": "check.ts",
4+
"build": "build.ts"
5+
},
6+
"copy": "venmic.node"
7+
}

package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -116,7 +116,8 @@
116116
"@vencord/venmic": "^6.1.0"
117117
},
118118
"hakDependencies": {
119-
"matrix-seshat": "^4.0.1"
119+
"matrix-seshat": "^4.0.1",
120+
"@vencord/venmic": "^6.1.0"
120121
},
121122
"resolutions": {
122123
"atomically": "2.1.1",

scripts/copy-res.ts

Lines changed: 0 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -79,26 +79,3 @@ INCLUDE_LANGS.forEach((file): void => {
7979
if (watch) {
8080
INCLUDE_LANGS.forEach((file) => watchLanguage(I18N_BASE_PATH + file, I18N_DEST));
8181
}
82-
83-
// Copy venmic native addon for Linux audio sharing
84-
// Only copy on Linux since venmic is Linux-only
85-
if (process.platform === "linux") {
86-
const venmicSource = path.join(
87-
"node_modules",
88-
"@vencord",
89-
"venmic",
90-
"prebuilds",
91-
`venmic-addon-linux-${process.arch}`,
92-
"node-napi-v7.node",
93-
);
94-
95-
if (fs.existsSync(venmicSource)) {
96-
const venmicDest = path.join("lib", `venmic-${process.arch}.node`);
97-
fs.copyFileSync(venmicSource, venmicDest);
98-
if (verbose) {
99-
console.log(`Copied venmic native addon to ${venmicDest}`);
100-
}
101-
} else if (verbose) {
102-
console.log("venmic native addon not found, skipping (optional dependency)");
103-
}
104-
}

src/venmic.ts

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -7,16 +7,15 @@ Please see LICENSE files in the repository root for full details.
77

88
import { app, ipcMain } from "electron";
99
import { createRequire } from "node:module";
10-
import { dirname, join } from "node:path";
11-
import { fileURLToPath } from "node:url";
10+
import { join } from "node:path";
11+
import { existsSync } from "node:fs";
1212

1313
import type { LinkData, Node, PatchBay as PatchBayType } from "@vencord/venmic";
1414

1515
import type { VenmicListResult } from "./@types/audio-sharing.js";
1616

1717
export type { VenmicListResult };
1818

19-
const __dirname = dirname(fileURLToPath(import.meta.url));
2019
const nativeRequire = createRequire(import.meta.url);
2120

2221
let PatchBay: typeof PatchBayType | undefined;
@@ -36,9 +35,14 @@ function importVenmic(): void {
3635
imported = true;
3736

3837
try {
39-
// Load the native .node file directly from lib/ where it's copied
40-
// during build. This follows the same approach used by Vesktop.
41-
const nativePath = join(__dirname, `venmic-${process.arch}.node`);
38+
// Load the native .node file from the HAK output.
39+
// In development: .hak/hakModules/@vencord/venmic/venmic.node
40+
// When packaged: node_modules/@vencord/venmic/venmic.node (electron-builder copies hakModules there)
41+
const appPath = app.getAppPath();
42+
const hakPath = join(appPath, ".hak", "hakModules", "@vencord", "venmic", "venmic.node");
43+
const packagedPath = join(appPath, "node_modules", "@vencord", "venmic", "venmic.node");
44+
45+
const nativePath = existsSync(hakPath) ? hakPath : packagedPath;
4246
PatchBay = (nativeRequire(nativePath) as { PatchBay: typeof PatchBayType }).PatchBay;
4347
hasPipewirePulse = PatchBay.hasPipeWire();
4448
} catch (e: unknown) {

0 commit comments

Comments
 (0)