Platform
ScaiWave ScaiGrid ScaiCore ScaiBot ScaiDrive ScaiKey Models Tools & Services
Solutions
Organisations Developers Internet Service Providers Managed Service Providers AI-in-a-Box
Resources
Support Documentation Blog Downloads
Company
About Research Careers Investment Opportunities Contact
Log in

Federation handshake fails

Symptom: Invite POST returns 4xx#

You try to invite a foreign user; the POST to your local API returns an error or the foreign side returns 4xx.

SW_FED_PEER_UNKNOWN#

Your server doesn't know the foreign server (or vice versa). Either:

  • Add the peer to allowed_peers in your federation policy.
  • Or set default_mode: "open" if you trust open peering.
bash
1
2
3
curl -X PUT https://your-host/v1/admin/federation/policy \
  -H "Authorization: Bearer $ADMIN" \
  -d '{"allowed_peers": ["peer.example.com"]}'

The foreign side needs the same setup pointed at your host.

SW_FED_SIGNATURE_MISMATCH#

The event arrived with a bad signature. Possible causes:

  • Foreign server rotated its key, your server has the old one cached. Refresh the foreign participant's profile:

    bash
    1
    2
    curl -X POST https://your-host/v1/admin/federation/foreign/$FED_PARTICIPANT_ID/refresh \
      -H "Authorization: Bearer $ADMIN"
    
  • Time skew between servers. Federation signatures include a timestamp; if clocks drift > 60s, signatures appear invalid. Sync NTP on both sides.

  • TLS chain on the well-known endpoint changed. Your server fetches /.well-known/scaiwave/server over TLS to get the public key; if their cert chain has a chain issue your server won't trust the descriptor.

SW_FED_PROTOCOL_VERSION#

The two servers run incompatible protocol versions. Federation is versioned (v1, future v2); both sides must speak at least one common version. Check:

bash
1
2
curl https://your-host/.well-known/scaiwave/server | jq .protocol_versions
curl https://peer.example.com/.well-known/scaiwave/server | jq .protocol_versions

Intersection must be non-empty.

Symptom: Invite accepted but no events flow#

Foreign user is in the member list but their messages don't appear (or yours don't reach them).

  • Check GET /v1/admin/federation/peers — the row for the peer has last_error and last_seen. If last_error is set, that's the reason.
  • The relay worker may be stuck. Restart the ARQ worker pods.
  • The foreign side may have you on a deny list. Their admin checks their policy.

Symptom: Backfill returns empty#

bash
1
curl -X POST https://your-host/v1/admin/rooms/$ROOM_ID/federation/backfill

Returns 200 with 0 events. Causes:

  • Their server's policy refuses backfill to your server (their max_backfill_events_per_request is 0, or their policy hides history).
  • The room isn't federated on their side (only on yours, by accident). Both sides have to set the per-room federate flag.

Symptom: Federation entirely silent#

You set everything up; no errors, no events flow.

GET /v1/admin/federation/peers shows the peer with events_sent_24h: 0, events_received_24h: 0. Likely:

  • TLS handshake to the peer is failing silently. Check your server's outbound logs for https://peer.example.com requests.
  • The peer's /well-known is reachable but their /send endpoint returns 404 (e.g. they removed the federation feature). They'd need to check.

Where to look#

Logs: federation.* events. Useful greppable names:

  • federation.send.success / federation.send.failed.
  • federation.signature_verify_failed.
  • federation.peer_discovery_failed.
  • federation.policy_rejected.

The federation event audit also has a row per refused / accepted event in sw_audit under action = federation.*.

Updated 2026-05-17 13:10:03 View source (.md) rev 3