v2.5.3
v2.5.3
Follow-up to v2.5.2. Completes the ABI-compatibility work begun in v2.5.2: the audit that should have run before v2.5.2 surfaced one more Jellyfin manager property accessed via a statically-bound IL call — the dashboard would have re-broken on Jellyfin 10.11.9+ from a different line within the same endpoint. v2.5.3 shims that and verifies every other injected-manager access in the codebase is already on stable ground. In-place upgrade. 254/254 tests pass.
Fix
-
ISessionManager.Sessionsreflection shim — theGetDashboardOverviewendpoint reaches_sessionManager.Sessions.Count()to populate the "active sessions" KPI. The active-sessions admin endpoint (POST /Sessions/{id}/Revoke) reaches_sessionManager.Sessionsto look up by id. TheGET /MySessionsendpoint reaches it to enrich device records with live-session activity. All three were direct property accesses onISessionManager.Sessions— the exact same risk class as theIUserManager.Usersissue patched in v2.5.2. Between Jellyfin 10.11.8 and 10.11.9+, the property's return type changed, so the IL-emitted callvirt would throwSystem.MissingMethodException: Method not found: 'IEnumerable<SessionInfo> ISessionManager.get_Sessions()'at runtime on a 10.11.9+ host.In practice, this meant v2.5.2's dashboard fix was incomplete — a 10.11.10 server would have thrown on line 3543 (Users) BEFORE v2.5.2 and would have thrown on line 3679 (Sessions) AFTER v2.5.2. The dashboard endpoint still returned "Failed to load dashboard," just from a different line. v2.5.3 actually completes the fix.
New
TwoFactorAuthController.EnumerateSessions()private helper mirrors the existingEnumerateAllUsers()pattern:typeof(ISessionManager).GetProperty(nameof(Sessions)).GetValue(...)re-binds at runtime against whateverIEnumerableshape the running Jellyfin actually exposes. Items downcast toSessionInfo, with try/catch + empty-yield fallback so endpoints degrade gracefully instead of 500-ing.Patched callsites:
TwoFactorAuthController.GetDashboardOverviewactiveSessions KPITwoFactorAuthController.RevokeSessionadmin endpointTwoFactorAuthController.MySessionsdevice-enrichment endpoint
Comprehensive ABI audit (verified clean)
A full audit was run on every direct call to Jellyfin injected manager interfaces. Findings classified by risk:
| Surface | Callsites | Risk class | Status |
|---|---|---|---|
_userManager.Users (property) |
0 | HIGH | Fixed v2.5.2 |
_sessionManager.Sessions (property) |
0 | HIGH | Fixed v2.5.3 |
_userManager.GetUserById/Name/UpdateAsync/CreateAsync (methods) |
36 | low | Stable signatures across 10.11.x |
_sessionManager.AuthenticateNewSession/Logout/ReportSessionEnded/SessionStarted |
11 | low | Stable signatures across 10.11.x |
_deviceManager.GetDevices(DeviceQuery) (method) |
9 | low | Stable signature across 10.11.x |
_appHost.Resolve<T>() (generic method) |
2 | low | Stable across all Jellyfin versions |
_httpContextAccessor.HttpContext |
3 | none | ASP.NET Core, not Jellyfin ABI |
User.HasPermission(PermissionKind) (extension) |
6 | low | Stable extension signature |
After the v2.5.3 patch, zero direct property accesses remain on injected Jellyfin manager interfaces. All risky surfaces flow through reflection shims that re-bind at runtime regardless of the host's ABI patch level.
Verification
- 254/254 xUnit tests pass.
- Clean build with
TreatWarningsAsErrors=true— 0 warnings, 0 errors. - The
EnumerateSessions()helper is identical in pattern toEnumerateAllUsers()+StatsService.EnumerateUsers(), both of which have been in production for months across the entire 10.11.x release cadence.
Upgrade
In-place. No config / enrollment / OIDC / audit-log changes. Plugin supports Jellyfin 10.11.0 through current (10.11.10 confirmed working with v2.5.3) for every code path that depends on injected manager interfaces. Subsequent Jellyfin patches that further refactor return types of these properties (likely scenarios for 10.11.11+) will continue to work because reflection bypasses static IL binding.