Project Files
src / config.ts
import { createConfigSchematics, type InferParsedConfig } from "@lmstudio/sdk";
export function getAutoDetectedShellPath(): string {
if (process.platform === "win32") {
try {
const { execSync } = require("child_process");
execSync("pwsh -Command 'Write-Output \"OK\"'", { stdio: ["pipe", "pipe", "ignore"], timeout: 1000 });
return "pwsh";
} catch {
try {
const powershellPath = process.env.SystemRoot + "\\System32\\WindowsPowerShell\\v1.0\\powershell.exe";
if (require("fs").existsSync(powershellPath)) return powershellPath;
} catch {}
}
} else {
const envShell = process.env.SHELL?.trim();
if (envShell && require("fs").existsSync(envShell)) return envShell;
for (const sh of ["/bin/zsh", "/bin/bash", "/bin/sh"]) {
try {
if (require("fs").existsSync(sh)) return sh;
} catch {}
}
}
return "";
}
export const configSchematics = createConfigSchematics()
.field(
"shellPath",
"string",
{
displayName: "Shell Path (optional)",
subtitle:
"Override the default shell. Leave empty to auto-detect. " +
"Windows: uses pwsh.exe (PowerShell 7) if available, then powershell.exe or cmd.exe. " +
"macOS/Linux: honours $SHELL env var, then zsh > bash > sh.",
placeholder: "Leave empty for auto-detection",
},
getAutoDetectedShellPath(),
)
.field(
"windowsShell",
"select",
{
displayName: "Windows Shell",
subtitle:
"Shell used for exec on Windows. " +
"PowerShell 7 (pwsh) is recommended — it supports modern syntax, pipelines, and UTF-8 natively. " +
"Falls back to powershell.exe if pwsh is not installed.",
options: [
{ value: "powershell", displayName: "PowerShell 7 / pwsh (recommended)" },
{ value: "cmd", displayName: "Command Prompt (cmd.exe)" },
],
},
"powershell",
)
.field(
"pythonPath",
"string",
{
displayName: "Python Executable (optional)",
subtitle:
"Override the Python binary used by run_script. " +
"Leave empty to auto-detect. " +
"Windows examples: python, py, C:\\Users\\you\\AppData\\Local\\Programs\\Python\\Python312\\python.exe",
placeholder: "Leave empty for auto-detection",
},
"",
)
.field(
"defaultCwd",
"string",
{
displayName: "Default Working Directory (optional)",
subtitle:
"Default directory for exec and run_script when cwd is not specified. " +
"Leave empty to use the home directory. Supports ~ and %ENVVAR% expansion.",
placeholder: "Leave empty for home directory",
},
"",
)
.field(
"maxOutputSize",
"numeric",
{
displayName: "Maximum Output Size (bytes)",
subtitle:
"Maximum size of output to return from exec commands. " +
"Larger outputs will be truncated with an indicator.",
hint: "Default: 10MB",
},
10 * 1024 * 1024,
)
.build();
export type ParsedConfig = InferParsedConfig<typeof configSchematics>;
// --- Validation helpers ---
/**
* Normalise and clamp numeric config values.
* Returns `null` when the value is out of acceptable bounds.
*/
export function clampNumeric(
value: number | undefined,
min: number,
max: number,
fallback: number,
): number {
if (value == null || !Number.isFinite(value)) return fallback;
if (value < min) return min;
if (value > max) return max;
return Math.trunc(value);
}
/**
* Validate `defaultCwd` exists on disk (lazily, at runtime).
*/
export function validateDefaultCwd(cwd: string | undefined): string {
if (!cwd || cwd.trim() === "") return "";
const fs = require("fs");
const expanded = cwd.replace(/^~/, require("os").homedir());
if (!fs.existsSync(expanded)) return ""; // will be resolved at runtime
return expanded;
}
/**
* Validate `windowsShell` value.
*/
export function validateWindowsShell(value: string | undefined): "powershell" | "cmd" {
if (value === "cmd") return "cmd";
return "powershell";
}