fix: show error messages when oh-my-opencode.json config fails to load (#242)
* fix: show error messages when oh-my-opencode.json config fails to load - Add console.error output for config parse errors (syntax errors) - Add console.error output for config validation errors (schema violations) - Display helpful hints for JSON syntax errors - List all validation errors clearly with proper formatting - Errors now shown immediately regardless of hook configuration Fixes #241 * refactor: replace console.error with toast notifications for config errors - Replace console.error with ctx.client.tui.showToast() for better UX - Show toast notifications for both syntax errors and validation errors - Toast notifications persist for 10 seconds for visibility - Display error details with bullet points for validation errors - Include helpful hints for JSON syntax errors This provides a more user-friendly notification system that integrates with OpenCode's UI instead of just logging to console. --------- Co-authored-by: sisyphus-dev-ai <sisyphus-dev-ai@users.noreply.github.com>
This commit is contained in:
37
src/index.ts
37
src/index.ts
@@ -116,7 +116,7 @@ function migrateConfigFile(configPath: string, rawConfig: Record<string, unknown
|
||||
return needsWrite;
|
||||
}
|
||||
|
||||
function loadConfigFromPath(configPath: string): OhMyOpenCodeConfig | null {
|
||||
function loadConfigFromPath(configPath: string, ctx: any): OhMyOpenCodeConfig | null {
|
||||
try {
|
||||
if (fs.existsSync(configPath)) {
|
||||
const content = fs.readFileSync(configPath, "utf-8");
|
||||
@@ -130,6 +130,20 @@ function loadConfigFromPath(configPath: string): OhMyOpenCodeConfig | null {
|
||||
const errorMsg = result.error.issues.map(i => `${i.path.join(".")}: ${i.message}`).join(", ");
|
||||
log(`Config validation error in ${configPath}:`, result.error.issues);
|
||||
addConfigLoadError({ path: configPath, error: `Validation error: ${errorMsg}` });
|
||||
|
||||
const errorList = result.error.issues
|
||||
.map(issue => `• ${issue.path.join(".")}: ${issue.message}`)
|
||||
.join("\n");
|
||||
|
||||
ctx.client.tui.showToast({
|
||||
body: {
|
||||
title: "❌ OhMyOpenCode: Config Validation Failed",
|
||||
message: `Failed to load ${configPath}\n\nValidation errors:\n${errorList}\n\nConfig will be ignored. Please fix the errors above.`,
|
||||
variant: "error" as const,
|
||||
duration: 10000,
|
||||
},
|
||||
}).catch(() => {});
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
@@ -140,6 +154,19 @@ function loadConfigFromPath(configPath: string): OhMyOpenCodeConfig | null {
|
||||
const errorMsg = err instanceof Error ? err.message : String(err);
|
||||
log(`Error loading config from ${configPath}:`, err);
|
||||
addConfigLoadError({ path: configPath, error: errorMsg });
|
||||
|
||||
const hint = err instanceof SyntaxError
|
||||
? "\n\nHint: Check for syntax errors in your JSON file (missing commas, quotes, brackets, etc.)"
|
||||
: "";
|
||||
|
||||
ctx.client.tui.showToast({
|
||||
body: {
|
||||
title: "❌ OhMyOpenCode: Config Load Failed",
|
||||
message: `Failed to load ${configPath}\n\nError: ${errorMsg}${hint}\n\nConfig will be ignored. Please fix the error above.`,
|
||||
variant: "error" as const,
|
||||
duration: 10000,
|
||||
},
|
||||
}).catch(() => {});
|
||||
}
|
||||
return null;
|
||||
}
|
||||
@@ -174,7 +201,7 @@ function mergeConfigs(
|
||||
};
|
||||
}
|
||||
|
||||
function loadPluginConfig(directory: string): OhMyOpenCodeConfig {
|
||||
function loadPluginConfig(directory: string, ctx: any): OhMyOpenCodeConfig {
|
||||
// User-level config path (OS-specific)
|
||||
const userConfigPath = path.join(
|
||||
getUserConfigDir(),
|
||||
@@ -190,10 +217,10 @@ function loadPluginConfig(directory: string): OhMyOpenCodeConfig {
|
||||
);
|
||||
|
||||
// Load user config first (base)
|
||||
let config: OhMyOpenCodeConfig = loadConfigFromPath(userConfigPath) ?? {};
|
||||
let config: OhMyOpenCodeConfig = loadConfigFromPath(userConfigPath, ctx) ?? {};
|
||||
|
||||
// Override with project config
|
||||
const projectConfig = loadConfigFromPath(projectConfigPath);
|
||||
const projectConfig = loadConfigFromPath(projectConfigPath, ctx);
|
||||
if (projectConfig) {
|
||||
config = mergeConfigs(config, projectConfig);
|
||||
}
|
||||
@@ -209,7 +236,7 @@ function loadPluginConfig(directory: string): OhMyOpenCodeConfig {
|
||||
}
|
||||
|
||||
const OhMyOpenCodePlugin: Plugin = async (ctx) => {
|
||||
const pluginConfig = loadPluginConfig(ctx.directory);
|
||||
const pluginConfig = loadPluginConfig(ctx.directory, ctx);
|
||||
const disabledHooks = new Set(pluginConfig.disabled_hooks ?? []);
|
||||
const isHookEnabled = (hookName: HookName) => !disabledHooks.has(hookName);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user