docs / getting-started / installation.md
Installation
This guide gets a self-hosted entrytwo instance running.
entrytwo is AI-native double-entry accounting with a Git-style data model. The AI posts real journal entries when confident. Full history, branches, blame. Self-hosted.
Deploy: Most production setups use a VPS with Docker and HTTPS. You can also install and run locally (e.g. on a Mac) for real use: same full app, like classic non-cloud accounting software. Runs on your VPS or locally.
Let AI install it for you
Not a terminal person? You can still get this running. Point an AI coding agent at this page (and the repo) and ask it to install entrytwo for you — for example Claude Code, OpenClaw, Hermes, Cursor, or a similar tool that can run commands on your machine or VPS. Share your goal (local Mac vs VPS + domain), paste errors back if something fails, and keep secrets (passwords, API keys) out of chats you do not trust. The steps below remain the source of truth; the agent just walks them with you.
Prerequisites
- Node.js 20+
- PostgreSQL 14+ (or use the included Docker Compose)
- Git
- Docker & Docker Compose (strongly recommended for production-like setups)
Optional but useful:
- A domain + reverse proxy (Caddy, Nginx, Traefik) for HTTPS
- SMTP for magic-link login (and invitation emails)
- Google and/or Microsoft Entra ID OAuth apps for staff sign-in
- LLM API key (OpenAI, Anthropic, xAI, etc.)
Quick Start (Recommended - Docker Compose)
- Clone and enter the directory:
git clone https://github.com/felixkrusch/entrytwo.git
cd entrytwo/entrytwo_v1
- Copy the example environment:
cp .env.example .env
- Edit
.envand set at minimum:
DATABASE_URL(or use the compose defaults)POSTGRES_PASSWORD(required by compose)AUTH_SECRET- generate with:openssl rand -base64 48(≥ 32 characters)ENCRYPTION_KEY- generate with:openssl rand -hex 32(64 hex chars; bank feeds / secrets)JOB_RUNNER_SECRET- generate with:openssl rand -base64 48UPDATER_TOKEN- generate with:openssl rand -base64 48(for the updater sidecar)- At least one LLM key if you want AI/chat features (
OPENAI_API_KEY,ANTHROPIC_API_KEY, etc.) NEXT_LLM_PROVIDERandNEXT_LLM_MODEL(defaults are usually fine for development)
- Start the stack:
docker compose up -d
This starts:
app(Next.js on port 3000)db(PostgreSQL)worker(background jobs)updater(isolated sidecar for signed updates - see Self-Hosted Updates)redis
- Run migrations and seed:
docker compose exec app npx prisma migrate deploy
docker compose exec app npm run db:seed
(Local non-Docker development can use npx prisma migrate dev instead of deploy.)
On first visit with no admin users, you will be able to create the initial ADMIN account.
Environment Variables (Key Ones)
Copy .env.example and fill in:
Required (local or production)
DATABASE_URLAUTH_SECRET(≥ 32 characters)POSTGRES_PASSWORD(when using compose)
Required in production (app refuses to start / health stays degraded without these)
ENCRYPTION_KEY(64 hex chars)JOB_RUNNER_SECRETAUTH_URL(public origin, e.g.https://books.example.com)AUTH_TRUST_HOST=true(behind nginx/caddy/traefik)- At least one real sign-in method:
- SMTP:
SMTP_HOST,SMTP_USER,SMTP_PASS(and ideallySMTP_FROM), and/or - Google:
GOOGLE_CLIENT_ID+GOOGLE_CLIENT_SECRET, and/or - Microsoft:
MICROSOFT_ENTRA_ID_ID+MICROSOFT_ENTRA_ID_SECRET(+ issuer)
- SMTP:
Strongly recommended
UPDATER_TOKEN- shared secret for the updater sidecar- LLM key +
NEXT_LLM_PROVIDER/NEXT_LLM_MODEL
For production / updates
UPDATE_MANIFEST_URL- points at your signed release manifest- Cosign settings (
COSIGN_IDENTITY,COSIGN_PUBLIC_KEY, etc.) STRIPE_WEBHOOK_SECRET/ PayPal secrets (if using processor feeds)
Full list and explanations are in the app .env.example. Production auth go-live: app repo docs/VPS-Auth-Install.md.
Manual Postgres (without Docker)
- Create the database:
CREATE DATABASE entrytwo;
CREATE USER entrytwo WITH PASSWORD 'entrytwo_dev_password';
GRANT ALL PRIVILEGES ON DATABASE entrytwo TO entrytwo;
- Set in
.env:
DATABASE_URL="postgresql://entrytwo:entrytwo_dev_password@localhost:5432/entrytwo"
- Install deps, migrate, seed:
npm install
npx prisma migrate dev
npm run db:seed
npm run dev
First Admin Bootstrap
entrytwo is designed so the very first user in a fresh installation becomes an ADMIN.
- If no
ADMINexists, the sign-in / onboarding flow allows creating one (company language + standard chart of accounts). - After the first admin exists, further users join via invitation (Admin → Users). They must sign in with the exact invited email using Google, Microsoft, or magic link.
- Roles:
ADMIN,ACCOUNTANT, orVIEWER. - In production, ADMIN must enable TOTP (2FA) before using the app.
See First Steps for the first-login experience.
Authentication (summary)
| Environment | How you sign in |
|---|---|
| Local development | Instant email (“Continue”) — no SMTP required |
| Production | Magic link (SMTP) and/or Google OAuth and/or Microsoft Entra ID |
Instant email is disabled when NODE_ENV=production. Configure OAuth redirect URIs to {AUTH_URL}/api/auth/callback/google and .../microsoft-entra-id.
Health and Basic Verification
- App health:
GET /api/health - Production should report
"ready": trueandauth.productionReady: true - After
docker compose up -d, the app container has a healthcheck on this endpoint
Production VPS (short)
Do these before expecting a green production boot:
- Secrets —
AUTH_SECRET,ENCRYPTION_KEY,JOB_RUNNER_SECRET,POSTGRES_PASSWORD(fresh per install). - Sign-in — full SMTP (
SMTP_HOST+USER+PASS) and/or Google/Microsoft OAuth. Instant email is off in production. - Public URL —
AUTH_URL=https://your.domain,AUTH_TRUST_HOST=true. - DNS — A record for the hostname → VPS IP before HTTPS. If certificates failed while DNS was missing, restart Caddy/nginx after DNS works.
- Deploy —
docker compose up -d --build(entrypoint runs migrations). Confirm/api/health→ready: true. - First admin — bootstrap, then TOTP for ADMIN.
RAM: plan ≥ 2 GB for one stack; ~4 GB if you run multiple installs (separate compose projects, ports, and hostnames) on one machine.
Packaging details and troubleshooting: app repo docs/PRODUCTION.md and docs/VPS-Auth-Install.md.
Common Next Steps
- Read First Steps
- Set up at least one LLM key and test the chat
- Configure SMTP and/or OAuth so teammates can sign in
- (Production) HTTPS, strong secrets, and the VPS auth checklist in the app repo
- (Later) Bank feeds, updates, and licensing
See also: