Fix issue with macstats on mac
This commit is contained in:
@@ -1,9 +1,9 @@
|
|||||||
import { NextResponse } from 'next/server';
|
import { NextResponse } from 'next/server';
|
||||||
import si from 'systeminformation';
|
import si from 'systeminformation';
|
||||||
import { createRequire } from 'module';
|
|
||||||
import os from 'os';
|
import os from 'os';
|
||||||
import { CpuInfo } from '@/types';
|
import { CpuInfo } from '@/types';
|
||||||
import { cached } from '@/server/apiCache';
|
import { cached } from '@/server/apiCache';
|
||||||
|
import { loadMacstats } from '@/server/macstats';
|
||||||
|
|
||||||
const isMac = os.platform() === 'darwin';
|
const isMac = os.platform() === 'darwin';
|
||||||
|
|
||||||
@@ -13,8 +13,8 @@ async function getCpuInfo(): Promise<CpuInfo> {
|
|||||||
|
|
||||||
if (isMac) {
|
if (isMac) {
|
||||||
try {
|
try {
|
||||||
const nativeRequire = createRequire(import.meta.url);
|
const ms = loadMacstats();
|
||||||
const ms = nativeRequire('macstats') as any;
|
if (!ms) throw new Error('macstats unavailable');
|
||||||
const ramData = ms.getRAMUsageSync();
|
const ramData = ms.getRAMUsageSync();
|
||||||
const cpuData = ms.getCpuDataSync();
|
const cpuData = ms.getCpuDataSync();
|
||||||
|
|
||||||
|
|||||||
@@ -1,9 +1,9 @@
|
|||||||
import { NextResponse } from 'next/server';
|
import { NextResponse } from 'next/server';
|
||||||
import { exec } from 'child_process';
|
import { exec } from 'child_process';
|
||||||
import { promisify } from 'util';
|
import { promisify } from 'util';
|
||||||
import { createRequire } from 'module';
|
|
||||||
import os from 'os';
|
import os from 'os';
|
||||||
import { cached } from '@/server/apiCache';
|
import { cached } from '@/server/apiCache';
|
||||||
|
import { loadMacstats } from '@/server/macstats';
|
||||||
|
|
||||||
const execAsync = promisify(exec);
|
const execAsync = promisify(exec);
|
||||||
|
|
||||||
@@ -47,11 +47,8 @@ async function getMacGpuInfo(): Promise<MacGpuResult | null> {
|
|||||||
let memUsed = 0;
|
let memUsed = 0;
|
||||||
let memTotal = memoryTotal;
|
let memTotal = memoryTotal;
|
||||||
|
|
||||||
try {
|
const ms = loadMacstats();
|
||||||
// Use createRequire to hide from webpack static analysis so it doesn't fail on non-mac platforms
|
if (ms) {
|
||||||
const nativeRequire = createRequire(import.meta.url);
|
|
||||||
const ms = nativeRequire('macstats') as any;
|
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const gpuData = ms.getGpuDataSync();
|
const gpuData = ms.getGpuDataSync();
|
||||||
temperature = gpuData.temperature || 0;
|
temperature = gpuData.temperature || 0;
|
||||||
@@ -84,8 +81,6 @@ async function getMacGpuInfo(): Promise<MacGpuResult | null> {
|
|||||||
} catch {
|
} catch {
|
||||||
// ignore
|
// ignore
|
||||||
}
|
}
|
||||||
} catch (error) {
|
|
||||||
console.warn('macstats not available:', error);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return { name: gpuName, memUsed, memTotal, gpuLoad, temperature, fanSpeed, powerDraw };
|
return { name: gpuName, memUsed, memTotal, gpuLoad, temperature, fanSpeed, powerDraw };
|
||||||
|
|||||||
38
ui/src/server/macstats.ts
Normal file
38
ui/src/server/macstats.ts
Normal file
@@ -0,0 +1,38 @@
|
|||||||
|
import * as nodeModule from 'module';
|
||||||
|
import os from 'os';
|
||||||
|
import path from 'path';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* macstats is a native, macOS-only optional dependency.
|
||||||
|
*
|
||||||
|
* It must not be bundled. Webpack special-cases `createRequire(...)`: with a literal base it
|
||||||
|
* resolves and inlines the module (a hard MODULE_NOT_FOUND throw when it can't), and with a
|
||||||
|
* computed base it replaces the whole call with `void 0` — both leave macstats unreachable at
|
||||||
|
* runtime even when it is installed, regardless of serverExternalPackages/externals. So look
|
||||||
|
* createRequire up dynamically, where the bundler can't recognize it, and base the require on
|
||||||
|
* process.cwd() (the ui/ directory the Next server runs in) so it resolves against
|
||||||
|
* ui/node_modules at runtime.
|
||||||
|
*/
|
||||||
|
|
||||||
|
// undefined = not tried yet, null = unavailable on this machine
|
||||||
|
let cachedModule: any | null | undefined;
|
||||||
|
|
||||||
|
export function loadMacstats(): any | null {
|
||||||
|
if (cachedModule !== undefined) return cachedModule;
|
||||||
|
|
||||||
|
if (os.platform() !== 'darwin') {
|
||||||
|
cachedModule = null;
|
||||||
|
return cachedModule;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
const createRequire = (nodeModule as any)['create' + 'Require'] as typeof nodeModule.createRequire;
|
||||||
|
const nativeRequire = createRequire(path.join(process.cwd(), 'package.json'));
|
||||||
|
cachedModule = nativeRequire('macstats');
|
||||||
|
} catch (error) {
|
||||||
|
console.warn('macstats not available:', error);
|
||||||
|
cachedModule = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
return cachedModule;
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user