-
Notifications
You must be signed in to change notification settings - Fork 7
Security
Security features and best practices for Memory Journal MCP Server.
Local-First Design: Your project context stays on your machine. No external API calls, no cloud dependencies - your development history remains private.
Memory Journal is local-first:
- All data stored locally in SQLite
- No external API calls
- No telemetry or analytics
- You own and control your data
const MAX_CONTENT_SIZE = 50 * 1024; // 50KB per entry
const MAX_TAG_LENGTH = 100; // 100 characters per tagWhy limits:
- Prevent resource exhaustion
- Ensure reasonable performance
- Protect database integrity
All queries use parameterized statements:
// Safe - parameterized query
db.run(
'INSERT INTO memory_journal (content) VALUES (?)',
[userContent]
);
// NEVER do this (vulnerable to SQL injection)
db.run(`INSERT INTO memory_journal (content) VALUES ('${userContent}')`); // DON'T!Benefits:
- SQL injection impossible
- Safe handling of quotes and special characters
- Database-level validation
# Create non-root user
RUN addgroup -g 1000 appuser && \
adduser -D -u 1000 -G appuser appuser
# Switch to non-root user
USER appuserBenefits:
- Container cannot modify host system
- Reduced attack surface
- Follows least privilege principle
FROM node:24-alpineAlpine Linux benefits:**
- Small attack surface (~5MB base)
- Security-focused distribution
- Fewer vulnerabilities
- Fast updates
{
"command": "docker",
"args": [
"run", "--rm", "-i",
// NO --privileged flag
// NO --cap-add flags
"-v", "./data:/app/data",
"writenotenow/memory-journal-mcp:latest"
]
}{
"args": [
"-v", "./data:/app/data:rw", // Only data directory
// NOT: "-v", "/:/host" - would expose entire host
]
}Best practices:
- Mount only necessary directories
- Use read-only mounts where possible
- Avoid mounting sensitive host directories
Recommended (highest security):
# Use SHA-256 digest for immutable reference
docker pull writenotenow/memory-journal-mcp@sha256:abc123...
# Find SHA digests at:
# https://hub.docker.com/r/writenotenow/memory-journal-mcp/tagsBenefits:
- Immutable image reference
- Protection against tag hijacking
- Reproducible deployments
- Supply chain verification
Tag-based (convenience):
docker pull writenotenow/memory-journal-mcp:latestPRAGMA journal_mode = WAL; -- Write-Ahead Logging
PRAGMA synchronous = NORMAL; -- Balance safety/speedBenefits:
- Crash recovery
- Data integrity
- Concurrent access safety
FOREIGN KEY (entry_id) REFERENCES memory_journal(id) ON DELETE CASCADEBenefits:
- Referential integrity
- Automatic cleanup
- Prevents orphaned records
db.run('BEGIN TRANSACTION');
try {
db.run('INSERT ...');
db.run('UPDATE ...');
db.run('COMMIT');
} catch (error) {
db.run('ROLLBACK');
throw error;
}Benefits:
- ACID compliance
- Data consistency
- Error recovery
No network access:
- No cloud storage
- No API calls (except Git/GitHub CLI)
- No user tracking
- No analytics
Data location:
- npm:
~/.memory-journal/memory_journal.db - Docker:
./data/memory_journal.db(volume mount)
Optional and transparent:
create_entry({
content: "...",
auto_context: false // Disable Git integration
})Git operations:
- Read-only (no commits)
- Local repository info only
- Optional GitHub CLI (user-controlled)
Data captured:
- Repository name and path
- Current branch
- Latest commit
- GitHub issues (if
ghCLI installed)
Not captured:
- File contents
- Uncommitted changes
- Remote repository data
- Credentials
// Soft delete (default)
delete_entry({ entry_id: 42, permanent: false })
// Sets deleted_at timestamp, entry remains in DB
// Permanent delete (explicit)
delete_entry({ entry_id: 42, permanent: true })
// Removes from database completelyBenefits:
- Accidental deletion recovery
- Audit trail
- No data loss
Soft-deleted entries:
- Excluded from searches
- Not visible in lists
- Still in database (for recovery)
Security handled by MCP client:
- Cursor IDE: Desktop app security
- Claude Desktop: Desktop app security
- User controls which servers run
npm installation:
# Database created with user permissions
chmod 600 ~/.memory-journal/memory_journal.dbDocker installation:
# Volume mount with appropriate permissions
mkdir -m 755 dataDocker environment variables:
{
"args": [
"-e", "DB_PATH=/app/data/custom.db",
// NO sensitive data in env vars
// NO API keys
// NO credentials
]
}No secrets required:
- No API keys
- No passwords
- No tokens
- Optional: GitHub CLI (user manages
gh auth)
1. Regular backups:
# Backup database
cp ./data/memory_journal.db ./backups/journal-$(date +%Y%m%d).db2. Docker image verification:
# Verify SHA digest
docker images --digests | grep memory-journal
# Use SHA-pinned images
docker pull writenotenow/memory-journal-mcp@sha256:...3. Limit Docker access:
{
"args": [
"-v", "./data:/app/data", // Only mount data dir
"--read-only", // Read-only root filesystem
"--tmpfs", "/tmp" // Writable tmp
]
}4. Review logs:
# Check for errors
docker logs <container_id>1. Input validation:
if (content.length > MAX_CONTENT_SIZE) {
throw new Error(`Content too large: ${content.length} > ${MAX_CONTENT_SIZE}`);
}2. Parameterized queries:
// Always use ? placeholders
db.run('SELECT * FROM memory_journal WHERE id = ?', [entryId]);3. Error handling:
try {
// Operation
} catch (error) {
// Log, don't expose internals to user
logger.error('Internal error', { error });
return { error: 'Operation failed' };
}4. Least privilege:
// Don't request unnecessary permissions
// Don't access unnecessary files
// Don't make unnecessary network callsFound a security issue?
- Do NOT open a public GitHub issue
- Email: security@example.com (use your actual security contact)
- Include:
- Description of vulnerability
- Steps to reproduce
- Potential impact
- Suggested fix (if any)
We will:
- Acknowledge within 48 hours
- Provide fix timeline
- Credit you (if desired)
- Publish security advisory
- ✅ Input validation (size limits)
- ✅ SQL injection prevention (parameterized queries)
- ✅ No credentials in code
- ✅ Non-root Docker execution
- ✅ Minimal base image (Alpine)
- ✅ No unnecessary privileges
- ✅ Local-only data storage
- ✅ Transaction safety (ACID)
- ✅ Error handling
- ✅ Soft delete option
Protected against:
- SQL injection
- Resource exhaustion (size limits)
- Accidental data loss (soft delete)
- Database corruption (WAL, transactions)
- Container escape (non-root, no privileges)
Not protected against:
- Malicious MCP client
- Compromised host system
- Physical access to database file
- User deleting database file
Why:
- Local-first design trusts the host
- User has full control
- Desktop application security model
GDPR-friendly:
- No data collection
- No data transmission
- Local storage only
- User controls all data
- Easy data export/deletion
No PII collection:
- No names
- No email addresses
- No tracking
- No analytics
npm:
# Update to latest version
npm install -g memory-journal-mcp@latestDocker:
# Pull latest image
docker pull writenotenow/memory-journal-mcp:latest
# Or specific SHA
docker pull writenotenow/memory-journal-mcp@sha256:...Monitor:
- GitHub releases
- Docker Hub updates
- Security advisories
Next: Check Architecture or Performance.