eaba21329c
* refactor: Clean up hook-response and new-hook files - Removed 'PreCompact' hook type and associated logic from hook-response.ts for improved type safety. - Deleted extensive architecture comments in new-hook.ts to streamline code readability. - Simplified debug logging in new-hook.ts to reduce verbosity. - Enhanced ensureWorkerRunning function in worker-utils.ts with a final health check before throwing errors. - Added a new documentation file outlining the hooks cleanup process and future improvements. * Refactor cleanup and user message hooks - Updated cleanup-hook.js to improve error handling and remove unnecessary input checks. - Simplified user-message-hook.js by removing time-sensitive announcements and streamlining output. - Enhanced logging functionality in both hooks for better debugging and clarity. * Refactor error handling in hooks to use centralized error handler - Introduced `handleWorkerError` function in `src/shared/hook-error-handler.ts` to manage worker-related errors. - Updated `context-hook.ts`, `new-hook.ts`, `save-hook.ts`, and `summary-hook.ts` to utilize the new error handler, simplifying error management and improving code readability. - Removed repetitive error handling logic from individual hooks, ensuring consistent user-friendly messages for connection issues. * Refactor user-message and summary hooks to utilize shared transcript parser; introduce hook exit codes - Moved user message extraction logic to a new shared module `transcript-parser.ts` for better code reuse. - Updated `summary-hook.ts` to use the new `extractLastMessage` function for retrieving user and assistant messages. - Replaced direct exit code usage in `user-message-hook.ts` with constants from `hook-constants.ts` for improved readability and maintainability. - Added `HOOK_EXIT_CODES` to `hook-constants.ts` to standardize exit codes across hooks. * Refactor hook input interfaces to enforce required fields - Updated `SessionStartInput`, `UserPromptSubmitInput`, `PostToolUseInput`, and `StopInput` interfaces to require `session_id`, `transcript_path`, and `cwd` fields, ensuring better type safety and clarity in hook inputs. - Removed optional index signatures from these interfaces to prevent unintended properties and improve code maintainability. - Adjusted related hook implementations to align with the new interface definitions. * Refactor save-hook to remove tool skipping logic; enhance summary-hook to handle spinner stopping with error logging; update SessionRoutes to load skip tools from settings; add CLAUDE_MEM_SKIP_TOOLS to SettingsDefaultsManager for configurable tool exclusion. * Document CLAUDE_MEM_SKIP_TOOLS setting in public docs Added documentation for the new CLAUDE_MEM_SKIP_TOOLS configuration setting in response to PR review feedback. Users can now discover and customize which tools are excluded from observations. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
141 lines
4.6 KiB
TypeScript
141 lines
4.6 KiB
TypeScript
/**
|
|
* SettingsDefaultsManager
|
|
*
|
|
* Single source of truth for all default configuration values.
|
|
* Provides methods to get defaults with optional environment variable overrides.
|
|
*/
|
|
|
|
import { readFileSync, writeFileSync, existsSync } from 'fs';
|
|
import { join } from 'path';
|
|
import { homedir } from 'os';
|
|
import { DEFAULT_OBSERVATION_TYPES_STRING, DEFAULT_OBSERVATION_CONCEPTS_STRING } from '../constants/observation-metadata.js';
|
|
import { logger } from '../utils/logger.js';
|
|
|
|
export interface SettingsDefaults {
|
|
CLAUDE_MEM_MODEL: string;
|
|
CLAUDE_MEM_CONTEXT_OBSERVATIONS: string;
|
|
CLAUDE_MEM_WORKER_PORT: string;
|
|
CLAUDE_MEM_SKIP_TOOLS: string;
|
|
// System Configuration
|
|
CLAUDE_MEM_DATA_DIR: string;
|
|
CLAUDE_MEM_LOG_LEVEL: string;
|
|
CLAUDE_MEM_PYTHON_VERSION: string;
|
|
CLAUDE_CODE_PATH: string;
|
|
// Token Economics
|
|
CLAUDE_MEM_CONTEXT_SHOW_READ_TOKENS: string;
|
|
CLAUDE_MEM_CONTEXT_SHOW_WORK_TOKENS: string;
|
|
CLAUDE_MEM_CONTEXT_SHOW_SAVINGS_AMOUNT: string;
|
|
CLAUDE_MEM_CONTEXT_SHOW_SAVINGS_PERCENT: string;
|
|
// Observation Filtering
|
|
CLAUDE_MEM_CONTEXT_OBSERVATION_TYPES: string;
|
|
CLAUDE_MEM_CONTEXT_OBSERVATION_CONCEPTS: string;
|
|
// Display Configuration
|
|
CLAUDE_MEM_CONTEXT_FULL_COUNT: string;
|
|
CLAUDE_MEM_CONTEXT_FULL_FIELD: string;
|
|
CLAUDE_MEM_CONTEXT_SESSION_COUNT: string;
|
|
// Feature Toggles
|
|
CLAUDE_MEM_CONTEXT_SHOW_LAST_SUMMARY: string;
|
|
CLAUDE_MEM_CONTEXT_SHOW_LAST_MESSAGE: string;
|
|
}
|
|
|
|
export class SettingsDefaultsManager {
|
|
/**
|
|
* Default values for all settings
|
|
*/
|
|
private static readonly DEFAULTS: SettingsDefaults = {
|
|
CLAUDE_MEM_MODEL: 'claude-haiku-4-5',
|
|
CLAUDE_MEM_CONTEXT_OBSERVATIONS: '50',
|
|
CLAUDE_MEM_WORKER_PORT: '37777',
|
|
CLAUDE_MEM_SKIP_TOOLS: 'ListMcpResourcesTool,SlashCommand,Skill,TodoWrite,AskUserQuestion',
|
|
// System Configuration
|
|
CLAUDE_MEM_DATA_DIR: join(homedir(), '.claude-mem'),
|
|
CLAUDE_MEM_LOG_LEVEL: 'INFO',
|
|
CLAUDE_MEM_PYTHON_VERSION: '3.13',
|
|
CLAUDE_CODE_PATH: '', // Empty means auto-detect via 'which claude'
|
|
// Token Economics
|
|
CLAUDE_MEM_CONTEXT_SHOW_READ_TOKENS: 'true',
|
|
CLAUDE_MEM_CONTEXT_SHOW_WORK_TOKENS: 'true',
|
|
CLAUDE_MEM_CONTEXT_SHOW_SAVINGS_AMOUNT: 'true',
|
|
CLAUDE_MEM_CONTEXT_SHOW_SAVINGS_PERCENT: 'true',
|
|
// Observation Filtering
|
|
CLAUDE_MEM_CONTEXT_OBSERVATION_TYPES: DEFAULT_OBSERVATION_TYPES_STRING,
|
|
CLAUDE_MEM_CONTEXT_OBSERVATION_CONCEPTS: DEFAULT_OBSERVATION_CONCEPTS_STRING,
|
|
// Display Configuration
|
|
CLAUDE_MEM_CONTEXT_FULL_COUNT: '5',
|
|
CLAUDE_MEM_CONTEXT_FULL_FIELD: 'narrative',
|
|
CLAUDE_MEM_CONTEXT_SESSION_COUNT: '10',
|
|
// Feature Toggles
|
|
CLAUDE_MEM_CONTEXT_SHOW_LAST_SUMMARY: 'true',
|
|
CLAUDE_MEM_CONTEXT_SHOW_LAST_MESSAGE: 'false',
|
|
};
|
|
|
|
/**
|
|
* Get all defaults as an object
|
|
*/
|
|
static getAllDefaults(): SettingsDefaults {
|
|
return { ...this.DEFAULTS };
|
|
}
|
|
|
|
/**
|
|
* Get a default value from defaults (no environment variable override)
|
|
*/
|
|
static get(key: keyof SettingsDefaults): string {
|
|
return this.DEFAULTS[key];
|
|
}
|
|
|
|
/**
|
|
* Get an integer default value
|
|
*/
|
|
static getInt(key: keyof SettingsDefaults): number {
|
|
const value = this.get(key);
|
|
return parseInt(value, 10);
|
|
}
|
|
|
|
/**
|
|
* Get a boolean default value
|
|
*/
|
|
static getBool(key: keyof SettingsDefaults): boolean {
|
|
const value = this.get(key);
|
|
return value === 'true';
|
|
}
|
|
|
|
/**
|
|
* Load settings from file with fallback to defaults
|
|
* Returns merged settings with defaults as fallback
|
|
*/
|
|
static loadFromFile(settingsPath: string): SettingsDefaults {
|
|
if (!existsSync(settingsPath)) {
|
|
return this.getAllDefaults();
|
|
}
|
|
|
|
const settingsData = readFileSync(settingsPath, 'utf-8');
|
|
const settings = JSON.parse(settingsData);
|
|
|
|
// MIGRATION: Handle old nested schema { env: {...} }
|
|
let flatSettings = settings;
|
|
if (settings.env && typeof settings.env === 'object') {
|
|
// Migrate from nested to flat schema
|
|
flatSettings = settings.env;
|
|
|
|
// Auto-migrate the file to flat schema
|
|
try {
|
|
writeFileSync(settingsPath, JSON.stringify(flatSettings, null, 2), 'utf-8');
|
|
logger.info('SETTINGS', 'Migrated settings file from nested to flat schema', { settingsPath });
|
|
} catch (error) {
|
|
logger.warn('SETTINGS', 'Failed to auto-migrate settings file', { settingsPath }, error);
|
|
// Continue with in-memory migration even if write fails
|
|
}
|
|
}
|
|
|
|
// Merge file settings with defaults (flat schema)
|
|
const result: SettingsDefaults = { ...this.DEFAULTS };
|
|
for (const key of Object.keys(this.DEFAULTS) as Array<keyof SettingsDefaults>) {
|
|
if (flatSettings[key] !== undefined) {
|
|
result[key] = flatSettings[key];
|
|
}
|
|
}
|
|
|
|
return result;
|
|
}
|
|
}
|