Skip to main content

Sign-in and workspaces

Built-in sign-in​

Campbooks is its own sign-in and token issuer. There is no separate identity service to run. People sign in with Google, Microsoft, Zoho or a passkey, and the server issues every token itself.

It needs no setup. Leave CAMPBOOKS_AUTH__ISSUER unset, as the shipped compose.yaml does. The issuer is CAMPBOOKS_PUBLIC_URL, so set that to the address people use.

  • CAMPBOOKS_PUBLIC_URL must be https://. Plain http:// works only with CAMPBOOKS_ENV=development, for a trial on your own machine.
  • The server signs tokens with keys it generates on first start and rotates every 30 days. They are stored in Postgres, encrypted with the instance secret key.
  • Passkeys need no configuration. Browsers offer them over https://, or on http://localhost in development.

The instance secret key​

On first boot, the one-shot server-init service generates the instance secret key into the server-secrets volume. The server reads it as a file, never from .env.

The key seals what Campbooks stores for you: the sign-in signing keys, web session tokens and the credentials of connected accounts. If you lose it, it cannot be recovered, and neither can what it seals. The server refuses to start when the key does not open the stored signing keys.

Keep a copy somewhere safe, apart from your backups. A backup that holds both the database and the key gives whoever finds it everything in the database. See Upgrades and backups.

How the web app signs you in​

The server signs browsers in itself. Open the app, and if you are not signed in it sends you to the sign-in screen and back. The browser only gets one HttpOnly, SameSite=Strict session cookie. The tokens stay on the server, encrypted, in Postgres.

  • Sessions end after 48 hours unused, or 30 days at most, or when you sign out.
  • Over https://, the cookie is Secure and __Host- prefixed. Over plain http:// it is neither, and the server logs a warning. Plain http is fine on localhost only.

The session settings are the CAMPBOOKS_BFF__* block, listed in Configuration.

Sign in with Google, Microsoft or Zoho​

Each provider is optional. It appears on the sign-in screen once you give it a client ID and a client secret. Without any, people can still use a passkey.

For each provider you want:

  1. Register an OAuth app in the provider's console, with this redirect URI (<provider> is google, microsoft or zoho):

    ${CAMPBOOKS_PUBLIC_URL}/auth/callback/<provider>
  2. Put the client ID in .env as CAMPBOOKS_GOOGLE__CLIENT_ID, CAMPBOOKS_MICROSOFT__CLIENT_ID or CAMPBOOKS_ZOHO__CLIENT_ID.

  3. Put the client secret in a file in deploy/secrets/: google-client-secret, microsoft-client-secret or zoho-client-secret. Never put secrets in .env. Compose mounts the folder read-only into the server at /run/secrets/campbooks, and the server runs as uid 10001:

    sudo chown 10001:10001 secrets/google-client-secret
    sudo chmod 0400 secrets/google-client-secret

    Docker Desktop on macOS or Windows does not need the chown.

  4. Point the server at the file in .env, for example:

    CAMPBOOKS_GOOGLE__CLIENT_ID=your-client-id
    CAMPBOOKS_GOOGLE__CLIENT_SECRET_FILE=/run/secrets/campbooks/google-client-secret
  5. Apply it:

    docker compose up -d

Provider notes:

  • Google: application type Web application. It is the same OAuth client that connects Gmail, so add the profile scope to its consent screen. Publish the app, because an app in Testing issues refresh tokens that expire after 7 days. Until Google verifies the app, people see its "unverified app" screen when they sign up.
  • Microsoft: personal, work and school accounts. In the Microsoft Entra admin center, register an app and add a Web redirect URI. CAMPBOOKS_MICROSOFT__TENANT (default common) narrows who may sign in: organizations, consumers or one tenant ID. Microsoft does not verify the email it reports, so on an invite_only instance it counts as verified only if you add the optional claim xms_edov to the ID token.
  • Zoho: in the Zoho API console, add a Server-based application and turn on Multi-DC, so one client works for every data centre. Without Multi-DC, set CAMPBOOKS_ZOHO__ACCOUNTS_SERVER to your app's data centre, for example https://accounts.zoho.eu.

The same Google and Zoho clients also connect mailboxes. See Connecting mailboxes.

To rotate a secret, replace the file and run docker compose up -d.

If your OAuth app already registered another callback path, set CAMPBOOKS_<PROVIDER>__REDIRECT_PATH and have your reverse proxy rewrite that path to /auth/callback/<provider>. Leave it unset for a new app.

Accounts and linking​

  • An account is linked to a provider account by its ID, never by email address. Signing in with a provider account that Campbooks does not know offers to create a new account.
  • Once signed in, a person can add more ways in under Settings, then Ways to sign in. The last way in cannot be removed.

Behind a reverse proxy​

Sign-in is rate-limited per client address. Behind a proxy, every request seems to come from the proxy, and all clients share one limit. Set CAMPBOOKS_TRUSTED_PROXIES in .env to the proxy's address or network, as comma-separated addresses or CIDR blocks:

CAMPBOOKS_TRUSTED_PROXIES=172.18.0.0/16

Workspaces and signup policy​

The first person to sign in creates the first workspace and invites the others from Settings, then Members. Who else may create a workspace is CAMPBOOKS_SIGNUP__POLICY:

ValueWhat happens
open (default)Anyone with an account may create a workspace.
invite_onlyNo public signup. Only people with an invitation get an account.
approvalAsking for a workspace records a request. Nobody is let in until it is approved.
codeCreating a workspace needs a signup code from CAMPBOOKS_SIGNUP__CODES.

The same policy decides whether Google, Microsoft and Zoho create accounts for new people. The instance's first user may always create a workspace, so on a fresh instance sign in yourself before you share the address.

Invitations are not emailed yet. The inviter gets the link once, right after inviting, and sends it on. The link is built from CAMPBOOKS_PUBLIC_URL, so set that to the address people use.

Use an outside identity provider​

This is advanced, and nothing is provisioned for it. Setting CAMPBOOKS_AUTH__ISSUER to an outside OpenID Connect issuer makes the API trust that issuer's tokens. Also set CAMPBOOKS_AUTH__JWKS_URL and CAMPBOOKS_AUTH__AUDIENCE. The web app then signs in through it with CAMPBOOKS_BFF__CLIENT_SECRET (or CAMPBOOKS_BFF__CLIENT_SECRET_FILE).

While you do, Campbooks' own sign-in, ways to sign in, apps and mailbox connection are off. Check these settings against your provider's documentation.