fix pattern edit

click-textual
Maveno 1 year ago
parent 3765f25fd8
commit 87ccb7e8a6

@ -0,0 +1,32 @@
import os
from ffx.pattern_controller import PatternController
from ffx.model.show import Base
from sqlalchemy import create_engine, Column, Integer, String, ForeignKey
from sqlalchemy.orm import relationship, sessionmaker, Mapped, backref
filename = 'Boruto.Naruto.Next.Generations.S01E256.GerEngSub.AAC.1080p.WebDL.x264-Tanuki.mkv'
# Data 'input' variable
context = {}
# Initialize DB
homeDir = os.path.expanduser("~")
ffxVarDir = os.path.join(homeDir, '.local', 'var', 'ffx')
if not os.path.exists(ffxVarDir):
os.makedirs(ffxVarDir)
context['database_url'] = f"sqlite:///{os.path.join(ffxVarDir, 'ffx.db')}"
context['database_engine'] = create_engine(context['database_url'])
context['database_session'] = sessionmaker(bind=context['database_engine'])
Base.metadata.create_all(context['database_engine'])
pc = PatternController(context)
print(pc.matchFilename(filename))

@ -1,4 +1,4 @@
import click import click, re
from ffx.model.pattern import Pattern from ffx.model.pattern import Pattern
@ -11,18 +11,47 @@ class PatternController():
self.Session = self.context['database_session'] # convenience self.Session = self.context['database_session'] # convenience
def updatePattern(self, show_id, pattern): def addPattern(self, patternDescriptor):
try: try:
s = self.Session() s = self.Session()
q = s.query(Pattern).filter(Pattern.show_id == int(show_id), Pattern.pattern == str(pattern)) q = s.query(Pattern).filter(Pattern.show_id == int(patternDescriptor['show_id']), Pattern.pattern == str(patternDescriptor['pattern']))
if not q.count(): if not q.count():
pattern = Pattern(show_id = int(show_id), pattern = str(pattern)) pattern = Pattern(show_id = int(patternDescriptor['show_id']),
pattern = str(patternDescriptor['pattern']))
s.add(pattern) s.add(pattern)
s.commit()
return patternDescriptor
else:
return {}
except Exception as ex:
raise click.ClickException(f"PatternController.addPattern(): {repr(ex)}")
finally:
s.close()
def updatePattern(self, patternId, patternDescriptor):
try:
s = self.Session()
q = s.query(Pattern).filter(Pattern.id == int(patternId))
if q.count():
pattern = q.first()
pattern.show_id = int(patternDescriptor['show_id'])
pattern.pattern = str(patternDescriptor['pattern'])
s.commit() s.commit()
return True return True
else:
return False
except Exception as ex: except Exception as ex:
raise click.ClickException(f"PatternController.updatePattern(): {repr(ex)}") raise click.ClickException(f"PatternController.updatePattern(): {repr(ex)}")
finally: finally:
@ -30,11 +59,11 @@ class PatternController():
def findPattern(self, showId, pattern): def findPattern(self, patternDescriptor):
try: try:
s = self.Session() s = self.Session()
q = s.query(Pattern).filter(Pattern.show_id == int(showId), Pattern.pattern == str(pattern)) q = s.query(Pattern).filter(Pattern.show_id == int(patternDescriptor['show_id']), Pattern.pattern == str(patternDescriptor['pattern']))
if q.count(): if q.count():
pattern = q.first() pattern = q.first()
@ -48,21 +77,22 @@ class PatternController():
s.close() s.close()
def getPatternDict(self, pattern):
patternDescriptor = {}
patternDescriptor['pattern'] = str(pattern.pattern)
patternDescriptor['show_id'] = int(pattern.show_id)
return patternDescriptor
def getPatternDescriptor(self, patternId): def getPatternDescriptor(self, patternId):
try: try:
s = self.Session() s = self.Session()
q = s.query(Pattern).filter(Pattern.id == int(patternId)) q = s.query(Pattern).filter(Pattern.id == int(patternId))
patternDescriptor = {}
if q.count(): if q.count():
pattern = q.first() pattern = q.first()
return self.getPatternDict(pattern)
patternDescriptor['id'] = pattern.id
patternDescriptor['pattern'] = pattern.pattern
patternDescriptor['show_id'] = pattern.show_id
return patternDescriptor
except Exception as ex: except Exception as ex:
raise click.ClickException(f"PatternController.getPatternDescriptor(): {repr(ex)}") raise click.ClickException(f"PatternController.getPatternDescriptor(): {repr(ex)}")
@ -90,3 +120,43 @@ class PatternController():
raise click.ClickException(f"PatternController.deletePattern(): {repr(ex)}") raise click.ClickException(f"PatternController.deletePattern(): {repr(ex)}")
finally: finally:
s.close() s.close()
def matchFilename(self, filename):
SEASON_PATTERN = '[sS]([0-9]+)'
EPISODE_PATTERN = '[eE]([0-9]+)'
result = {}
try:
s = self.Session()
q = s.query(Pattern)
for pattern in q.all():
match = re.search(pattern.pattern, filename)
if match:
result['pattern_id'] = pattern.id
result['show_id'] = pattern.show_id
result['indicator'] = match.group(1)
seasonMatch = re.search(SEASON_PATTERN, result['indicator'])
if seasonMatch:
result['season'] = int(seasonMatch.group(1))
episodeMatch = re.search(EPISODE_PATTERN, result['indicator'])
if episodeMatch:
result['episode'] = int(episodeMatch.group(1))
except Exception as ex:
raise click.ClickException(f"PatternController.matchFilename(): {repr(ex)}")
finally:
s.close()
return result

@ -55,6 +55,7 @@ class PatternDeleteScreen(Screen):
self.__pc = PatternController(context = self.context) self.__pc = PatternController(context = self.context)
self.__sc = ShowController(context = self.context) self.__sc = ShowController(context = self.context)
self.pattern_id = patternId
self.pattern_obj = self.__pc.getPatternDescriptor(patternId) if patternId is not None else {} self.pattern_obj = self.__pc.getPatternDescriptor(patternId) if patternId is not None else {}
self.show_obj = self.__sc.getShowDesciptor(showId) if showId is not None else {} self.show_obj = self.__sc.getShowDesciptor(showId) if showId is not None else {}
@ -97,13 +98,11 @@ class PatternDeleteScreen(Screen):
if event.button.id == "delete_button": if event.button.id == "delete_button":
if self.__pc.deletePattern(self.pattern_obj['id']): if self.pattern_id is None:
raise click.ClickException('PatternDeleteScreen.on_button_pressed(): pattern id is undefined')
screenResult = {} if self.__pc.deletePattern(self.pattern_id):
screenResult['show_id'] = self.show_obj['id'] self.dismiss(self.pattern_obj)
screenResult['pattern'] = self.pattern_obj['pattern']
self.dismiss(screenResult)
else: else:
#TODO: Meldung #TODO: Meldung

@ -79,7 +79,9 @@ class PatternDetailsScreen(Screen):
self.__sc = ShowController(context = self.context) self.__sc = ShowController(context = self.context)
self.__tc = TrackController(context = self.context) self.__tc = TrackController(context = self.context)
self.pattern_id = patternId
self.pattern_obj = self.__pc.getPatternDescriptor(patternId) if patternId is not None else {} self.pattern_obj = self.__pc.getPatternDescriptor(patternId) if patternId is not None else {}
self.show_obj = self.__sc.getShowDesciptor(showId) if showId is not None else {} self.show_obj = self.__sc.getShowDesciptor(showId) if showId is not None else {}
@ -106,7 +108,7 @@ class PatternDetailsScreen(Screen):
self.audioStreamsTable.clear() self.audioStreamsTable.clear()
trackIds = self.__tc.findAllTracks(self.pattern_obj['id']) trackIds = self.__tc.findAllTracks(self.pattern_id) #! id missing
for audioTrackId in trackIds['audio']: for audioTrackId in trackIds['audio']:
@ -126,7 +128,7 @@ class PatternDetailsScreen(Screen):
self.audioStreamsTable.clear() self.audioStreamsTable.clear()
trackIds = self.__tc.findAllTracks(self.pattern_obj['id']) trackIds = self.__tc.findAllTracks(self.pattern_id)
for audioTrackId in trackIds['audio']: for audioTrackId in trackIds['audio']:
@ -157,6 +159,7 @@ class PatternDetailsScreen(Screen):
self.updateAudioTracks() self.updateAudioTracks()
self.updateSubtitleTracks() self.updateSubtitleTracks()
def compose(self): def compose(self):
self.audioStreamsTable = DataTable(classes="five") self.audioStreamsTable = DataTable(classes="five")
@ -306,19 +309,31 @@ class PatternDetailsScreen(Screen):
# Check if the button pressed is the one we are interested in # Check if the button pressed is the one we are interested in
if event.button.id == "save_button": if event.button.id == "save_button":
pattern = self.getPatternFromInput() patternDescriptor = {}
patternDescriptor['show_id'] = self.show_obj['id']
patternDescriptor['pattern'] = self.getPatternFromInput()
if self.__pc.updatePattern(self.show_obj['id'], pattern): if self.pattern_obj:
screenResult = {} if self.pattern_id is None:
screenResult['show_id'] = self.show_obj['id'] #TODO: Meldung
screenResult['pattern'] = pattern self.app.pop_screen()
else:
if self.__pc.updatePattern(self.pattern_id, patternDescriptor):
self.dismiss(patternDescriptor)
else:
#TODO: Meldung
self.app.pop_screen()
self.dismiss(screenResult) else:
if self.__pc.addPattern(patternDescriptor):
self.dismiss(patternDescriptor)
else: else:
#TODO: Meldung #TODO: Meldung
self.app.pop_screen() self.app.pop_screen()
if event.button.id == "cancel_button": if event.button.id == "cancel_button":
self.app.pop_screen() self.app.pop_screen()
@ -329,27 +344,27 @@ class PatternDetailsScreen(Screen):
#self.pattern_obj #self.pattern_obj
if event.button.id == "button_add_audio_stream": if event.button.id == "button_add_audio_stream":
self.app.push_screen(TrackDetailsScreen(trackType = TrackType.AUDIO, patternId = self.pattern_obj['id'], subIndex = len(self.audioStreamsTable.rows)), self.handle_add_stream) self.app.push_screen(TrackDetailsScreen(trackType = TrackType.AUDIO, patternId = self.pattern_obj['id'], subIndex = len(self.audioStreamsTable.rows)), self.handle_add_track)
if event.button.id == "button_edit_audio_stream": if event.button.id == "button_edit_audio_stream":
self.app.push_screen(TrackDetailsScreen(trackId = self.getSelectedAudioTrackId()), self.handle_edit_stream) self.app.push_screen(TrackDetailsScreen(trackId = self.getSelectedAudioTrackId()), self.handle_edit_track)
selectedAudioTrackId = self.getSelectedAudioTrackId() selectedAudioTrackId = self.getSelectedAudioTrackId()
if selectedAudioTrackId is not None: if selectedAudioTrackId is not None:
if event.button.id == "button_delete_audio_stream": if event.button.id == "button_delete_audio_stream":
self.app.push_screen(TrackDeleteScreen(trackId = selectedAudioTrackId), self.handle_delete_stream) self.app.push_screen(TrackDeleteScreen(trackId = selectedAudioTrackId), self.handle_delete_track)
if event.button.id == "button_add_subtitle_stream": if event.button.id == "button_add_subtitle_stream":
self.app.push_screen(TrackDetailsScreen(trackType = TrackType.SUBTITLE, patternId = self.pattern_obj['id'], subIndex = len(self.subtitleStreamsTable.rows)), self.handle_add_stream) self.app.push_screen(TrackDetailsScreen(trackType = TrackType.SUBTITLE, patternId = self.pattern_obj['id'], subIndex = len(self.subtitleStreamsTable.rows)), self.handle_add_track)
if event.button.id == "button_edit_subtitle_stream": if event.button.id == "button_edit_subtitle_stream":
self.app.push_screen(TrackDetailsScreen(trackId = self.getSelectedSubtitleTrackId()), self.handle_edit_stream) self.app.push_screen(TrackDetailsScreen(trackId = self.getSelectedSubtitleTrackId()), self.handle_edit_track)
selectedSubtitleTrackId = self.getSelectedSubtitleTrackId() selectedSubtitleTrackId = self.getSelectedSubtitleTrackId()
if selectedSubtitleTrackId is not None: if selectedSubtitleTrackId is not None:
if event.button.id == "button_delete_subtitle_stream": if event.button.id == "button_delete_subtitle_stream":
self.app.push_screen(TrackDeleteScreen(trackId = selectedSubtitleTrackId), self.handle_delete_stream) self.app.push_screen(TrackDeleteScreen(trackId = selectedSubtitleTrackId), self.handle_delete_track)
def handle_add_stream(self, trackDescriptor): def handle_add_track(self, trackDescriptor):
dispoList = trackDescriptor['disposition_list'] dispoList = trackDescriptor['disposition_list']
@ -376,7 +391,7 @@ class PatternDetailsScreen(Screen):
self.subtitleStreamsTable.add_row(*map(str, row)) self.subtitleStreamsTable.add_row(*map(str, row))
def handle_edit_stream(self, trackDescriptor): def handle_edit_track(self, trackDescriptor):
try: try:
if trackDescriptor['type'] == TrackType.AUDIO: if trackDescriptor['type'] == TrackType.AUDIO:
@ -401,7 +416,7 @@ class PatternDetailsScreen(Screen):
pass pass
def handle_delete_stream(self, trackDescriptor): def handle_delete_track(self, trackDescriptor):
try: try:
if trackDescriptor['type'] == TrackType.AUDIO: if trackDescriptor['type'] == TrackType.AUDIO:

@ -23,9 +23,9 @@ class ShowDetailsScreen(Screen):
CSS = """ CSS = """
Grid { Grid {
grid-size: 2 14; grid-size: 5 14;
grid-rows: 2 2 2 2 2 2 2 2 2 2 2 6 2 2; grid-rows: 2 2 2 2 2 2 2 2 2 2 2 6 2 2;
grid-columns: 30 90; grid-columns: 30 30 30 30 30;
height: 100%; height: 100%;
width: 100%; width: 100%;
padding: 1; padding: 1;
@ -50,6 +50,15 @@ class ShowDetailsScreen(Screen):
.two { .two {
column-span: 2; column-span: 2;
} }
.three {
column-span: 3;
}
.four {
column-span: 4;
}
.five {
column-span: 5;
}
.box { .box {
height: 100%; height: 100%;
@ -114,7 +123,7 @@ class ShowDetailsScreen(Screen):
self.query_one("#indicator_episode_digits_input", Input).value = "2" self.query_one("#indicator_episode_digits_input", Input).value = "2"
def getSelectedPattern(self): def getSelectedPatternDescriptor(self):
selectedPattern = {} selectedPattern = {}
@ -127,6 +136,7 @@ class ShowDetailsScreen(Screen):
if row_key is not None: if row_key is not None:
selected_row_data = self.patternTable.get_row(row_key) selected_row_data = self.patternTable.get_row(row_key)
selectedPattern['show_id'] = self.show_obj['id']
selectedPattern['pattern'] = str(selected_row_data[0]) selectedPattern['pattern'] = str(selected_row_data[0])
except CellDoesNotExist: except CellDoesNotExist:
@ -140,7 +150,7 @@ class ShowDetailsScreen(Screen):
def action_add_pattern(self): def action_add_pattern(self):
if self.show_obj: if self.show_obj:
self.app.push_screen(PatternDetailsScreen(showId = self.show_obj['id']), self.handle_add_pattern) self.app.push_screen(PatternDetailsScreen(showId = self.show_obj['id']), self.handle_add_pattern) # <-
def handle_add_pattern(self, screenResult): def handle_add_pattern(self, screenResult):
@ -151,31 +161,36 @@ class ShowDetailsScreen(Screen):
def action_edit_pattern(self): def action_edit_pattern(self):
selectedPattern = self.getSelectedPattern() selectedPatternDescriptor = self.getSelectedPatternDescriptor()
if selectedPattern: if selectedPatternDescriptor:
selectedPatternId = self.__pc.findPattern(self.show_obj['id'], selectedPattern['pattern']) selectedPatternId = self.__pc.findPattern(selectedPatternDescriptor)
if selectedPatternId is None: if selectedPatternId is None:
raise click.ClickException(f"ShowDetailsScreen.action_edit_pattern(): Pattern to remove has no id") raise click.ClickException(f"ShowDetailsScreen.action_edit_pattern(): Pattern to remove has no id")
self.app.push_screen(PatternDetailsScreen(patternId = selectedPatternId, showId = self.show_obj['id']), self.handle_edit_pattern) self.app.push_screen(PatternDetailsScreen(patternId = selectedPatternId, showId = self.show_obj['id']), self.handle_edit_pattern) # <-
def handle_edit_pattern(self, screenResult): def handle_edit_pattern(self, screenResult):
try:
row_key, col_key = self.patternTable.coordinate_to_cell_key(self.patternTable.cursor_coordinate)
self.patternTable.update_cell(row_key, self.column_key_pattern, screenResult['pattern'])
except CellDoesNotExist:
pass pass
#pattern = (screenResult['pattern'],)
#self.patternTable.add_row(*map(str, pattern))
def action_remove_pattern(self): def action_remove_pattern(self):
selectedPattern = self.getSelectedPattern() selectedPatternDescriptor = self.getSelectedPatternDescriptor()
if selectedPattern: if selectedPatternDescriptor:
selectedPatternId = self.__pc.findPattern(self.show_obj['id'], selectedPattern['pattern']) selectedPatternId = self.__pc.findPattern(selectedPatternDescriptor)
if selectedPatternId is None: if selectedPatternId is None:
raise click.ClickException(f"ShowDetailsScreen.action_remove_pattern(): Pattern to remove has no id") raise click.ClickException(f"ShowDetailsScreen.action_remove_pattern(): Pattern to remove has no id")
@ -196,10 +211,10 @@ class ShowDetailsScreen(Screen):
def compose(self): def compose(self):
# Create the DataTable widget # Create the DataTable widget
self.patternTable = DataTable(classes="two") self.patternTable = DataTable(classes="five")
# Define the columns with headers # Define the columns with headers
self.column_key_id = self.patternTable.add_column("Pattern", width=90) self.column_key_pattern = self.patternTable.add_column("Pattern", width=150)
#self.column_key_name = self.patternTable.add_column("Name", width=50) #self.column_key_name = self.patternTable.add_column("Name", width=50)
#self.column_key_year = self.patternTable.add_column("Year", width=10) #self.column_key_year = self.patternTable.add_column("Year", width=10)
@ -211,52 +226,52 @@ class ShowDetailsScreen(Screen):
with Grid(): with Grid():
# 1 # 1
yield Static("Show" if self.show_obj else "New Show", id="toplabel", classes="two") yield Static("Show" if self.show_obj else "New Show", id="toplabel", classes="five")
# 2 # 2
yield Static("ID") yield Static("ID")
if self.show_obj: if self.show_obj:
yield Static("", id="id_wdg") yield Static("", id="id_wdg", classes="four")
else: else:
yield Input(type="integer", id="id_wdg") yield Input(type="integer", id="id_wdg", classes="four")
# 3 # 3
yield Static("Name") yield Static("Name")
yield Input(type="text", id="name_input") yield Input(type="text", id="name_input", classes="four")
# 4 # 4
yield Static("Year") yield Static("Year")
yield Input(type="integer", id="year_input") yield Input(type="integer", id="year_input", classes="four")
#5 #5
yield Static(" ", classes="two") yield Static(" ", classes="five")
#6 #6
yield Static("Index Season Digits") yield Static("Index Season Digits")
yield Input(type="integer", id="index_season_digits_input") yield Input(type="integer", id="index_season_digits_input", classes="four")
#7 #7
yield Static("Index Episode Digits") yield Static("Index Episode Digits")
yield Input(type="integer", id="index_episode_digits_input") yield Input(type="integer", id="index_episode_digits_input", classes="four")
#8 #8
yield Static("Indicator Season Digits") yield Static("Indicator Season Digits")
yield Input(type="integer", id="indicator_season_digits_input") yield Input(type="integer", id="indicator_season_digits_input", classes="four")
#9 #9
yield Static("Indicator Edisode Digits") yield Static("Indicator Edisode Digits")
yield Input(type="integer", id="indicator_episode_digits_input") yield Input(type="integer", id="indicator_episode_digits_input", classes="four")
# 10 # 10
yield Static(" ", classes="two") yield Static(" ", classes="five")
# 11 # 11
yield Static("File patterns", classes="two") yield Static("File patterns", classes="five")
# 12 # 12
yield self.patternTable yield self.patternTable
# 13 # 13
yield Static(" ", classes="two") yield Static(" ", classes="five")
# 14 # 14
yield Button("Save", id="save_button") yield Button("Save", id="save_button")

Loading…
Cancel
Save