Skip to content

Fix/epg collision - #224

Open
sparrowjack63 wants to merge 1 commit into
Davidona:developfrom
sparrowjack63:fix/epg-collision
Open

Fix/epg collision#224
sparrowjack63 wants to merge 1 commit into
Davidona:developfrom
sparrowjack63:fix/epg-collision

Conversation

@sparrowjack63

Copy link
Copy Markdown

Problem

The EPG guide displays the same programme on multiple unrelated channels
when the provider returns a non-unique epg_channel_id.

Some Xtream panels populate epg_channel_id poorly: dozens of unrelated
channels share a single placeholder value (the same id repeated across many
different channels). Each of these channels is correctly resolved to a
distinct external XMLTV xmltv_channel_id, yet the guide shows one
channel's programmes on all of them.

Root cause

getResolvedProgrammes() fetches programmes correctly (via the unique
xmltvChannelId for external, channelId for provider-native), but stores
them in the result map keyed by epgChannelId
:

val lookupKey = channel.epgChannelId?.trim()?.takeIf(String::isNotEmpty)
    ?: channel.streamId.takeIf { it > 0L }?.toString()
    ?: continue
result[lookupKey] = progs

When several channels share the same epgChannelId, they collide on the same
map entry — the last one processed wins, and every other channel inherits its
guide. The grid reads back with the same epgChannelId-first key
(Channel.guideLookupKey()), so the collision is consistent end to end.

Reproduction

  1. Provider returns the same epg_channel_id for several unrelated channels.
  2. Each channel is resolved to a distinct EXTERNAL xmltv_channel_id.
  3. Guide shows the same programme for all of them.

Example: two unrelated channels (say channel A and channel B) each map to
their own XMLTV entry with different programmes, but because both carry the
same provider epg_channel_id, the guide shows channel B's programme on
channel A as well.

Setting channels.epg_channel_id = NULL (without touching
channel_epg_mappings) immediately fixes the guide — isolating the key
collision as the cause.

Fix

Prefer streamId (always unique per channel within a provider) as the guide
lookup key, in both the producer (EpgResolutionEngine.getResolvedProgrammes,
external + provider blocks), the consumer (Channel.guideLookupKey), and the
playback path (getResolvedProgramsForPlaybackChannel).

epgChannelId is still used for provider-native programme joins
(ProgramDao.getForChannelsSync joins on channel_id = epgChannelId), so:

  • no schema change, no migration,
  • provider-native guide behaviour is preserved,
  • the change only affects the identity key used to bucket programmes per
    channel, never the lookup key used to fetch them.

Testing

  • ./gradlew testDebugUnitTest passes.
  • Verified on a real device: with the provider's duplicate epg_channel_id
    values intact in the DB, each channel now shows its own distinct programme.
    Before the patch, they shared one guide.

Fixes #210.

Prefer streamId (always unique per channel) as the guide lookup key.
epgChannelId is still used for provider-native programme joins, so no
schema change and provider-guide behaviour is preserved.

Fixes Davidona#210.
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