Security

This section explains the configuration options and settings that affect the appliance’s security.

Rate Limits

To reduce the risk of brute-force and automated abuse of public (unauthenticated) REST endpoints, the system can enforce rate limits. A rate limit restricts how many requests a client can send within a defined time period. If the limit is exceeded, additional requests may be temporarily blocked or delayed. This helps protect service availability and performance, and it can make password guessing and similar attacks significantly harder.

The following rate limits apply:

  • Login failures

  • 2FA failures

  • Portal Signup & Password reset

  • PDF replies

Login failures

If the number of failed login attempts from the same IP address exceeds the allowed maximum, the admin or portal user will be temporarily blocked from signing in from that IP address.

Default: maximum 5 login failures in 300 seconds

Note

With IPv6, users can easily obtain many different IP addresses. For this reason, instead of blocking a single IP address, we block the entire /64 address range.

The default rate limits can be modified by using an Ansible override file Pro/Ent only

sudo vi /etc/ciphermail/ansible/group_vars/all/override.yml

Add the following YAML:

# admin login rate limits
ciphermail_backend__login_failure_max_failures: 5
ciphermail_backend__login_failure_lifetime_seconds: 300
# portal login rate limits
ciphermail_portal_backend__login_failure_max_failures: 5
ciphermail_portal_backend__login_failure_lifetime_seconds: 300

Change the values to match your requirements.

After changing Ansible override file, run the playbook:

sudo cm-run-playbook

2FA failures

If 2FA is enabled and the number of failed 2FA attempts exceeds the allowed maximum, the admin or portal user will be temporarily blocked from signing.

Default: maximum 4 2FA failures in 60 seconds

The default rate limits can be modified by using an Ansible override file Pro/Ent only

sudo vi /etc/ciphermail/ansible/group_vars/all/override.yml

Add the following YAML:

# admin 2FA rate limits
ciphermail_backend__2fa_failure_max_failures: 4
ciphermail_backend__2fa_failure_lifetime_seconds: 60
# portal 2FA rate limits
ciphermail_portal_backend__2fa_failure_max_failures: 4
ciphermail_portal_backend__2fa_failure_lifetime_seconds: 60

Change the values to match your requirements.

After changing Ansible override file, run the playbook:

sudo cm-run-playbook

Portal Signup & Password reset

Portal sign-up and password reset requests are limited to prevent abuse. If you exceed the allowed number of sign-up or password reset attempts, your account will be temporarily blocked from signing up or resetting your password.

To prevent excessive password reset emails, password reset requests from the same IP address are limited to a set rate.

Default: maximum 5 requests in 30 seconds per user or 60 requests in 60 seconds per IP address.

Note

With IPv6, users can easily obtain many different IP addresses. For this reason, instead of blocking a single IP address, we block the entire /64 address range.

The default rate limits can be modified by using an Ansible override file Pro/Ent only

sudo vi /etc/ciphermail/ansible/group_vars/all/override.yml

Add the following YAML:

# portal 2FA rate limits
ciphermail_backend__portal_rate_limit_max_attempts: 5
ciphermail_backend__portal_rate_limit_lifetime_seconds: 30
ciphermail_portal_backend__auth_ip_max_request_rate: 60
ciphermail_portal_backend__auth_ip_lifetime_seconds: 60

Change the values to match your requirements.

After changing Ansible override file, run the playbook:

sudo cm-run-playbook

Caution

If ciphermail_portal_backend__auth_ip_max_request_rate is set too low, or ciphermail_portal_backend__auth_ip_lifetime_seconds is set too high, legitimate users can be blocked from signing in. This can happen when the portal backend cannot see the user’s real external IP address and instead sees the same shared IP for many users. This situation is common in environments that use NAT (Network Address Translation) firewalls or a Web Application Firewall (WAF) with SSL/TLS termination. If these components do not correctly forward the original client IP address to the portal backend, many different users may appear to come from a single IP address. As a result, rate limits and IP-based blocking may be applied to everyone using that shared IP, potentially preventing all users from accessing the portal. To avoid this, make sure your reverse proxy, NAT device, or WAF is configured to forward the original client IP to the backend, and choose rate-limit and lifetime values that match your network setup and expected user traffic. For improved protection, apply rate limiting at your Web Application Firewall (WAF).

PDF replies

To prevent abuse, the number of PDF replies an external user can send is rate-limited.

Default: maximum 2 replies in 60 seconds per user.

The default rate limits can be modified by using an Ansible override file Pro/Ent only

sudo vi /etc/ciphermail/ansible/group_vars/all/override.yml

Add the following YAML:

# limits the rate at which PDF replies can be sent
ciphermail_portal_backend__pdf_max_reply_rate: 2
ciphermail_portal_backend__pdf_lifetime_seconds: 60

Change the values to match your requirements.

After changing Ansible override file, run the playbook:

sudo cm-run-playbook