Skip to content

Ticket import: persist rank, promote new device to Server#139

Open
passcod wants to merge 1 commit into
mainfrom
import-ticket-rank-trust
Open

Ticket import: persist rank, promote new device to Server#139
passcod wants to merge 1 commit into
mainfrom
import-ticket-rank-trust

Conversation

@passcod
Copy link
Copy Markdown
Member

@passcod passcod commented May 14, 2026

Summary

Two bugs in `Server::upsert_from_ticket` that meant operators had to fix things by hand after every import:

  1. Rank silently dropped. The function computed `rank` from the ticket (or the fallback argument) but never plugged it into the upsert's `.values()`/`.set()` clauses. Same story for `cloud` and `parent_server_id`. Fix: include them in both insert and update paths.
  2. Device left Untrusted. The device row created (or found) for the ticket's public key inherited the `Untrusted` default. The ticket is the operator's trust signal, so promote any Untrusted device to `Server` on import. Already-trusted devices (Admin, Releaser, Server) are not touched.

The update path now also re-applies kind/rank/cloud/parent_server_id so a re-import propagates ticket-side changes. Operator-edited state (`listed`, `geolocation`, `alert_when_down`) is preserved.

Tests

  • `upsert_from_ticket_persists_rank_and_trusts_device` — first import sets rank and device role.
  • `upsert_from_ticket_re_import_refreshes_rank` — a second import with a different rank updates it.
  • `upsert_from_ticket_preserves_higher_role_on_existing_device` — re-importing does not demote a manually-promoted Admin device.

…, and trusts the device

The previous upsert built a Server value with rank/cloud/parent_server_id
but never plugged them into the .values()/.set() clauses, so they were
silently dropped on import. Operators had to fix rank by hand every
time.

Likewise, the device created for the ticket's public key inherited the
DeviceRole::Untrusted default, leaving the operator to flip it to
Server manually. The ticket carries the operator's trust signal, so
promote any Untrusted device on import.

Update-on-conflict now re-applies all ticket-derived fields
(name, host, kind, rank, device_id, parent_server_id, cloud).
Operator-edited state (listed, geolocation, alert_when_down) is
preserved across re-imports.
@passcod passcod added this pull request to the merge queue May 14, 2026
@passcod passcod removed this pull request from the merge queue due to a manual request May 14, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant