Performance replication copies the primary cluster’s storage (except node-local paths) to one or more performance secondaries. A secondary serves reads locally and forwards writes to the primary. This lets you scale read traffic and place it closer to consumers.
Before you start
Before you configure Performance replication, prepare the following:
- Make sure both clusters run Stronghold EE with integrated Raft storage and that replication is enabled. For details, refer to Overview.
- Make sure the primary cluster port is reachable from the secondary and that you have the primary CA certificate for TLS.
- Prepare a token with permissions for
sys/replication/*on both clusters.
In the examples below ${PRIMARY_ADDR} and ${SECONDARY_ADDR} are the API
addresses of the clusters, and ${VAULT_TOKEN} is a token authorized for
sys/replication/*.
If you enable replication on a cluster that already holds data (for example,
after upgrading from a build without replication), or after a period with
replication disabled, the node re-indexes its storage on the first boot by
itself. You do not need to call sys/replication/reindex manually.
Step 1. Enable the primary
On the primary cluster, enable Performance replication in the primary mode:
- Stronghold in Deckhouse Platform
- Stronghold in Linux
d8 stronghold write -force sys/replication/performance/primary/enablestronghold write -force sys/replication/performance/primary/enableEnabling a primary restarts the core, and the node is unavailable for a few
seconds. Before continuing, wait until it responds again and
sys/replication/performance/status shows mode: primary.
Step 2. Create an activation token for the secondary
Generate a wrapping activation token for a specific secondary identified by
id:
- Stronghold in Deckhouse Platform
- Stronghold in Linux
d8 stronghold write sys/replication/performance/primary/secondary-token id=sec-1 ttl=24hstronghold write sys/replication/performance/primary/secondary-token id=sec-1 ttl=24hThe id parameter is required; ttl defaults to 30m. The command returns a
short-lived wrapping token in the wrap_info.token field — pass exactly this
token to the secondary.
Step 3. Enable the secondary
Provide the wrapping token from the previous step. For self-signed environments,
ca_file or ca_path (the primary CA in PEM format, read on the secondary
server) is required, otherwise the TLS connection to the primary cannot be
verified.
curl --header "X-Vault-Token: ${VAULT_TOKEN}" --request POST --data @secondary-enable.json "${SECONDARY_ADDR}/v1/sys/replication/performance/secondary/enable"Example secondary-enable.json:
{
"token": "<WRAPPING_TOKEN>",
"primary_api_addr": "<PRIMARY_API_ADDR>",
"ca_file": "<PRIMARY_CA_FILE>"
}Fields of secondary/enable:
token— required; the wrapping token from step 2.primary_api_addr— the primary address used to unwrap the token; required if the token does not contain anaddrclaim.ca_file/ca_path— path to a PEM file with the primary CA or to a directory of PEM files, read on the secondary server.client_cert_pem/client_key_pem— optional client certificate and key for the unwrap TLS connection.
After bootstrap the secondary wipes its own token store, so the secondary’s
original root token stops working. Log in through a replicated auth method
(for example, userpass) that was configured on the primary before
replication was enabled.
Step 4. Verify the status
Check the replication status on the secondary cluster:
- Stronghold in Deckhouse Platform
- Stronghold in Linux
d8 stronghold read -address="${SECONDARY_ADDR}" sys/replication/performance/statusstronghold read -address="${SECONDARY_ADDR}" sys/replication/performance/statusWhen the secondary is connected and pulling the WAL, state is stream-wals
and connection_state is ready. The secondary has caught up with the primary
when its last_wal reaches last_remote_wal.
Step 5. Verify data replication
Run the commands against the secondary with a token from the replicated auth method you logged in with in step 3 — the primary’s root token is not valid on the secondary.
- Stronghold in Deckhouse Platform
- Stronghold in Linux
# Write on the primary.
d8 stronghold kv put -address="${PRIMARY_ADDR}" secret/hello value=world
# Read on the secondary once it has converged.
d8 stronghold kv get -address="${SECONDARY_ADDR}" secret/hello
# A write on the secondary is forwarded to the primary and returns through the WAL.
d8 stronghold kv put -address="${SECONDARY_ADDR}" secret/fromsec value=1# Write on the primary.
stronghold kv put -address="${PRIMARY_ADDR}" secret/hello value=world
# Read on the secondary once it has converged.
stronghold kv get -address="${SECONDARY_ADDR}" secret/hello
# A write on the secondary is forwarded to the primary and returns through the WAL.
stronghold kv put -address="${SECONDARY_ADDR}" secret/fromsec value=1Path filters
A primary can selectively withhold specific mounts or namespaces from a specific
secondary. Filters are configured per secondary by id:
deny— replicate everything except the listed paths.allow— replicate only the listed paths.
The default mode is allow.
# Deny the mount blocked/ for sec-1.
curl --header "X-Vault-Token: ${VAULT_TOKEN}" --request POST --data '{"mode":"deny","paths":["blocked/"]}' "${PRIMARY_ADDR}/v1/sys/replication/performance/primary/paths-filter/sec-1"
# Read the filter.
curl --header "X-Vault-Token: ${VAULT_TOKEN}" "${PRIMARY_ADDR}/v1/sys/replication/performance/primary/paths-filter/sec-1"
# Read the expanded filter (the actual storage prefixes that will apply).
curl --header "X-Vault-Token: ${VAULT_TOKEN}" "${PRIMARY_ADDR}/v1/sys/replication/performance/primary/dynamic-filter/sec-1"
# Remove the filter.
curl --header "X-Vault-Token: ${VAULT_TOKEN}" --request DELETE "${PRIMARY_ADDR}/v1/sys/replication/performance/primary/paths-filter/sec-1"A filter change is applied live: when a path is added to deny (or removed from
allow), the primary streams an invalidation and the secondary drops the
previously allowed data; when the change is reversed, the data is replicated
again.
A performance secondary cannot be promoted while path filters are configured on it. Remove the filters first.
When a filtered mount is unmounted, remounted, or disabled, its storage prefix is automatically removed from all filters, so a stale entry does not govern a new mount at the same path.
Management operations
The table lists the commands for managing Performance replication:
| Action | Endpoint |
|---|---|
| Status | d8 stronghold read sys/replication/performance/status |
| Revoke a secondary | d8 stronghold write sys/replication/performance/primary/revoke-secondary id=sec-1 |
| Disable on the primary | d8 stronghold write -force sys/replication/performance/primary/disable |
| Disable on the secondary | d8 stronghold write -force sys/replication/performance/secondary/disable |
| Demote the primary | d8 stronghold write -force sys/replication/performance/primary/demote |
| Promote a secondary | d8 stronghold write -force sys/replication/performance/secondary/promote |
| Re-point a secondary | d8 stronghold write sys/replication/performance/secondary/update-primary token=<ACTIVATION_TOKEN> |
Notes:
revoke-secondaryalso removes the per-secondary filter, so it leaves no orphaned entries.- For
update-primary, when the new primary has a new identity (for example, a promoted former secondary), use the token method with a fresh activation token from the new primary. The address method (primary_cluster_addr) is only valid if the primary kept its identity.