Commit 9c90f1b8 authored by ale's avatar ale

Add a README

parent 6014a12f
Pipeline #652 passed with stages
in 59 seconds
auth-server
===========
A low-level authentication server with pluggable backends and some
advanced features:
* two-factor authentication support (TOTP, U2F)
* application-specific passwords
* rate limiting and brute force protection
* new device detection
Its purpose is to be the single point of authentication for all
authentication flows in a service.
# Deployment
The auth-server is fully stateless: it delegates state to other
backends such as Memcached for short-term storage, and
[usermetadb](https://git.autistici.org/id/usermetadb) for long-term
anonymized user activity data. For this reason, it is recommended to
install an auth-server on every host.
It listens for authorization requests over a UNIX socket. UNIX
permissions should be used to control access to the socket if
necessary. Clients speak a custom simple line-based attribute/value
protocol, and can send multiple requests over the same connection.
## Services
A *service* in auth-server is a specific scope for an authentication
workflow, normally associated with a specific user-facing
service. Multiple services can be defined, each with its own
functionality and user backends.
## User backends
The authentication server data model is based on the concept of a
*user account*. The server knows how to retrieve user accounts stored
in LDAP, but it has to be told the specific details of how to find
them and how to map the information there to what it needs.
# Configuration
The behavior of auth-server can be configured with a YAML file.
The YAML file should contain a dictionary with the following attributes:
* `services` is a dictionary describing all known services and their
authentication parameters. See the *Service definition* section below
* `rate_limits` defines the global rate limiters and blacklists. See
the *Rate limiting* section below.
* `enabled_backends` is the list of user backends that should be
enabled (the available backends are *file* and *ldap*)
* `ldap_config` specifies the configuration for the LDAP backend --
see the *LDAP Backend* section below
* `user_meta_server` holds the configuration for the user-meta-server
backend:
* `backend_url` is the URL of the service
* `tls_config` configures TLS for the client:
* `cert` is the path to the client certificate
* `key` is the path to the client private key
* `ca` is the path to the CA store to verify the server certificate
## Rate limiting
Rate limits and blacklists are global (available to all services), to
allow brute force protection to work across multiple services. The
top-level configuration attribute `rate_limits` is a dictionary of
named rate limiting configurations, that can be later referenced in
the service-specific `rate_limits` list. Each rate limiter definition
should specify the following attributes:
* `limit` counts the number of events to allow over a period of time
* `period` defines the period of time
* `blacklist_for` adds the client to a blacklist if their request rate
goes above the specified threshold
* `on_failure` is a boolean value, when true the rate limiter will
only be applied to failed authentication requests
* `keys` is a list of strings specifying the request identifiers that
will make up the rate limiter key. The list can include one or both
of *ip* (referring to the remote client's IP) and *user* (username)
## Service definition
Each service definition is a dictionary with the following attributes:
* `backends` is a list of user backend specifications, each one should
include a backend-specific configuration under an attribute named
after the backend itself:
* `file` is simply a path to a user list file, see the *File
backend* section below
* `ldap` configues the LDAP backend for this service
* `challenge_response` is a boolean parameter that, when true, enables
two-factor authentication for this service (it should be enabled
only for interactive services)
* `enforce_2fa` is a boolean flag that, when true, will disable
non-2FA logins for this service
* `enable_device_tracking` is a boolean flag that enables device
tracking for this service (assuming the client provides device
information)
* `rate_limits` is a list of names of global rate limiters to be
applied to this service.
## File backend
The *file* backend reads users and their credentials from a
YAML-encoded file. This file should contain a list of dictionaries,
each representing a user, with the following attributes:
* `name` is the username
* `email` is the email associated with the user (optional)
* `password` stores the encrypted password
* `totp_secret` stores the *unencrypted* TOTP secret seed
* `groups` is a list of group names that the user belongs to
The file backend only supports TOTP as a two-factor authentication
method, U2F support is currently missing.
## LDAP Backend
The *ldap* backend will look up user information in a LDAP database.
### Query definition
LDAP queries are meant to return a single user account object from the
database using a *search* operation. There's two parts to it: first
the right object needs to be located, then we need to map the object's
attributes to someting that the auth-server understands.
The LDAP query for a service is defined by the following standard LDAP
parameters:
* `search_base` specifies a base DN for the search
* `search_filter` specifies a filter to apply to the search
* `scope` specifies the scope of the LDAP search, must be one of
*base*, *one* or *sub*
* `attrs` is a dictionary mapping LDAP attributes to their auth-server
metadata counterparts, see *Schema definition* below.
The `search_filter` should contain somewhere the literal string `%s`,
which will be replaced with the username in the final LDAP query.
### Schema definition
In order to retrieve authentication information from the LDAP object,
the authentication server needs to know which attributes to use. To do
so, we use a so-called *schema definition* (a map of symbolic names to
LDAP attributes). The following attribute names are defined:
* `password` contains the encrypted password. Since this attribute is
often also used for authentication of the LDAP protocol itself, an
eventual `{crypt}` prefix is ignored. Passwords should be encrypted.
* `otp_secret` should contain the hex-encoded TOTP secret
* `app_specific_password` (possibly repeated) contains an encrypted
app-specific password
The default attribute mapping looks like this:
password: userPassword
totp_secret: totpSecret
app_specific_password: appSpecificPassword
Except for *userPassword*, the others are custom LDAP attributes and
are not part of any standard schema definition. You should create your
own.
App-specific passwords should be encoded as colon-separated strings:
service:encrypted_password:comment
The password should be encrypted. The comment is a free-form string
set by the user to tell the various credentials apart.
## OTP implementation
The authentication server uses a very simple implementation of
time-based OTP (TOTP), supporting a single secret per user and without
any fancy features such as emergency tokens etc. The reason for this
is that TOTP authentication requires just plain read-only access to
the user database, while counter-based authentication with proper
token revocation is a read-write, locked operation which is more
difficult to perform on a LDAP backend.
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment