# Redis

Native Redis, one per VPS, with its own ACL user, RDB persistence, TLS and external access limited by an IP allowlist.

Source: https://ardumaker.com/en/docs/redis/

- Category: Servers and infrastructure
- Status: Available
- Requirements: An active VPS with the `redis` feature available; If Redis already exists: version 6.0 or later
- MCP tools (Read only): `ver_catalogo_apps`, `ver_preflight_app`, `ver_app`, `ver_acceso_app`, `ver_operacion_app`
- MCP tools (Write or modify): `instalar_app`, `revelar_credencial_app`, `cambiar_lista_ip_app`, `controlar_app`, `reintentar_operacion_app`
- MCP tools (Destructive): `revocar_acceso_app`, `desinstalar_app`

## What can you do with it?

Redis is a single native engine per VPS and the app is the engine itself. ArduMaker installs it (or adopts the one already running), creates its own ACL user and, if requested, publishes it with TLS for certain IPs.

- Use it as a cache or queue from the VPS apps (`127.0.0.1:6379`).
- Start, stop or restart it.
- Reveal user, password and the `rediss://` URI.
- From the VPS Redis tab: statistics, memory, keys, size per database, last save, persistence, configuration and flushing.

## When should you use it?

- Cache, sessions or job queues of an app deployed on the same VPS.
- An external service that needs Redis with TLS from known IPs.

> **INFO:** The [n8n](https://ardumaker.com/en/docs/n8n) Docker stack brings its own Redis (`n8n-redis`), separate from this one.

## How does it work in ArduMaker?

1. Engine: if absent, it is installed once; if it already runs, it is adopted without reinstalling or changing version or password. A version older than 6.0 fails with `redis_no_soportado` without touching anything.
2. `app<id>_<hex>` credential with a random password, stored encrypted before touching the VPS.
3. `ACL SETUSER <user> reset on ~* &* +@all -@admin -@dangerous` with the password, through stdin; the admin password travels in `REDISCLI_AUTH`, never in `-a`. The `default` user is not touched.
4. It is persisted with `ACL SAVE` (if there is an `aclfile`) or `CONFIG REWRITE`.
5. Health as the app user: `PING`, `SET` of its own temporary key with `EX 60`, `GET` and `DEL`. It never lists nor reads customer keys.

Only `external_access` is accepted in `config`: Redis numeric databases do not isolate and are not offered. A second request on the same VPS answers `app_ya_existe` with the id of the existing one.

`config.external_access` decides whether the database is reachable from the internet: `{"ips": [...]}` opens it only to those IPs; `{"local": true}` (or `false`) keeps it inside the VPS. If omitted, the dashboard uses the installer's IP; over MCP the agent's IP does not count, so without `ips` the database stays local instead of failing.

## What actually changes?

| Installer setting | Value |
| --- | --- |
| `bind` | `127.0.0.1` |
| `port` | `6379` |
| `maxmemory` | `256mb` |
| `maxmemory-policy` | `allkeys-lru` |
| `save` | `900 1`, `300 10`, `60 10000` (RDB) |
| `appendonly` | `no` |
| TLS (if external access) | `tls-port 6380`, own certificate, `tls-auth-clients no` |

> **PRECAUCION:** With `allkeys-lru` and 256 MB, when memory fills up Redis evicts the least used keys. Good for caching; for data that must not be lost this has to be taken into account or the configuration adjusted.

## Internet access and IP allowlist

By default the engine listens only inside the VPS (6380 on `127.0.0.1`). To use the database from outside, ArduMaker publishes an endpoint of the engine: `db-<VPS id>` inside the platform zone (direct DNS record, no proxy), on a reserved port between 61000 and 64999. On the host, a proxy carries that port to the VPS 6380 and the firewall lets in only the IPs on the list.

For Redis the proxy points to `tls-port` 6380 with the certificate of the `db-<id>` name; plain 6379 is never published. Enabling TLS for the first time restarts Redis: it is done automatically only if Apps installed it; on an adopted one it waits for confirmation.

| List rule | Detail |
| --- | --- |
| Format | IPv4 or IPv6, with or without prefix; a single IP is /32 or /128. No names, loopback, link-local or multicast |
| Width | Minimum prefix /24 for IPv4 and /48 for IPv6 by default; `0.0.0.0/0` and `::/0` are rejected in the list |
| Size | Up to 20 entries; empty = closed to everyone |
| Host names | Up to 5 (`allowed_hosts`), with up to 8 public IPs each; re-resolved every 5 minutes, and a DNS failure keeps the last known value |
| Open to everyone | Only with `allow_any` and `confirm_open` together; the answer says so in `open_to_any` |

The list belongs to the engine, not to each database: changing it from any Redis database changes access for every database of that engine on that VPS (the answer says so with `shared_with_engine` and `affected_apps`).

1. Missing firewall rules are added, one per CIDR (`ufw allow from <cidr> to any port <port> proto tcp`).
2. Then the extra ones are removed and their open connections are cut.
3. Only then is the listener created and verified: rules equal to the list, no rule open to anyone, listener present and a TLS handshake with the right name.

> **INFO:** Adding before removing means the intermediate state is always the union of two valid lists: there is never a moment open to everyone. If verification fails, the listener is removed.

> **PRECAUCION:** Another VPS on the same host does not get through the public IP even if it is on the list: the connection times out. The answer warns with `warnings` (`mismo_host`); between two such VPS an SSH tunnel is used (`configurar_tunel_entre_vps`).

## Uninstalling, persistence and backups

- Without `delete_data` (the default): the app's own external access is closed and it stops being listed as installed, but the database, its user and its data stay on the VPS. The next reconciliation shows it as discovered. Nothing is lost.
- On Redis uninstalling always removes the ACL user Apps created (it is an access, not data). With `delete_data` it also flushes every key (`FLUSHALL`), unless that Redis holds an n8n queue. The engine stays installed.
- The engine is never uninstalled from Apps: it stays installed even with no databases.
- If the VPS or the engine do not answer, `desinstalar_app` with `forzar=true` tries each step once, removes the app and lists in `not_cleaned` what was left on the server.
- Data lives on the VPS disk and travels in its weekly backup, which is taken while the VPS is running. For a consistent copy of a specific database it is better to also make your own dump from the [database manager](https://ardumaker.com/en/docs/gestor-de-bases-de-datos) (export) or with the engine's tools.

> **PELIGRO:** With `delete_data` the uninstall is irreversible.

## Diagram

**Connections to Redis**

```text
App on the same VPS (`127.0.0.1:6379`)
  ↓
External client (`rediss://` to `db-<id>:<port>`)
  ↓
Host firewall and proxy (listed IPs only → VPS 6380)
  ↓
redis-server (TLS on 6380; plain 6379 is never published)
```

## Expected result

```text
rediss://app<id>_<hex>@db-<vps>.<zona>:<puerto>/0
```

The `rediss://<user>@<host>:<port>/0` URI appears without password once access is ready; it names database 0 (no numeric database is assigned per app).

## Errors and troubleshooting

| Error | Cause | Retry? |
| --- | --- | --- |
| `redis_no_soportado` | Redis older than 6.0 (no ACL nor `tls-port`) | No |
| `redis_usuario_no_creado` / `redis_salud_fallida` | `ACL SETUSER`, its persistence or the health check failed | Yes |
| `redis_usado_por_n8n` | That Redis holds the queue of an npm n8n: it is not published (the app stays installed) | No |
| `requiere_reinicio` | The first TLS restarts Redis; on an adopted Redis a person must confirm it | After confirming |
| `redis_control_fallido` | `start`, `stop` or `restart` did not finish well | Request the action again |
| `app_ya_existe` | There is already a Redis on that VPS | No |

## MCP access

The whole database lifecycle can be operated over MCP with the permissions of the person who authorized the agent. Reference at [/mcp/docs](https://ardumaker.com/en/mcp/docs) and [/mcp/bases-de-datos](https://ardumaker.com/en/mcp/bases-de-datos).

- Read: `ver_catalogo_apps`, `ver_preflight_app`, `listar_apps_empresa`, `ver_app`, `ver_acceso_app` (host, port, TLS and IP list, no secrets), `ver_operacion_app`.
- Modify: `instalar_app` with `app_type: redis` (requires `idempotency_key`), `cambiar_lista_ip_app` (only if its owner is an admin; IPs must be named explicitly: the agent's IP is not the person's), `reintentar_operacion_app`, `refrescar_apps`.
- Sensitive: `revelar_credencial_app` (admins only, no `idempotency_key`; the answer is marked `sensible: true` and the audit records that it was revealed, never the value).
- Destructive: `revocar_acceso_app` (closes external access for the whole engine) and `desinstalar_app` (with `delete_data` it erases data; requires `confirm_delete_data`).

To read and write data inside the database, the agent uses the [database manager](https://ardumaker.com/en/docs/gestor-de-bases-de-datos) tools. An agent authorized as read-only does not see the tools that modify and cannot reveal credentials.

Also, `controlar_app` accepts `start`, `stop` and `restart` on the Redis app. Keys and engine configuration are seen from the dashboard Redis tab: they have no MCP tool.

## Related features

- [PostgreSQL](https://ardumaker.com/en/docs/postgresql/)
- [n8n](https://ardumaker.com/en/docs/n8n/)
- [Firewall and ports](https://ardumaker.com/en/docs/firewall-y-puertos/)
- [SSH tunnels](https://ardumaker.com/en/docs/tuneles-ssh/)
- [Backups](https://ardumaker.com/en/docs/backups/)
