The original report claimed an onboarded user's refresh token doesn't persist and that this blocks all second users. That is false. Ground-truth DB inspection:
Jonas's real account 29e6f18b (Authentik, subject = jonas.eiemarker@gmail.com, connected 2026-06-09 17:10) has an active YouTube connection and 255 videos discovered. Multi-user discovery works. His momentary "no videos" was a timing gap — the screenshot was taken ~4 min after connecting, before the next 2h scheduler pass ran. A manually-triggered pass populated his 255 videos. → the durable fix for that gap is #6 (trigger discovery on connect).
The ref not found error in the logs is a different, stale account, not Jonas.
The two real (lower-severity) issues
A. Scheduler runs discovery for connection-less users → spurious token errors
store.ListAllUsers (internal/adapters/store/identity.go:47) returns everyuser_identities row, and the scheduler builds a per-user runner for each — even users with no YouTube connection. That runner still attempts resolve youtube oauth token: youtube/<uid>/refresh_token → secrets: ref not found, logged as a WARN every pass. Noise, and it actively misled this debug.
Fix: before running a user's discovery pass, skip users with no active video_connections row (or no resolvable token ref). Downgrade the genuine "connected but token missing" case to a clear, single signal rather than a recurring per-pass error.
B. Dex→Authentik left an orphan tapir user
user_identities has a stale row: subject CiQ…SBWxvY2Fs (decodes to a Dex local-connector subject, internal id 3a1c3159…) → user fef8adf1…, created 2026-06-07 (pre-migration), now with 0 connections, 0 videos. It's a leftover from the Dex era; the same human (if any) re-onboarded under a fresh Authentik identity, leaving the Dex users row orphaned.
Fix: audit user_identities for Dex-subject rows (the Ci… protobuf format vs Authentik's email/uuid subjects); decide per row: delete the empty orphan, or merge if it carries data. Confirm no active human has split data across a Dex account + an Authentik account. Generalises the cobalt-dingo subject-change lesson to tapir's own user table.
Net
Multi-user tapir is functional (proven: 255 videos for a second user). These are cleanup + a missing-token UX signal, not a blocker. Severity downgraded from the original.
## CORRECTED (original framing was wrong)
The original report claimed an onboarded user's refresh token doesn't persist and that this blocks all second users. **That is false.** Ground-truth DB inspection:
- **Jonas's real account `29e6f18b`** (Authentik, subject = `jonas.eiemarker@gmail.com`, connected 2026-06-09 17:10) has an **active** YouTube connection and **255 videos** discovered. Multi-user discovery works. His momentary "no videos" was a **timing gap** — the screenshot was taken ~4 min after connecting, before the next 2h scheduler pass ran. A manually-triggered pass populated his 255 videos. → the durable fix for that gap is #6 (trigger discovery on connect).
The `ref not found` error in the logs is a **different, stale account**, not Jonas.
## The two real (lower-severity) issues
### A. Scheduler runs discovery for connection-less users → spurious token errors
`store.ListAllUsers` (`internal/adapters/store/identity.go:47`) returns **every** `user_identities` row, and the scheduler builds a per-user runner for each — even users with **no YouTube connection**. That runner still attempts `resolve youtube oauth token: youtube/<uid>/refresh_token` → `secrets: ref not found`, logged as a WARN every pass. Noise, and it actively misled this debug.
**Fix:** before running a user's discovery pass, skip users with no active `video_connections` row (or no resolvable token ref). Downgrade the genuine "connected but token missing" case to a clear, single signal rather than a recurring per-pass error.
### B. Dex→Authentik left an orphan tapir user
`user_identities` has a stale row: subject `CiQ…SBWxvY2Fs` (decodes to a **Dex local-connector** subject, internal id `3a1c3159…`) → user `fef8adf1…`, created 2026-06-07 (pre-migration), now with **0 connections, 0 videos**. It's a leftover from the Dex era; the same human (if any) re-onboarded under a fresh Authentik identity, leaving the Dex `users` row orphaned.
**Fix:** audit `user_identities` for Dex-subject rows (the `Ci…` protobuf format vs Authentik's email/uuid subjects); decide per row: delete the empty orphan, or merge if it carries data. Confirm no active human has split data across a Dex account + an Authentik account. Generalises the cobalt-dingo subject-change lesson to tapir's own user table.
## Net
Multi-user tapir is **functional** (proven: 255 videos for a second user). These are cleanup + a missing-token UX signal, not a blocker. Severity downgraded from the original.
mathias
changed title from bug(connect): 2nd user's YouTube connection has no usable refresh token — discovery fails ref-not-found to bug(scheduler): discovery runs for connection-less users -> spurious token errors; + stale Dex-era orphan user2026-06-09 18:44:56 +00:00
runDiscoveryPass now calls ConnectionsForUser and skips users with no video connection before running their pass, so the scheduler no longer attempts a YouTube token for connection-less identities (e.g. the stale Dex-era orphan fef8adf1). TDD: TestDiscoveryPassSkipsUsersWithoutConnections (red→green); task check green (fmt/vet/lint/tests). No change to connected users. Deploys via CI → Flux.
Part B still open — clean up the orphan user_identities row (CiQ…SBWxvY2Fs → fef8adf1, Dex local subject, 0 connections/0 videos) and audit for any other Dex-subject rows left by the Authentik migration. Leaving this issue open for B.
**Part A done** — `c5f556d` on `main`.
`runDiscoveryPass` now calls `ConnectionsForUser` and **skips users with no video connection** before running their pass, so the scheduler no longer attempts a YouTube token for connection-less identities (e.g. the stale Dex-era orphan `fef8adf1`). TDD: `TestDiscoveryPassSkipsUsersWithoutConnections` (red→green); `task check` green (fmt/vet/lint/tests). No change to connected users. Deploys via CI → Flux.
**Part B still open** — clean up the orphan `user_identities` row (`CiQ…SBWxvY2Fs` → `fef8adf1`, Dex local subject, 0 connections/0 videos) and audit for any other Dex-subject rows left by the Authentik migration. Leaving this issue open for B.
Part A (skip discovery for connection-less users) shipped in v0.9.0 — deployed, verified live: zero fef8adf1 ref-not-found errors on the new pod. Part B (clean up the stale Dex-era orphan user_identities row) remains open. Related: #3 (a different orphan, 2b85ade1, with videos but no identity) — same cleanup theme, worth bundling.
Part A (skip discovery for connection-less users) shipped in v0.9.0 — deployed, verified live: zero fef8adf1 ref-not-found errors on the new pod. Part B (clean up the stale Dex-era orphan user_identities row) remains open. Related: #3 (a different orphan, 2b85ade1, with videos but no identity) — same cleanup theme, worth bundling.
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
CORRECTED (original framing was wrong)
The original report claimed an onboarded user's refresh token doesn't persist and that this blocks all second users. That is false. Ground-truth DB inspection:
29e6f18b(Authentik, subject =jonas.eiemarker@gmail.com, connected 2026-06-09 17:10) has an active YouTube connection and 255 videos discovered. Multi-user discovery works. His momentary "no videos" was a timing gap — the screenshot was taken ~4 min after connecting, before the next 2h scheduler pass ran. A manually-triggered pass populated his 255 videos. → the durable fix for that gap is #6 (trigger discovery on connect).The
ref not founderror in the logs is a different, stale account, not Jonas.The two real (lower-severity) issues
A. Scheduler runs discovery for connection-less users → spurious token errors
store.ListAllUsers(internal/adapters/store/identity.go:47) returns everyuser_identitiesrow, and the scheduler builds a per-user runner for each — even users with no YouTube connection. That runner still attemptsresolve youtube oauth token: youtube/<uid>/refresh_token→secrets: ref not found, logged as a WARN every pass. Noise, and it actively misled this debug.Fix: before running a user's discovery pass, skip users with no active
video_connectionsrow (or no resolvable token ref). Downgrade the genuine "connected but token missing" case to a clear, single signal rather than a recurring per-pass error.B. Dex→Authentik left an orphan tapir user
user_identitieshas a stale row: subjectCiQ…SBWxvY2Fs(decodes to a Dex local-connector subject, internal id3a1c3159…) → userfef8adf1…, created 2026-06-07 (pre-migration), now with 0 connections, 0 videos. It's a leftover from the Dex era; the same human (if any) re-onboarded under a fresh Authentik identity, leaving the Dexusersrow orphaned.Fix: audit
user_identitiesfor Dex-subject rows (theCi…protobuf format vs Authentik's email/uuid subjects); decide per row: delete the empty orphan, or merge if it carries data. Confirm no active human has split data across a Dex account + an Authentik account. Generalises the cobalt-dingo subject-change lesson to tapir's own user table.Net
Multi-user tapir is functional (proven: 255 videos for a second user). These are cleanup + a missing-token UX signal, not a blocker. Severity downgraded from the original.
bug(connect): 2nd user's YouTube connection has no usable refresh token — discovery fails ref-not-foundto bug(scheduler): discovery runs for connection-less users -> spurious token errors; + stale Dex-era orphan userPart A done —
c5f556donmain.runDiscoveryPassnow callsConnectionsForUserand skips users with no video connection before running their pass, so the scheduler no longer attempts a YouTube token for connection-less identities (e.g. the stale Dex-era orphanfef8adf1). TDD:TestDiscoveryPassSkipsUsersWithoutConnections(red→green);task checkgreen (fmt/vet/lint/tests). No change to connected users. Deploys via CI → Flux.Part B still open — clean up the orphan
user_identitiesrow (CiQ…SBWxvY2Fs→fef8adf1, Dex local subject, 0 connections/0 videos) and audit for any other Dex-subject rows left by the Authentik migration. Leaving this issue open for B.Part A (skip discovery for connection-less users) shipped in v0.9.0 — deployed, verified live: zero fef8adf1 ref-not-found errors on the new pod. Part B (clean up the stale Dex-era orphan user_identities row) remains open. Related: #3 (a different orphan, 2b85ade1, with videos but no identity) — same cleanup theme, worth bundling.