Skip to content

Commit

Permalink
Fix guessit parsing numbered episode titles as multi season (#8413)
Browse files Browse the repository at this point in the history
* Fix guessit parsing numbered episode titles as multi season

* Bring back old rules

* Add stricter rules

* Make less strict

* More strict again

* Magic

* Add blankies

* some more

* Add tests

* add ext
  • Loading branch information
medariox authored Aug 30, 2020
1 parent 7248052 commit e3c1088
Show file tree
Hide file tree
Showing 2 changed files with 200 additions and 51 deletions.
199 changes: 148 additions & 51 deletions medusa/name_parser/rules/rules.py
Original file line number Diff line number Diff line change
Expand Up @@ -181,7 +181,6 @@ class FixInvalidAbsoluteReleaseGroups(Rule):
"type": "episode"
}
with this fix:
For: Show.Name.s16e03-05.313-315
GuessIt found: {
Expand Down Expand Up @@ -713,6 +712,97 @@ def when(self, matches, context):
return to_remove, to_append


class OnePreGroupAsMultiEpisode(Rule):
"""Remove last episode (one) and add the first episode as absolute.
There are animes where the absolute episode is detected as
multi episode because of a number (one) before the group.
Medusa rule:
- The first episode should be added as absolute
- The last episode should be removed
- Episode title should be release group
e.g.: Kemono.Michi.Rise.Up.E03.1080p.WEB.x264.1-URANiME-Obfuscated
guessit -t episode "Kemono.Michi.Rise.Up.E03.1080p.WEB.x264.1-URANiME-Obfuscated"
without this rule:
For: Kemono.Michi.Rise.Up.E03.1080p.WEB.x264.1-URANiME-Obfuscated
GuessIt found: {
"title": "Kemono Michi Rise Up",
"episode": [
3,
1
],
"screen_size": "1080p",
"source": "Web",
"video_codec": "H.264",
"episode_title": "URANiME",
"other": "Obfuscated",
"type": "episode"
}
with this rule:
For: Kemono.Michi.Rise.Up.E03.1080p.WEB.x264.1-URANiME-Obfuscated
GuessIt found: {
"title": "Kemono Michi Rise Up",
"episode": 3,
"absolute_episode": 3,
"screen_size": "1080p",
"source": "Web",
"video_codec": "H.264",
"release_group": "URANiME",
"other": "Obfuscated",
"type": "episode"
}
"""

priority = POST_PROCESS
consequence = [RemoveMatch, AppendMatch]

def when(self, matches, context):
"""Evaluate the rule.
:param matches:
:type matches: rebulk.match.Matches
:param context:
:type context: dict
:return:
"""
titles = matches.named('title')
if not titles:
return

episodes = matches.named('episode')
if not episodes or len(episodes) != 2:
return

is_anime = context.get('show_type') == 'anime' or matches.tagged('anime')
if is_anime or matches.named('season'):
return

sorted_episodes = sorted(episodes)
if sorted_episodes[-1].value != 1:
return

episode = copy.copy(sorted_episodes[0])
episode.name = 'absolute_episode'

to_remove = [sorted_episodes[-1]]
to_append = [episode]

episode_titles = matches.named('episode_title')
if episode_titles:
release_group = copy.copy(episode_titles[0])
release_group.name = 'release_group'

to_remove.append(episode_titles[0])
to_append.append(release_group)

return to_remove, to_append


class AnimeAbsoluteEpisodeNumbers(Rule):
"""Move episode numbers to absolute episode numbers for animes.
Expand Down Expand Up @@ -851,7 +941,6 @@ class AbsoluteEpisodeNumbers(Rule):
"screen_size": "720p",
"type": "episode"
}
"""

priority = POST_PROCESS
Expand Down Expand Up @@ -906,54 +995,50 @@ def when(self, matches, context):
return to_remove, to_append


class OnePreGroupAsMultiEpisode(Rule):
"""Remove last episode (one) and add the first episode as absolute.
class FixEpisodeTitleAsMultiSeason(Rule):
"""Remove the last season and add it to the episode title.
There are animes where the absolute episode is detected as
multi episode because of a number (one) before the group.
e.g.: The.X-Flies.S09E06.Trust.No.1.x265.HEVC-Qman[UTR].mkv
Medusa rule:
- The first episode should be added as absolute
- The last episode should be removed
- Episode title should be release group
e.g.: Kemono.Michi.Rise.Up.E03.1080p.WEB.x264.1-URANiME-Obfuscated
guessit -t episode "Kemono.Michi.Rise.Up.E03.1080p.WEB.x264.1-URANiME-Obfuscated"
guessit -t episode "The.X-Flies.S09E06.Trust.No.1.x265.HEVC-Qman[UTR].mkv"
without this rule:
For: Kemono.Michi.Rise.Up.E03.1080p.WEB.x264.1-URANiME-Obfuscated
For: The.X-Flies.S09E06.Trust.No.1.x265.HEVC-Qman[UTR].mkv
GuessIt found: {
"title": "Kemono Michi Rise Up",
"episode": [
3,
"title": "The X-Flies",
"season": [
9,
1
],
"screen_size": "1080p",
"source": "Web",
"video_codec": "H.264",
"episode_title": "URANiME",
"other": "Obfuscated",
"episode": 6,
"episode_title": "Trust No",
"video_codec": "H.265",
"video_profile": "High Efficiency Video Coding",
"release_group": "Qman[UTR]",
"container": "mkv",
"mimetype": "video/x-matroska",
"type": "episode"
}
with this rule:
For: Kemono.Michi.Rise.Up.E03.1080p.WEB.x264.1-URANiME-Obfuscated
For: The.X-Flies.S09E06.Trust.No.1.x265.HEVC-Qman[UTR].mkv
GuessIt found: {
"title": "Kemono Michi Rise Up",
"episode": 3,
"absolute_episode": 3,
"screen_size": "1080p",
"source": "Web",
"video_codec": "H.264",
"release_group": "URANiME",
"other": "Obfuscated",
"title": "The X-Flies",
"season": 9
"episode": 6,
"episode_title": "Trust No 1",
"video_codec": "H.265",
"video_encoder": "x265",
"video_profile": "High Efficiency Video Coding",
"release_group": "Qman",
"container": "mkv",
"mimetype": "video/x-matroska",
"type": "episode"
}
"""

priority = POST_PROCESS
consequence = [RemoveMatch, AppendMatch]
consequence = [RemoveMatch]

def when(self, matches, context):
"""Evaluate the rule.
Expand All @@ -968,33 +1053,45 @@ def when(self, matches, context):
if not titles:
return

episodes = matches.named('episode')
if not episodes or len(episodes) != 2:
return

is_anime = context.get('show_type') == 'anime' or matches.tagged('anime')
if is_anime or matches.named('season'):
if is_anime:
return

sorted_episodes = sorted(episodes)
if sorted_episodes[-1].value != 1:
seasons = matches.named('season')
if not seasons or len(seasons) not in [2, 3]:
return

episode = copy.copy(sorted_episodes[0])
episode.name = 'absolute_episode'
if len(seasons) == 2:
season = seasons[-1]
else:
season = seasons[len(seasons) - 2]

to_remove = [sorted_episodes[-1]]
to_append = [episode]
next_episode = matches.next(season, predicate=lambda match: match.name == 'episode')
if next_episode:
return

to_remove = []

episode_titles = matches.named('episode_title')
if episode_titles:
release_group = copy.copy(episode_titles[0])
release_group.name = 'release_group'
previous = matches.previous(season, predicate=lambda match: match.name == 'episode_title')
if not previous:
return

to_remove.append(episode_titles[0])
to_append.append(release_group)
episode_title = episode_titles[0]
if not episode_title.value[0].isdigit():
episode_title.value = episode_title.value + ' ' + str(season.value)
to_remove.append(season)
else:
previous = matches.previous(season, predicate=lambda match: match.name == 'episode')
if not previous:
return

return to_remove, to_append
episode_title = season
episode_title.name = 'episode_title'
episode_title.value = str(season.value)

return to_remove


class PartsAsEpisodeNumbers(Rule):
Expand Down Expand Up @@ -1141,6 +1238,7 @@ class FixParentFolderReplacingTitle(Rule):
"mimetype": "video/x-matroska",
"type": "episode"
}
with the rule:
For: /Comedy 23/Funny.Show.S4E19.mkv
GuessIt found: {
Expand Down Expand Up @@ -1220,7 +1318,6 @@ class FixMultipleSources(Rule):
"type": "episode"
}
with this rule:
For: Show.Name.S02E01.eps2.0.unm4sk-pt1.tc.1080p.WEB-DL.DD5.1.H264-GROUP
GuessIt found: {
Expand Down Expand Up @@ -1462,7 +1559,6 @@ class ReleaseGroupPostProcessor(Rule):
"type": "episode"
}
with this post processor:
For: Some.Show.S02E14.1080p.HDTV.X264-GROUP[TRASH]
GuessIt found: {
Expand Down Expand Up @@ -1582,6 +1678,7 @@ def rules():
AnimeWithSeasonMultipleEpisodeNumbers,
AnimeAbsoluteEpisodeNumbers,
AbsoluteEpisodeNumbers,
FixEpisodeTitleAsMultiSeason,
OnePreGroupAsMultiEpisode,
PartsAsEpisodeNumbers,
RemoveInvalidEpisodeSeparator,
Expand Down
52 changes: 52 additions & 0 deletions tests/test_guessit.yml
Original file line number Diff line number Diff line change
Expand Up @@ -1402,6 +1402,58 @@
release_group: Group
type: episode

? The.X-Flies.S09E06.Trust.No.1.x265.HEVC-Group.mkv
: title: The X-Flies
season: 9
episode: 6
episode_title: Trust No 1
video_codec: H.265
video_encoder: x265
video_profile: High Efficiency Video Coding
release_group: Group
container: mkv
mimetype: video/x-matroska
type: episode

? /media/Season 09/The.X-Flies.S09E06.Trust.No.1.x265.HEVC-Group.mkv
: title: The X-Flies
season: 9
episode: 6
episode_title: Trust No 1
video_codec: H.265
video_encoder: x265
video_profile: High Efficiency Video Coding
release_group: Group
container: mkv
mimetype: video/x-matroska
type: episode

? The.X-Flies.S09E07.3.x265.HEVC-Group.mkv
: title: The X-Flies
season: 9
episode: 7
episode_title: '3'
video_codec: H.265
video_encoder: x265
video_profile: High Efficiency Video Coding
release_group: Group
container: mkv
mimetype: video/x-matroska
type: episode

? /media/Season 09/The.X-Flies.S09E07.3.x265.HEVC-Group.mkv
: title: The X-Flies
season: 9
episode: 7
episode_title: '3'
video_codec: H.265
video_encoder: x265
video_profile: High Efficiency Video Coding
release_group: Group
container: mkv
mimetype: video/x-matroska
type: episode

# https://github.com/guessit-io/guessit/issues/295
? - Some.Show.S02E14.X264.1080p.HDTV
- /Some.Show.S02E14.X264.1080p.HDTV/Some.Show.S02E14.X264.1080p.HDTV
Expand Down

0 comments on commit e3c1088

Please sign in to comment.