-
Notifications
You must be signed in to change notification settings - Fork 0
Users and API Keys
Fold uses OIDC authentication for user management and API tokens for programmatic access. This guide covers user registration, group management, API key generation, and chunking strategies for large codebases.
Fold supports two authentication methods:
Session-Based (Web UI)
- Browser-based login via OIDC providers
- Session cookies with httpOnly and secure flags
- Automatic expiry
Token-Based (API and MCP)
- API tokens generated by authenticated users
- Bearer token authentication
- Project-scoped access control
Fold integrates with OIDC providers for authentication. Configure providers through environment variables or the web UI.
| Provider | Configuration |
|---|---|
OIDC_GOOGLE_CLIENT_ID, OIDC_GOOGLE_CLIENT_SECRET
|
|
| GitHub |
OIDC_GITHUB_CLIENT_ID, OIDC_GITHUB_CLIENT_SECRET
|
| Zitadel |
OIDC_ZITADEL_URL, OIDC_ZITADEL_CLIENT_ID, OIDC_ZITADEL_CLIENT_SECRET
|
| Custom |
OIDC_ISSUER, OIDC_CLIENT_ID, OIDC_CLIENT_SECRET
|
# Google OAuth
OIDC_GOOGLE_CLIENT_ID=your-google-client-id
OIDC_GOOGLE_CLIENT_SECRET=your-google-client-secret
# GitHub OAuth
OIDC_GITHUB_CLIENT_ID=your-github-client-id
OIDC_GITHUB_CLIENT_SECRET=your-github-client-secret
# Zitadel
OIDC_ZITADEL_URL=https://zitadel.example.com
OIDC_ZITADEL_CLIENT_ID=your-client-id
OIDC_ZITADEL_CLIENT_SECRET=your-client-secret
# Callback URL (must match provider configuration)
OIDC_REDIRECT_URI=https://fold.example.com/auth/callback
Fold requests the following scopes by default:
-
openid— Get a unique identifier -
profile— Display name and avatar -
email— User email address
User visits /auth/login/:provider
│
▼
Redirects to OIDC provider
│
▼
User enters credentials
│
▼
Provider redirects back to /auth/callback
│
▼
Fold creates/updates user record
│
▼
Session created, user logged in
Get Current User
GET /auth/me
Authorization: Bearer token or Cookie: session=...
Response:
{
"id": "user_abc123",
"provider": "google",
"email": "user@example.com",
"display_name": "John Doe",
"avatar_url": "https://...",
"created_at": "2026-02-03T10:00:00Z"
}
Login with Provider
GET /auth/login/:provider
Redirects to OIDC provider login page.
Supported providers: google, github, zitadel, custom
Logout
POST /auth/logout
Authorization: Bearer token or Cookie: session=...
Invalidates session/token and logs out user.
Fold uses project-based access control. Users and groups are assigned to projects with roles (member or viewer). Access is managed through project membership; tokens inherit the user's access.
By User: Users access projects based on their membership (direct or via groups).
By Token: API tokens inherit the user's project access. They cannot be further scoped to restrict access.
Access is controlled through:
-
Direct membership (
project_memberstable) — user to project -
Group membership (
group_memberstable +project_group_memberstable) — user to group to project - Roles — member (read/write) or viewer (read-only) per project
Groups are implemented:
- Organise users into groups (
groupstable) - Assign group access to projects with roles (
project_group_memberstable) - Users inherit group permissions automatically
Via API
curl -X POST https://fold.example.com/me/tokens \
-H "Authorization: Bearer <session_token>" \
-H "Content-Type: application/json" \
-d '{
"name": "CI Pipeline"
}'
Response: 201 Created
{
"id": "tok_abc123",
"name": "CI Pipeline",
"token": "fold_xxxxxxxxxxxxxxxxxxxxxxxxxxxx",
"created_at": "2026-02-03T10:00:00Z"
}
The token is only returned once. Store it securely (environment variable, secret manager).
The token inherits all project access from the user who created it. No project scoping is possible at token creation time.
Include the token in the Authorization header:
curl -H "Authorization: Bearer fold_xxxxxxxxxxxxxxxxxxxxxxxxxxxx" \
https://fold.example.com/api/projects
Or in MCP configuration:
claude mcp add -t http -s user fold http://localhost:8765/mcp \
--header "Authorization: Bearer fold_xxxxxxxxxxxxxxxxxxxxxxxxxxxx"
curl -H "Authorization: Bearer <token>" \
https://fold.example.com/me/tokens
Response:
{
"tokens": [
{
"id": "tok_abc123",
"name": "CI Pipeline",
"created_at": "2026-02-03T10:00:00Z",
"last_used": "2026-02-04T15:30:00Z"
}
]
}
curl -X DELETE https://fold.example.com/me/tokens/tok_abc123 \
-H "Authorization: Bearer <token>"
Best Practices:
- Store tokens in environment variables or secrets manager
- Never commit tokens to git
- Rotate tokens regularly
- Revoke unused tokens
- Use short-lived tokens for CI/CD where possible
- Control token access via project membership (direct user or group membership)
- Revoke tokens for users who leave the team
Token Format
fold_<16-char-random>
Tokens are hashed with SHA256 in the database. Only the full token is shown once at creation.
When indexing large files, Fold uses intelligent chunking to break content into manageable pieces for analysis and embedding.
Single-Memory Model
Despite chunking during analysis, Fold creates one memory per file, not per chunk. Chunks are used for:
- LLM analysis (summarisation, metadata extraction)
- Embedding generation (semantic search)
- Context reconstruction
The full file content is stored in fold/a/b/hash.md.
# Maximum file size (skip larger files)
MAX_FILE_SIZE=100KB # Default: 100KB
# Chunk size for analysis
CHUNK_SIZE=8KB # Default: 8KB
# Chunk overlap (for context)
CHUNK_OVERLAP=1KB # Default: 1KB
Large File (src/service.ts)
│
▼
Split into chunks (8KB each with 1KB overlap)
│
┌──┴──────────────────────────┐
▼ ▼
Chunk 1 Chunk 2
"export class Service..." "...public method..."
│ │
▼ ▼
LLM analyses each chunk LLM analyses chunk
│ │
┌──┴────────────────────────────┘
│
▼
Combine insights into single summary
│
▼
Create memory with full file content + metadata
Code Chunks
Split on:
- Function/class definitions
- Logical blocks
- Line boundaries (max 8KB)
Documentation Chunks
Split on:
- Sections (markdown headers)
- Paragraphs
- Line boundaries
Mixed Chunks
For files with code and docs, split intelligently based on content type.
Chunks overlap by 1KB to preserve context:
Chunk 1: [lines 1-200] + overlap (last 15 lines)
Chunk 2: [overlap (first 15 lines) + lines 200-400] + overlap
Chunk 3: [overlap (first 15 lines) + lines 400-600]
This ensures the LLM doesn't miss relationships at chunk boundaries.
File Too Large (>100KB)
- Skipped during indexing
- Logged with reason
- Can be manually chunked by user
Workaround
For large generated files (e.g. bundled CSS):
- Exclude from indexing:
exclude = ["dist/**", "*.min.js"] - Or manually split into logical chunks using file structure
# Session secret (used for signing cookies)
SESSION_SECRET=your-random-secret-key
# Session lifetime
SESSION_TIMEOUT=24h # Default: 24 hours
# Cookie settings
COOKIE_DOMAIN=fold.example.com # Optional domain restriction
COOKIE_PATH=/ # Default: root
- httpOnly: Prevents JavaScript access
- Secure: Only sent over HTTPS in production
- SameSite: Strict (prevents CSRF)
- Expiry: Configurable timeout
Sessions are automatically rotated:
- On login
- After specified timeout
- On privilege changes
- User logs in via OIDC
- User creates API token via
/me/tokensendpoint - Token is generated and hashed
- Token returned once (show to user to copy)
- Token included in
Authorization: Bearerheader - Server validates token against database
- Permission check: user who owns token must have access to the project
- Operation proceeds with token's user context and project membership
Tokens do not expire automatically. Users must revoke manually:
curl -X DELETE https://fold.example.com/me/tokens/:id \
-H "Authorization: Bearer <token>"
Future feature: Log all token usage for security auditing.
# 1. Create a service account user (or use existing user)
# User must have access to the project(s) being indexed
# 2. Create API token for the service account
curl -X POST https://fold.example.com/me/tokens \
-H "Authorization: Bearer <session>" \
-d '{
"name": "GitHub Actions"
}'
# 3. Copy token and add to GitHub secrets
# Settings → Secrets → New repository secret
# FOLD_API_TOKEN = fold_xxxx...
# 4. Use in workflow
- name: Index codebase
env:
FOLD_API_TOKEN: ${{ secrets.FOLD_API_TOKEN }}
run: |
claude mcp add -t http -s user fold http://fold:8765/mcp \
--header "Authorization: Bearer $FOLD_API_TOKEN"
Token will have access to all projects that the service account user has access to. To limit access, adjust the service account's project membership instead.
- Team member logs in via Google/GitHub/Zitadel
- Admin creates project
- Admin shares project slug with team member
- Team member can access project after login
- Remove user from project membership (direct or group)
- Or delete API token:
DELETE /me/tokens/:id - Or disable OIDC provider in user's identity provider
"Invalid token"
- Token is malformed or expired
- Verify token format starts with
fold_ - Check token hasn't been revoked
"Forbidden" (403)
- User doesn't have access to the project
- Check project membership (direct or group)
- Ensure user has at least viewer role on the project
"Provider not configured"
- OIDC provider environment variables not set
- Check
OIDC_*variables in.env
"Session expired"
- Session timeout reached (default 24 hours)
- Log in again to create new session
See Configuration for OIDC provider setup details and API-Reference for endpoint documentation.