mirror of
https://github.com/4gray/iptvnator.git
synced 2026-10-10 18:36:15 -08:00
fix(stalker): key every session by endpoint, identity and credentials
Four review findings, all the same root cause — the session key was not applied consistently: - The in-run token cache still used an identity-only key, so editing the portal URL without restarting returned the cached token and sent that bearer to the newly configured host. Both caches now use one key. - Credentials were in neither key, so changing a status-2 portal's login kept serving the previous account's session indefinitely. - A stored token with NO recorded fingerprint was accepted. Rows written before the fingerprint existed carry exactly that, and re-presenting one after an edit is the disclosure the fingerprint prevents. Missing now counts as unverified; such a row owes a full profile anyway, so nothing is lost. - `StreamResolverService` read `playlist.isFullStalkerPortal` directly instead of the shared predicate, so a legacy row with an absent flag but a canonical URL skipped authentication — a restored older backup opened a direct-URL radio favorite with no Bearer header. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
1 parent
d2f28334de
commit
226ffbb9e6
7 files changed
+142
-46
No files matched your search
@@ -268,11 +268,17 @@ A renegotiated session is written back best-effort
|
||||
The handshake's `not_valid` flag is propagated into the follow-up
|
||||
`get_profile` as `not_valid_token`.
|
||||
|
||||
Reuse is gated on identity. The fingerprint the session was negotiated for is
|
||||
persisted next to the token (`Playlist.stalkerSessionIdentity`), and a token
|
||||
whose fingerprint no longer matches the playlist is never re-presented — an
|
||||
edited MAC, serial or device id must not inherit the previous session, which
|
||||
is the same rule the in-memory cache enforces for the current run.
|
||||
Reuse is gated on a session fingerprint (`stalkerSessionFingerprint`) covering
|
||||
the **portal origin, the device identity and the account credentials**, stored
|
||||
next to the token as `Playlist.stalkerSessionIdentity` and used for the
|
||||
in-run cache as well, so an edit applies without a restart. All three halves
|
||||
are load-bearing: `ensureToken()` re-presents tokens in a handshake, so an
|
||||
endpoint edit would otherwise disclose the previous portal's bearer token to
|
||||
another host; an identity edit must not inherit the old session; and for a
|
||||
status-2 portal the login decides which account the token represents. A token
|
||||
with no recorded fingerprint (written before this existed) counts as
|
||||
unverified and is never re-presented — such a row owes a full profile anyway,
|
||||
and the write-back then records the fingerprint.
|
||||
|
||||
Because that reuse skips the only response carrying the watchdog cadence, the
|
||||
cadence is persisted **with** the token (`Playlist.stalkerWatchdogTimeout` /
|
||||
|
||||
Reference in new issue
Block a user