Complete the rpId migration of a connection
POST /v1/connections/{connection_id}:complete-rp-id-migration · permission connections:write
Ends the running rpId migration of a passkey connection before its window ends. The status becomes completed_early (or completed if the window had already ended), the passkeys still on the previous rpId are revoked (reason rp_id_changed), the previous rpId's origin stops being accepted and the passkey_rp_id.migration_completed event is published. This cannot be undone: users who have not registered a passkey on the new rpId must sign in another way.
Request
| Field | Type | Required | Description |
|---|---|---|---|
connection_id |
path | yes | Passkey connection ID (conn_…). |
Idempotency-Key |
header | no | Optional key that makes a retried request safe (16-64 characters). |
The body is optional; if present it must be {}.
Response
200 OK; the closed migration (see Get the rpId migration).
{
"id": "rpm_01j9xr4a6b8c0d2e4f6g8h0j2k",
"connection_id": "conn_01j9xp6q0r1s5t7v9w1x3y5z7b",
"previous_rp_id": null,
"new_rp_id": "login.example.com",
"status": "completed_early",
"started_at": "2026-10-27T10:00:00Z",
"ends_at": "2027-01-25T10:00:00Z",
"completed_at": "2026-12-01T09:00:00Z",
"revoked_count": 12,
"new_registration_count": 340,
"fallback_enabled_by_migration": false
}
Errors
| HTTP | code | When |
|---|---|---|
| 400 | unknown_field |
The body contains a field. |
| 404 | not_found |
The connection does not exist or belongs to another environment. |
| 409 | no_active_rp_id_migration |
The connection has no running rpId migration (for example, it was already completed). |
| 401 | unauthenticated |
The credential is missing, invalid or revoked. |
| 403 | insufficient_permissions |
The credential lacks the required permission. |
| 429 | rate_limited |
The rate limit was exceeded; retry after the Retry-After period. |
| 503 | service_unavailable |
The passkey counts could not be read, or another dependency is unavailable; the migration stays open. Retry after the Retry-After period. |
Example
curl -X POST "https://api.eu.keenauth.com/v1/connections/conn_01j9xp6q0r1s5t7v9w1x3y5z7b:complete-rp-id-migration" \
-H "Authorization: Bearer $KEENAUTH_SECRET_KEY"
keenauth connections complete-rp-id-migration conn_01j9xp6q0r1s5t7v9w1x3y5z7b --yes