Skip to content

Quickstart

masks is an OpenID Connect and OAuth 2.0 provider. Run it as a container or inside a Rails app, then sign people in to your apps against it. Each section links to its full guide.

masks ships as a container image that needs one Postgres database. It migrates itself on boot.

services:
masks:
image: ghcr.io/masksrb/masks:latest
environment:
POSTGRES_HOST: postgres
POSTGRES_USER: masks
POSTGRES_PASSWORD: ...
POSTGRES_DATABASE: masks
MASKS_MIGRATION_USER: masks_owner
MASKS_MIGRATION_PASSWORD: ...
MASKS_TENANT: acme
MASKS_PUBLIC_ORIGIN_TEMPLATE: https://auth.example.com
volumes:
- masks-storage:/rails/storage
depends_on:
- postgres
postgres:
image: postgres:17-alpine
environment:
POSTGRES_USER: postgres
POSTGRES_PASSWORD: ...
volumes:
- postgres:/var/lib/postgresql/data
- ./initdb:/docker-entrypoint-initdb.d:ro
volumes:
postgres:
masks-storage:

initdb/01-roles.sql creates the role that owns the schema and the role that serves requests:

CREATE ROLE masks_owner WITH LOGIN PASSWORD '...' CREATEDB;
CREATE ROLE masks WITH LOGIN PASSWORD '...';

masks migrates as the first and serves as the second, so the role answering requests cannot switch off the row-level security that keeps tenants apart.

Put a TLS proxy in front of port 3000, open the public origin, and set up the first account with the setup token masks prints in its logs. The first account holds masks:manage and can open /manage. The masks-storage volume holds the generated master key, which every encrypted column depends on, so back it up with the database.

See Self-hosting for TLS, image tags, database roles, secrets, and tenants.

The masks gem signs people in to your app against a masks server that runs somewhere else:

gem "masks"
Terminal window
bin/rails generate masks:install --resource https://app.example.com

--resource is a URL on your app’s own origin, which the handshake registers the app for. Set MASKS_ISSUER to your masks server, start the app, and open /auth/handshake to connect it. Then require a signed-in person in any controller:

class ApplicationController < ActionController::Base
include Masks::Rails::Authentication
before_action :authenticate_masks!
end

To run masks inside your app instead, the masks-server gem mounts it as an engine:

gem "masks-server"
Terminal window
bin/rails generate masks:server:install --at /auth

See Rails apps for client, server, and engine mode.

@masks/client signs people in from a single-page app in the browser:

Terminal window
npm install @masks/client

Session mode talks to a backend running Masks::Rails, which keeps the tokens and gives the browser a cookie:

import { createSession } from "@masks/client";
const auth = createSession({ basePath: "/auth" });
const account = await auth.session();
if (!account) auth.login({ returnTo: "/dashboard" });

Browser mode runs the code flow with PKCE in the page, for an app with no backend. It needs a public client, one registered with token_endpoint_auth_method set to none:

import { createBrowserClient } from "@masks/client";
const auth = createBrowserClient({
issuer: "https://auth.example.com",
clientId: "...",
redirectUri: "https://app.example.com/callback",
scope: ["openid", "profile"],
});
if (auth.pending()) await auth.callback();
else await auth.authorize({ returnTo: "/dashboard" });

See Connecting via SDK for what each SDK covers, and the @masks/client reference.

The repository runs a full stack with ./dev, which needs Docker with Compose, and Ruby.

Terminal window
git clone https://github.com/masksrb/masks.git
cd masks
./dev

masks answers at http://masks.localhost:12345, and this documentation at http://masks.localhost:12346. The dev stack’s setup token is masks-dev. ./dev reset deletes the database and brings back the first-run screen.

  • Core concepts explains tenants, clients, scopes, and namespaces.
  • Features covers clients, signing in, and signing out.
  • SSO / SAML signs people into SAML applications and provisions them over SCIM.
  • Security describes what masks protects and how.
  • OIDC and OAuth lists the specifications masks implements, and the GraphQL reference documents the manage API.