12149470a2
- Created comprehensive installation guide detailing quick start, system requirements, and advanced installation steps. - Developed troubleshooting guide addressing common issues with worker service, hooks, database, and search tools. - Introduced getting started documentation explaining automatic operation, session summaries, and context injection. - Added detailed usage instructions for MCP search tools, including query examples and advanced filtering techniques.
9.7 KiB
9.7 KiB
Development Guide
Building from Source
Prerequisites
- Node.js 18.0.0 or higher
- npm (comes with Node.js)
- Git
Clone and Build
# Clone repository
git clone https://github.com/thedotmack/claude-mem.git
cd claude-mem
# Install dependencies
npm install
# Build all components
npm run build
Build Process
The build process uses esbuild to compile TypeScript:
- Compiles TypeScript to JavaScript
- Creates standalone executables for each hook in
plugin/scripts/ - Bundles MCP search server to
plugin/scripts/search-server.js - Bundles worker service to
plugin/scripts/worker-service.cjs
Build Output:
- Hook executables:
*-hook.js(ESM format) - Worker service:
worker-service.cjs(CJS format) - Search server:
search-server.js(ESM format)
Build Scripts
# Build everything
npm run build
# Build only hooks
npm run build:hooks
# The build script is defined in scripts/build-hooks.js
Development Workflow
1. Make Changes
Edit TypeScript source files in src/:
src/
├── bin/hooks/ # Hook entry points
├── hooks/ # Hook implementations
├── services/ # Worker service and database
├── servers/ # MCP search server
├── sdk/ # Claude Agent SDK integration
├── shared/ # Shared utilities
└── utils/ # General utilities
2. Build
npm run build
3. Test
# Run all tests
npm test
# Test specific file
node --test tests/session-lifecycle.test.ts
# Test context injection
npm run test:context
# Verbose context test
npm run test:context:verbose
4. Manual Testing
# Start worker manually
npm run worker:start
# Check worker status
npm run worker:status
# View logs
npm run worker:logs
# Test hooks manually
echo '{"session_id":"test-123","cwd":"'$(pwd)'","source":"startup"}' | node plugin/scripts/context-hook.js
5. Iterate
Repeat steps 1-4 until your changes work as expected.
Adding New Features
Adding a New Hook
- Create hook implementation in
src/hooks/your-hook.ts:
import { HookInput } from './types';
export async function yourHook(input: HookInput) {
// Hook implementation
return {
hookSpecificOutput: 'Optional output'
};
}
- Create entry point in
src/bin/hooks/your-hook.ts:
#!/usr/bin/env node
import { readStdin } from '../../shared/stdin';
import { yourHook } from '../../hooks/your-hook';
async function main() {
const input = await readStdin();
const result = await yourHook(input);
console.log(JSON.stringify(result));
}
main().catch(console.error);
- Add to
plugin/hooks/hooks.json:
{
"YourHook": [{
"hooks": [{
"type": "command",
"command": "node ${CLAUDE_PLUGIN_ROOT}/scripts/your-hook.js",
"timeout": 120
}]
}]
}
- Rebuild:
npm run build
Modifying Database Schema
- Add migration to
src/services/sqlite/migrations.ts:
export const migration011: Migration = {
version: 11,
up: (db: Database) => {
db.run(`
ALTER TABLE observations ADD COLUMN new_field TEXT;
`);
},
down: (db: Database) => {
// Optional: define rollback
}
};
- Update types in
src/services/sqlite/types.ts:
export interface Observation {
// ... existing fields
new_field?: string;
}
- Update database methods in
src/services/sqlite/SessionStore.ts:
createObservation(obs: Observation) {
// Include new_field in INSERT
}
- Test migration:
# Backup database first!
cp ~/.claude-mem/claude-mem.db ~/.claude-mem/claude-mem.db.backup
# Run tests
npm test
Extending SDK Prompts
- Modify prompts in
src/sdk/prompts.ts:
export function buildObservationPrompt(observation: Observation): string {
return `
<observation>
<!-- Add new XML structure -->
</observation>
`;
}
- Update parser in
src/sdk/parser.ts:
export function parseObservation(xml: string): ParsedObservation {
// Parse new XML fields
}
- Test:
npm test
Adding MCP Search Tools
- Add tool definition in
src/servers/search-server.ts:
server.setRequestHandler(CallToolRequestSchema, async (request) => {
if (request.params.name === 'your_new_tool') {
// Implement tool logic
const results = await search.yourNewSearch(params);
return formatResults(results);
}
});
- Add search method in
src/services/sqlite/SessionSearch.ts:
yourNewSearch(params: YourParams): SearchResult[] {
// Implement FTS5 search
}
- Rebuild and test:
npm run build
npm test
Testing
Running Tests
# All tests
npm test
# Specific test file
node --test tests/your-test.test.ts
# With coverage (if configured)
npm test -- --coverage
Writing Tests
Create test files in tests/:
import { describe, it } from 'node:test';
import assert from 'node:assert';
describe('YourFeature', () => {
it('should do something', () => {
// Test implementation
assert.strictEqual(result, expected);
});
});
Test Database
Use a separate test database:
import { SessionStore } from '../src/services/sqlite/SessionStore';
const store = new SessionStore(':memory:'); // In-memory database
Code Style
TypeScript Guidelines
- Use TypeScript strict mode
- Define interfaces for all data structures
- Use async/await for asynchronous code
- Handle errors explicitly
- Add JSDoc comments for public APIs
Formatting
- Follow existing code formatting
- Use 2-space indentation
- Use single quotes for strings
- Add trailing commas in objects/arrays
Example
/**
* Create a new observation in the database
*/
export async function createObservation(
obs: Observation
): Promise<number> {
try {
const result = await db.insert('observations', {
session_id: obs.session_id,
tool_name: obs.tool_name,
// ...
});
return result.id;
} catch (error) {
logger.error('Failed to create observation', error);
throw error;
}
}
Debugging
Enable Debug Logging
export DEBUG=claude-mem:*
npm run worker:restart
npm run worker:logs
Inspect Database
sqlite3 ~/.claude-mem/claude-mem.db
# View schema
.schema observations
# Query data
SELECT * FROM observations LIMIT 10;
Trace Observations
Use correlation IDs to trace observations through the pipeline:
sqlite3 ~/.claude-mem/claude-mem.db
SELECT correlation_id, tool_name, created_at
FROM observations
WHERE session_id = 'YOUR_SESSION_ID'
ORDER BY created_at;
Debug Hooks
Run hooks manually with test input:
# Test context hook
echo '{"session_id":"test-123","cwd":"'$(pwd)'","source":"startup"}' | node plugin/scripts/context-hook.js
# Test new hook
echo '{"session_id":"test-123","cwd":"'$(pwd)'","prompt":"test"}' | node plugin/scripts/new-hook.js
Publishing
NPM Publishing
# Update version in package.json
npm version patch # or minor, or major
# Build
npm run build
# Publish to NPM
npm run release
The release script:
- Runs tests
- Builds all components
- Publishes to NPM registry
Creating a Release
- Update version in
package.json - Update
CHANGELOG.md - Commit changes
- Create git tag
- Push to GitHub
- Publish to NPM
# Update version
npm version 4.2.4
# Update changelog
# Edit CHANGELOG.md manually
# Commit
git add .
git commit -m "chore: Release v4.2.4"
# Tag
git tag v4.2.4
# Push
git push origin main --tags
# Publish to NPM
npm run release
Contributing
Contribution Workflow
- Fork the repository
- Create a feature branch (
git checkout -b feature/amazing-feature) - Make your changes
- Write tests
- Update documentation
- Commit your changes (
git commit -m 'Add amazing feature') - Push to the branch (
git push origin feature/amazing-feature) - Open a Pull Request
Pull Request Guidelines
- Clear title: Describe what the PR does
- Description: Explain why the change is needed
- Tests: Include tests for new features
- Documentation: Update docs as needed
- Changelog: Add entry to CHANGELOG.md
- Commits: Use clear, descriptive commit messages
Code Review Process
- Automated tests must pass
- Code review by maintainer
- Address feedback
- Final approval
- Merge to main
Development Tools
Recommended VSCode Extensions
- TypeScript
- ESLint
- Prettier
- SQLite Viewer
Useful Commands
# Check TypeScript types
npx tsc --noEmit
# Lint code (if configured)
npm run lint
# Format code (if configured)
npm run format
# Clean build artifacts
rm -rf plugin/scripts/*.js plugin/scripts/*.cjs
Troubleshooting Development
Build Fails
-
Clean node_modules:
rm -rf node_modules npm install -
Check Node.js version:
node --version # Should be >= 18.0.0 -
Check for syntax errors:
npx tsc --noEmit
Tests Fail
-
Check database:
rm ~/.claude-mem/claude-mem.db npm test -
Check worker status:
npm run worker:status -
View logs:
npm run worker:logs
Worker Won't Start
-
Kill existing process:
pm2 delete claude-mem-worker -
Check port:
lsof -i :37777 -
Try custom port:
export CLAUDE_MEM_WORKER_PORT=38000 npm run worker:start
Next Steps
- Architecture Overview - Understand the system
- Configuration - Customize Claude-Mem
- Troubleshooting - Common issues