Skip to content

Commit cba001d

Browse files
committed
[test-627] added test cases for os.helpers.ts
1 parent 38ea360 commit cba001d

File tree

3 files changed

+209
-1
lines changed

3 files changed

+209
-1
lines changed

src/__tests__/unit/os.test.ts

+203
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,203 @@
1+
import {
2+
bsmSpawn,
3+
// bsmExec,
4+
isProcessRunning,
5+
// getProcessId,
6+
} from "main/helpers/os.helpers";
7+
8+
import cp from "child_process";
9+
import crypto from "crypto";
10+
import log from "electron-log";
11+
import { ifDescribe, ifIt } from "__tests__/utils";
12+
import { BS_APP_ID } from "main/constants";
13+
14+
Object.defineProperty(global, "crypto", {
15+
value: {
16+
randomUUID: () => crypto.webcrypto.randomUUID(),
17+
}
18+
});
19+
jest.mock("electron", () => ({
20+
app: { getPath: () => "" },
21+
}));
22+
jest.mock("electron-log", () => ({
23+
info: jest.fn(),
24+
error: jest.fn(),
25+
}));
26+
jest.mock("ps-list", () => () => []);
27+
28+
const IS_WINDOWS = process.platform === "win32";
29+
const IS_LINUX = process.platform === "linux";
30+
31+
describe("Test os.helpers bsmSpawn", () => {
32+
const spawnSpy: jest.SpyInstance = jest.spyOn(cp, "spawn")
33+
.mockImplementation();
34+
const logSpy: jest.SpyInstance = jest.spyOn(log, "info");
35+
const originalContainer = process.env.container;
36+
37+
const BS_ENV = {
38+
SteamAppId: BS_APP_ID,
39+
SteamOverlayGameId: BS_APP_ID,
40+
SteamGameId: BS_APP_ID,
41+
};
42+
43+
beforeAll(() => {
44+
if (IS_LINUX) {
45+
Object.assign(BS_ENV, {
46+
WINEDLLOVERRIDES: "winhttp=n,b",
47+
STEAM_COMPAT_DATA_PATH: "/compatdata",
48+
STEAM_COMPAT_INSTALL_PATH: "/BSInstance",
49+
STEAM_COMPAT_CLIENT_INSTALL_PATH: "/steam",
50+
STEAM_COMPAT_APP_ID: BS_APP_ID,
51+
SteamEnv: "1",
52+
});
53+
}
54+
});
55+
56+
afterAll(() => {
57+
spawnSpy.mockRestore();
58+
});
59+
60+
afterEach(() => {
61+
spawnSpy.mockClear();
62+
logSpy.mockClear();
63+
process.env.container = originalContainer;
64+
});
65+
66+
it("Simple spawn command", () => {
67+
bsmSpawn("cd", {
68+
args: ["folder1", "folder2"],
69+
});
70+
expect(spawnSpy).toHaveBeenCalledTimes(1);
71+
expect(spawnSpy).toHaveBeenCalledWith("cd folder1 folder2", expect.anything());
72+
73+
expect(logSpy).toHaveBeenCalledTimes(0);
74+
});
75+
76+
it("Simple spawn command with logging", () => {
77+
bsmSpawn("mkdir", {
78+
args: ["new_folder"],
79+
log: true,
80+
});
81+
expect(spawnSpy).toHaveBeenCalledTimes(1);
82+
expect(spawnSpy).toHaveBeenCalledWith("mkdir new_folder", expect.anything());
83+
84+
expect(logSpy).toHaveBeenCalledTimes(1);
85+
});
86+
87+
it("Complex spawn command call (Mods install)", () => {
88+
bsmSpawn(`"./BSIPA.exe" "./Beat Saber.exe" -n`, {
89+
log: true,
90+
linux: { prefix: `"./wine64"` },
91+
});
92+
93+
expect(spawnSpy).toHaveBeenCalledTimes(1);
94+
expect(spawnSpy).toHaveBeenCalledWith(
95+
process.platform === "win32"
96+
? `"./BSIPA.exe" "./Beat Saber.exe" -n`
97+
: `"./wine64" "./BSIPA.exe" "./Beat Saber.exe" -n`,
98+
expect.anything()
99+
);
100+
101+
expect(logSpy).toHaveBeenCalledTimes(1);
102+
});
103+
104+
it("Complex spawn command call (BS launch)", () => {
105+
bsmSpawn(`"./Beat Saber.exe"`, {
106+
args: ["--no-yeet", "fpfc"],
107+
options: {
108+
cwd: "/",
109+
detached: true,
110+
env: BS_ENV,
111+
},
112+
log: true,
113+
linux: { prefix: `"./proton" run` },
114+
});
115+
116+
expect(spawnSpy).toHaveBeenCalledTimes(1);
117+
expect(spawnSpy).toHaveBeenCalledWith(
118+
IS_WINDOWS
119+
? `"./Beat Saber.exe" --no-yeet fpfc`
120+
: `"./proton" run "./Beat Saber.exe" --no-yeet fpfc`,
121+
expect.objectContaining({
122+
cwd: "/",
123+
detached: true,
124+
env: BS_ENV,
125+
})
126+
);
127+
128+
expect(logSpy).toHaveBeenCalledTimes(1);
129+
});
130+
131+
ifIt(IS_LINUX)("Complex spawn command call (BS launch flatpak)", () => {
132+
const flatpakEnv = [
133+
"SteamAppId",
134+
"SteamOverlayGameId",
135+
"SteamGameId",
136+
"WINEDLLOVERRIDES",
137+
"STEAM_COMPAT_DATA_PATH",
138+
"STEAM_COMPAT_INSTALL_PATH",
139+
"STEAM_COMPAT_CLIENT_INSTALL_PATH",
140+
"STEAM_COMPAT_APP_ID",
141+
"SteamEnv"
142+
];
143+
const newEnv = {
144+
...BS_ENV,
145+
something: "else",
146+
more: "tests",
147+
};
148+
bsmSpawn(`"./Beat Saber.exe"`, {
149+
args: ["--no-yeet", "fpfc"],
150+
options: {
151+
cwd: "/",
152+
detached: true,
153+
env: newEnv,
154+
},
155+
log: true,
156+
linux: { prefix: `"./proton" run` },
157+
flatpak: {
158+
host: true,
159+
env: flatpakEnv,
160+
},
161+
});
162+
163+
expect(spawnSpy).toHaveBeenCalledTimes(1);
164+
const envArgs = flatpakEnv.map(argName =>
165+
`--env=${argName}="${(BS_ENV as any)[argName]}"`
166+
).join(" ");
167+
expect(spawnSpy).toHaveBeenCalledWith(
168+
`flatpak-spawn --host ${envArgs} "./proton" run "./Beat Saber.exe" --no-yeet fpfc`,
169+
expect.objectContaining({
170+
cwd: "/",
171+
detached: true,
172+
env: newEnv,
173+
})
174+
);
175+
176+
expect(logSpy).toHaveBeenCalledTimes(1);
177+
});
178+
});
179+
180+
ifDescribe(IS_LINUX)("Test os.helpers isProcessRunning", () => {
181+
const logSpy: jest.SpyInstance = jest.spyOn(log, "error");
182+
afterEach(() => {
183+
logSpy.mockClear();
184+
});
185+
186+
it("Process is running", async () => {
187+
// There will always a node process running
188+
const running = await isProcessRunning("node");
189+
expect(running).toBe(true);
190+
191+
// No errors received
192+
expect(logSpy).toHaveBeenCalledTimes(0);
193+
});
194+
195+
it("Process is not running", async () => {
196+
const running = await isProcessRunning(`bs-manager-${crypto.randomUUID()}`);
197+
expect(running).toBe(false);
198+
199+
// No errors received
200+
expect(logSpy).toHaveBeenCalledTimes(0);
201+
});
202+
});
203+

src/__tests__/utils.ts

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
2+
export const ifDescribe = (condition: boolean) => condition ? describe : describe.skip;
3+
4+
export const ifIt = (condition: boolean) => condition ? it : it.skip;
5+

src/main/helpers/os.helpers.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,7 @@ export function bsmExec(command: string, options?: BsmExecOptions): Promise<{
9898
if (error) { return reject(error); }
9999
resolve({ stdout, stderr });
100100
});
101-
})
101+
});
102102
}
103103

104104
async function isProcessRunningLinux(name: string): Promise<boolean> {

0 commit comments

Comments
 (0)