mirror of
https://github.com/MODSetter/SurfSense.git
synced 2026-04-25 08:46:22 +02:00
173 lines
6.8 KiB
Text
173 lines
6.8 KiB
Text
|
|
---
|
||
|
|
title: Docker Compose
|
||
|
|
description: Manual Docker Compose setup for SurfSense
|
||
|
|
---
|
||
|
|
|
||
|
|
## Setup
|
||
|
|
|
||
|
|
```bash
|
||
|
|
git clone https://github.com/MODSetter/SurfSense.git
|
||
|
|
cd SurfSense/docker
|
||
|
|
cp .env.example .env
|
||
|
|
# Edit .env, at minimum set SECRET_KEY
|
||
|
|
docker compose up -d
|
||
|
|
```
|
||
|
|
|
||
|
|
After starting, access SurfSense at:
|
||
|
|
|
||
|
|
- **Frontend**: [http://localhost:3929](http://localhost:3929)
|
||
|
|
- **Backend API**: [http://localhost:8929](http://localhost:8929)
|
||
|
|
- **API Docs**: [http://localhost:8929/docs](http://localhost:8929/docs)
|
||
|
|
---
|
||
|
|
|
||
|
|
## Configuration
|
||
|
|
|
||
|
|
All configuration lives in a single `docker/.env` file (or `surfsense/.env` if you used the install script). Copy `.env.example` to `.env` and edit the values you need.
|
||
|
|
|
||
|
|
### Required
|
||
|
|
|
||
|
|
| Variable | Description |
|
||
|
|
|----------|-------------|
|
||
|
|
| `SECRET_KEY` | JWT secret key. Generate with: `openssl rand -base64 32`. Auto-generated by the install script. |
|
||
|
|
|
||
|
|
### Core Settings
|
||
|
|
|
||
|
|
| Variable | Description | Default |
|
||
|
|
|----------|-------------|---------|
|
||
|
|
| `SURFSENSE_VERSION` | Image tag to deploy. Use `latest`, a clean version (e.g. `0.0.14`), or a specific build (e.g. `0.0.14.1`) | `latest` |
|
||
|
|
| `AUTH_TYPE` | Authentication method: `LOCAL` (email/password) or `GOOGLE` (OAuth) | `LOCAL` |
|
||
|
|
| `ETL_SERVICE` | Document parsing: `DOCLING` (local), `UNSTRUCTURED`, or `LLAMACLOUD` | `DOCLING` |
|
||
|
|
| `EMBEDDING_MODEL` | Embedding model for vector search | `sentence-transformers/all-MiniLM-L6-v2` |
|
||
|
|
| `TTS_SERVICE` | Text-to-speech provider for podcasts | `local/kokoro` |
|
||
|
|
| `STT_SERVICE` | Speech-to-text provider for audio files | `local/base` |
|
||
|
|
| `REGISTRATION_ENABLED` | Allow new user registrations | `TRUE` |
|
||
|
|
|
||
|
|
### Ports
|
||
|
|
|
||
|
|
| Variable | Description | Default |
|
||
|
|
|----------|-------------|---------|
|
||
|
|
| `FRONTEND_PORT` | Frontend service port | `3929` |
|
||
|
|
| `BACKEND_PORT` | Backend API service port | `8929` |
|
||
|
|
|
||
|
|
### Custom Domain / Reverse Proxy
|
||
|
|
|
||
|
|
Only set these if serving SurfSense on a real domain via a reverse proxy (Caddy, Nginx, Cloudflare Tunnel, etc.). Leave commented out for standard localhost deployments.
|
||
|
|
|
||
|
|
| Variable | Description |
|
||
|
|
|----------|-------------|
|
||
|
|
| `NEXT_FRONTEND_URL` | Public frontend URL (e.g. `https://app.yourdomain.com`) |
|
||
|
|
| `BACKEND_URL` | Public backend URL for OAuth callbacks (e.g. `https://api.yourdomain.com`) |
|
||
|
|
| `NEXT_PUBLIC_FASTAPI_BACKEND_URL` | Backend URL used by the frontend (e.g. `https://api.yourdomain.com`) |
|
||
|
|
|
||
|
|
### Database
|
||
|
|
|
||
|
|
Defaults work out of the box. Change for security in production.
|
||
|
|
|
||
|
|
| Variable | Description | Default |
|
||
|
|
|----------|-------------|---------|
|
||
|
|
| `DB_USER` | PostgreSQL username | `surfsense` |
|
||
|
|
| `DB_PASSWORD` | PostgreSQL password | `surfsense` |
|
||
|
|
| `DB_NAME` | PostgreSQL database name | `surfsense` |
|
||
|
|
| `DB_HOST` | PostgreSQL host | `db` |
|
||
|
|
| `DB_PORT` | PostgreSQL port | `5432` |
|
||
|
|
| `DB_SSLMODE` | SSL mode: `disable`, `require`, `verify-ca`, `verify-full` | `disable` |
|
||
|
|
| `DATABASE_URL` | Full connection URL override. Use for managed databases (RDS, Supabase, etc.) | *(built from above)* |
|
||
|
|
|
||
|
|
### Authentication
|
||
|
|
|
||
|
|
| Variable | Description |
|
||
|
|
|----------|-------------|
|
||
|
|
| `GOOGLE_OAUTH_CLIENT_ID` | Google OAuth client ID (required if `AUTH_TYPE=GOOGLE`) |
|
||
|
|
| `GOOGLE_OAUTH_CLIENT_SECRET` | Google OAuth client secret (required if `AUTH_TYPE=GOOGLE`) |
|
||
|
|
|
||
|
|
Create credentials at the [Google Cloud Console](https://console.cloud.google.com/apis/credentials).
|
||
|
|
|
||
|
|
### External API Keys
|
||
|
|
|
||
|
|
| Variable | Description |
|
||
|
|
|----------|-------------|
|
||
|
|
| `FIRECRAWL_API_KEY` | [Firecrawl](https://www.firecrawl.dev/) API key for web crawling |
|
||
|
|
| `UNSTRUCTURED_API_KEY` | [Unstructured.io](https://unstructured.io/) API key (required if `ETL_SERVICE=UNSTRUCTURED`) |
|
||
|
|
| `LLAMA_CLOUD_API_KEY` | [LlamaCloud](https://cloud.llamaindex.ai/) API key (required if `ETL_SERVICE=LLAMACLOUD`) |
|
||
|
|
|
||
|
|
### Connector OAuth Keys
|
||
|
|
|
||
|
|
Uncomment the connectors you want to use. Redirect URIs follow the pattern `http://localhost:8000/api/v1/auth/<connector>/connector/callback`.
|
||
|
|
|
||
|
|
| Connector | Variables |
|
||
|
|
|-----------|-----------|
|
||
|
|
| Google Drive / Gmail / Calendar | `GOOGLE_DRIVE_REDIRECT_URI`, `GOOGLE_GMAIL_REDIRECT_URI`, `GOOGLE_CALENDAR_REDIRECT_URI` |
|
||
|
|
| Notion | `NOTION_CLIENT_ID`, `NOTION_CLIENT_SECRET`, `NOTION_REDIRECT_URI` |
|
||
|
|
| Slack | `SLACK_CLIENT_ID`, `SLACK_CLIENT_SECRET`, `SLACK_REDIRECT_URI` |
|
||
|
|
| Discord | `DISCORD_CLIENT_ID`, `DISCORD_CLIENT_SECRET`, `DISCORD_BOT_TOKEN`, `DISCORD_REDIRECT_URI` |
|
||
|
|
| Jira & Confluence | `ATLASSIAN_CLIENT_ID`, `ATLASSIAN_CLIENT_SECRET`, `JIRA_REDIRECT_URI`, `CONFLUENCE_REDIRECT_URI` |
|
||
|
|
| Linear | `LINEAR_CLIENT_ID`, `LINEAR_CLIENT_SECRET`, `LINEAR_REDIRECT_URI` |
|
||
|
|
| ClickUp | `CLICKUP_CLIENT_ID`, `CLICKUP_CLIENT_SECRET`, `CLICKUP_REDIRECT_URI` |
|
||
|
|
| Airtable | `AIRTABLE_CLIENT_ID`, `AIRTABLE_CLIENT_SECRET`, `AIRTABLE_REDIRECT_URI` |
|
||
|
|
| Microsoft Teams | `TEAMS_CLIENT_ID`, `TEAMS_CLIENT_SECRET`, `TEAMS_REDIRECT_URI` |
|
||
|
|
|
||
|
|
### Observability (optional)
|
||
|
|
|
||
|
|
| Variable | Description |
|
||
|
|
|----------|-------------|
|
||
|
|
| `LANGSMITH_TRACING` | Enable LangSmith tracing (`true` / `false`) |
|
||
|
|
| `LANGSMITH_ENDPOINT` | LangSmith API endpoint |
|
||
|
|
| `LANGSMITH_API_KEY` | LangSmith API key |
|
||
|
|
| `LANGSMITH_PROJECT` | LangSmith project name |
|
||
|
|
|
||
|
|
### Advanced (optional)
|
||
|
|
|
||
|
|
| Variable | Description | Default |
|
||
|
|
|----------|-------------|---------|
|
||
|
|
| `SCHEDULE_CHECKER_INTERVAL` | How often to check for scheduled connector tasks (e.g. `5m`, `1h`) | `5m` |
|
||
|
|
| `RERANKERS_ENABLED` | Enable document reranking for improved search | `FALSE` |
|
||
|
|
| `RERANKERS_MODEL_NAME` | Reranker model name (e.g. `ms-marco-MiniLM-L-12-v2`) | |
|
||
|
|
| `RERANKERS_MODEL_TYPE` | Reranker model type (e.g. `flashrank`) | |
|
||
|
|
| `PAGES_LIMIT` | Max pages per user for ETL services | unlimited |
|
||
|
|
|
||
|
|
---
|
||
|
|
|
||
|
|
## Docker Services
|
||
|
|
|
||
|
|
| Service | Description |
|
||
|
|
|---------|-------------|
|
||
|
|
| `db` | PostgreSQL with pgvector extension |
|
||
|
|
| `redis` | Message broker for Celery |
|
||
|
|
| `backend` | FastAPI application server |
|
||
|
|
| `celery_worker` | Background task processing (document indexing, etc.) |
|
||
|
|
| `celery_beat` | Periodic task scheduler (connector sync) |
|
||
|
|
| `frontend` | Next.js web application |
|
||
|
|
|
||
|
|
All services start automatically with `docker compose up -d`.
|
||
|
|
|
||
|
|
The backend includes a health check. Dependent services (workers, frontend) wait until the API is fully ready before starting. You can monitor startup progress with `docker compose ps` (look for `(health: starting)` → `(healthy)`).
|
||
|
|
|
||
|
|
---
|
||
|
|
|
||
|
|
## Useful Commands
|
||
|
|
|
||
|
|
```bash
|
||
|
|
# View logs (all services)
|
||
|
|
docker compose logs -f
|
||
|
|
|
||
|
|
# View logs for a specific service
|
||
|
|
docker compose logs -f backend
|
||
|
|
|
||
|
|
# Stop all services
|
||
|
|
docker compose down
|
||
|
|
|
||
|
|
# Restart a specific service
|
||
|
|
docker compose restart backend
|
||
|
|
|
||
|
|
# Stop and remove all containers + volumes (destructive!)
|
||
|
|
docker compose down -v
|
||
|
|
```
|
||
|
|
|
||
|
|
---
|
||
|
|
|
||
|
|
## Troubleshooting
|
||
|
|
|
||
|
|
- **Ports already in use**: Change the relevant `*_PORT` variable in `.env` and restart.
|
||
|
|
- **Permission errors on Linux**: You may need to prefix `docker` commands with `sudo`.
|
||
|
|
- **Line ending issues on Windows**: Run `git config --global core.autocrlf true` before cloning.
|