Skip to content

Set a per-user feature-flag override

Use this runbook when you need to change a feature flag for one specific user — for example, to enable a beta capability for a pilot customer, or to disable a flag that’s misbehaving for a single account without touching the global default. The change applies at the user tier and overrides the registry default for every flag-eligible device that user owns.

  • An admin role on your operator account. Bearer tokens are rejected; you must be signed in with a cookie session.
  • The target user’s Polaris Express user ID. Find it from Admin → Users and copy the ID from the user detail page.
  • A clear idea of which flag key and value you intend to set. Unknown keys and values that fail the registry’s schema are rejected.
  • If a device-level override already exists for the same flag on one of this user’s devices, that device override will continue to win. Check Admin → Devices → Feature flags for the user’s devices first if you need the user-level value to take effect everywhere.
  1. Open the user's feature-flag panel

    From Admin → Users, search for the target user and open their detail page. Select the Feature flags tab.

  2. Locate the flag you want to override

    The panel lists every flag in the registry along with its current effective value for this user and the source of that value (registry default or user override). Find the row for the flag key you want to change.

  3. Set the override value

    Click Edit on the flag row. Enter the value you want — the form coerces it to the flag’s expected type (boolean, number, string, or JSON object) before submission. Click Save.

    Under the hood this issues a PATCH /api/admin/users/\{userId\}/feature-flags with a body of the form { flags: [{ key, value }] }. The value is validated against the flag’s Zod schema before anything is written. Up to 32 entries can be sent in a single request; if you submit duplicate keys, the last one wins.

  4. Clear an override (optional)

    To remove the user-level override and fall back to the registry default, click Clear override on the row. This sends { key, value: null }, which deletes the row from user_feature_flag_values. Any device-level override for the same key still applies on that device.

  1. The response from the save call returns { ok: true, flags: { … } } where flags is the post-write effective user-scoped map. The row in the panel should refresh to show the new value with source user override.
  2. Open the audit log (Admin → Audit) and filter by event user.feature_flags.changed. You should see an entry with the admin user ID who made the change, the target user ID, and the changedKeys and values in the metadata.
  3. If the user has flag-eligible devices (phone, tablet, or laptop NFC clients — chargers are excluded), those devices receive a device.feature-flags.changed SSE event and should reflect the new value on next reconnect. You can confirm in Admin → Devices → {device} → Live events.

Every successful PATCH writes a user.feature_flags.changed audit entry containing:

  • the admin user ID who made the change (changedByUserId),
  • the target user ID,
  • the list of changedKeys,
  • the new values for each key (with null for deletions),
  • the requesting IP and user agent,
  • the route /api/admin/users/[userId]/feature-flags.

To reverse a change:

  • If you set a value, edit the row again and either set it back to the previous value or click Clear override to fall back to the registry default.
  • If you cleared an override, re-save the previous value by editing the row. The audit log entry from the original write contains the prior values if you need to recover it.

There is no automatic undo. Reversal is a second PATCH, which produces its own audit entry.