Major system rework

This commit is contained in:
RatzzFatzz
2025-12-10 21:31:29 +01:00
parent d5e452557c
commit 0b61deccbf
44 changed files with 865 additions and 851 deletions

View File

@@ -1,6 +1,7 @@
package at.pcgamingfreaks.mkvaudiosubtitlechanger.impl;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.config.InputConfig;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.InputConfig;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.ResultStatistic;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.util.DateUtils;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.extension.ExtendWith;
@@ -16,7 +17,9 @@ import java.io.File;
import java.nio.file.Path;
import java.nio.file.attribute.BasicFileAttributes;
import java.util.Date;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.regex.Pattern;
import java.util.stream.Stream;
@@ -34,38 +37,44 @@ class FileFilterTest {
@BeforeEach
void beforeEach() {
ResultStatistic.getInstance(true);
}
private static Stream<Arguments> accept() {
return Stream.of(
Arguments.of("~/video.mkv", new String[]{".mkv"}, null, null, ".*", true),
Arguments.of("~/video.mp4", new String[]{".mkv"}, null, null, ".*", false),
Arguments.of("~/video.mkv", Set.of(".mkv"), -1, ".*", true, 1, 0),
Arguments.of("~/video.mp4", Set.of(".mkv"), -1, ".*", false, 0, 0),
Arguments.of("~/video.mkv", new String[]{".mkv"}, null, null, "v.*", true),
Arguments.of("~/video.mkv", new String[]{".mkv"}, null, null, "a.*", false),
Arguments.of("~/video.mkv", Set.of(".mkv"), -1, "v.*", true, 1, 0),
Arguments.of("~/video.mkv", Set.of(".mkv"), -1, "a.*", false, 1, 1),
Arguments.of("~/video.mkv", new String[]{".mkv"}, new Date(System.currentTimeMillis() - 1000), new Date(), ".*", false),
Arguments.of("~/video.mkv", new String[]{".mkv"}, new Date(), new Date(System.currentTimeMillis() - 1000), ".*", true)
Arguments.of("~/video.mkv", Set.of(".mkv"), -1000, ".*", true, 1, 0),
Arguments.of("~/video.mkv", Set.of(".mkv"), 1000, ".*", false, 1, 1)
);
}
/**
* @param filterDateOffset move filter data into the future or past by positive and negative values
*/
@ParameterizedTest
@MethodSource
void accept(String path, String[] args, Date fileCreationDate, Date filterDate, String pattern, boolean expected) {
void accept(String path, Set<String> args, int filterDateOffset, String pattern, boolean expectedHit, int total, int excluded) {
when(file.getAbsolutePath()).thenReturn(path);
when(file.getName()).thenReturn(List.of(path.split("/")).get(1));
when(file.toPath()).thenReturn(Path.of(TEST_FILE));
InputConfig.getInstance(true).setIncludePattern(Pattern.compile(pattern));
if (filterDate != null) InputConfig.getInstance().setFilterDate(filterDate);
long currentTime = System.currentTimeMillis();
InputConfig.getInstance().setFilterDate(new Date(currentTime + filterDateOffset));
try (MockedStatic<DateUtils> mockedFiles = Mockito.mockStatic(DateUtils.class)) {
mockedFiles
.when(() -> DateUtils.convert(anyLong()))
.thenReturn(fileCreationDate);
.thenReturn(new Date(currentTime));
assertEquals(expected, FileFilter.accept(file, args));
assertEquals(expectedHit, FileFilter.accept(file, new HashSet<>(args)), "File is accepted");
assertEquals(total, ResultStatistic.getInstance().getTotal(), "Total files");
assertEquals(excluded, ResultStatistic.getInstance().getExcluded(), "Excluded files");
}
}
}

View File

@@ -1,9 +1,11 @@
package at.pcgamingfreaks.mkvaudiosubtitlechanger.impl;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.config.InputConfig;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.AttributeConfig;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.FileAttribute;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.impl.processors.MkvFileProcessor;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.FileInfo;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.InputConfig;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.AttributeConfig;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.TrackAttributes;
import org.junit.jupiter.api.Disabled;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.Arguments;
import org.junit.jupiter.params.provider.MethodSource;
@@ -29,11 +31,12 @@ class MkvFileProcessorTest {
@ParameterizedTest
@MethodSource
void detectDesiredTracks(AttributeConfig expectedMatch, List<FileAttribute> tracks, AttributeConfig... configs) {
@Disabled
void detectDesiredTracks(AttributeConfig expectedMatch, List<TrackAttributes> tracks, AttributeConfig... configs) {
InputConfig.getInstance().setPreferredSubtitles(Set.of());
FileInfo info = new FileInfo(null);
MkvFileProcessor processor = new MkvFileProcessor();
processor.detectDesiredTracks(info, tracks, tracks, configs);
// processor.detectDesiredTracks(info, tracks, tracks, configs);
assertEquals(expectedMatch.getAudioLanguage(), info.getMatchedConfig().getAudioLanguage());
assertEquals(expectedMatch.getSubtitleLanguage(), info.getMatchedConfig().getSubtitleLanguage());
}
@@ -48,43 +51,4 @@ class MkvFileProcessorTest {
Arguments.of(List.of(), List.of())
);
}
@ParameterizedTest
@MethodSource
void retrieveNonForcedTracks(List<FileAttribute> attributes, List<FileAttribute> expected) {
InputConfig.getInstance().setPreferredSubtitles(Set.of());
InputConfig.getInstance().setForcedKeywords(Set.of("forced"));
MkvFileProcessor processor = new MkvFileProcessor();
List<FileAttribute> actual = processor.retrieveNonForcedTracks(attributes);
assertEquals(expected.size(), actual.size());
for (int i = 0; i < expected.size(); i++) {
assertEquals(expected.get(i), actual.get(i));
}
}
private static Stream<Arguments> retrieveNonCommentaryTracks() {
return Stream.of(
Arguments.of(List.of(SUB_GER, SUB_ENG, AUDIO_GER_COMMENTARY), List.of(SUB_GER, SUB_ENG)),
Arguments.of(List.of(SUB_GER, SUB_ENG), List.of(SUB_GER, SUB_ENG)),
Arguments.of(List.of(AUDIO_GER, SUB_GER, SUB_ENG), List.of(AUDIO_GER, SUB_GER, SUB_ENG)),
Arguments.of(List.of(AUDIO_GER), List.of(AUDIO_GER)),
Arguments.of(List.of(AUDIO_GER_COMMENTARY), List.of()),
Arguments.of(List.of(), List.of())
);
}
@ParameterizedTest
@MethodSource
void retrieveNonCommentaryTracks(List<FileAttribute> attributes, List<FileAttribute> expected) {
InputConfig.getInstance().setPreferredSubtitles(Set.of());
InputConfig.getInstance().setCommentaryKeywords(Set.of("commentary"));
MkvFileProcessor processor = new MkvFileProcessor();
List<FileAttribute> actual = processor.retrieveNonCommentaryTracks(attributes);
assertEquals(expected.size(), actual.size());
for (int i = 0; i < expected.size(); i++) {
assertEquals(expected.get(i), actual.get(i));
}
}
}

View File

@@ -1,7 +1,7 @@
package at.pcgamingfreaks.mkvaudiosubtitlechanger.impl;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.FileAttribute;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.LaneType;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.TrackAttributes;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.TrackType;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.Arguments;
import org.junit.jupiter.params.provider.MethodSource;
@@ -34,13 +34,13 @@ class SubtitleTrackComparatorTest {
@ParameterizedTest
@MethodSource("compareArguments")
void compare(List<FileAttribute> input, List<FileAttribute> expected) {
List<FileAttribute> result = input.stream().sorted(comparator.reversed()).collect(Collectors.toList());
void compare(List<TrackAttributes> input, List<TrackAttributes> expected) {
List<TrackAttributes> result = input.stream().sorted(comparator.reversed()).collect(Collectors.toList());
assertArrayEquals(expected.toArray(new FileAttribute[0]), result.toArray(new FileAttribute[0]));
assertArrayEquals(expected.toArray(new TrackAttributes[0]), result.toArray(new TrackAttributes[0]));
}
private static FileAttribute attr(String trackName, boolean defaultTrack) {
return new FileAttribute(0, "", trackName, defaultTrack, false, LaneType.SUBTITLES);
private static TrackAttributes attr(String trackName, boolean defaultTrack) {
return new TrackAttributes(0, "", trackName, defaultTrack, false, false, false, TrackType.SUBTITLES);
}
}

View File

@@ -0,0 +1,238 @@
package at.pcgamingfreaks.mkvaudiosubtitlechanger.impl.processors;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.AttributeConfig;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.FileInfo;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.InputConfig;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.TrackAttributes;
import org.apache.logging.log4j.util.Strings;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.Arguments;
import org.junit.jupiter.params.provider.MethodSource;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Stream;
import static at.pcgamingfreaks.mkvaudiosubtitlechanger.util.FileInfoTestUtil.*;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertTrue;
class AttributeProcessorTest {
private static Stream<Arguments> attributeConfigMatching() {
return Stream.of(
Arguments.of(
List.of(withName(AUDIO_ENG, null), SUB_ENG),
arr(a("eng:eng")), "eng:eng",
Map.ofEntries(on(withName(AUDIO_ENG, null)), on(SUB_ENG))
),
Arguments.of(
List.of(AUDIO_ENG, SUB_ENG),
arr(a("eng:eng")), "eng:eng",
Map.ofEntries(on(AUDIO_ENG), on(SUB_ENG))
),
Arguments.of(
List.of(AUDIO_ENG, AUDIO_GER, SUB_ENG, SUB_GER),
arr(a("eng:eng")), "eng:eng",
Map.ofEntries(on(AUDIO_ENG), on(SUB_ENG))
),
Arguments.of(
List.of(AUDIO_ENG_DEFAULT, AUDIO_GER, SUB_ENG, SUB_GER),
arr(a("ger:eng")), "ger:eng",
Map.ofEntries(off(AUDIO_ENG_DEFAULT), on(AUDIO_GER), on(SUB_ENG))
),
Arguments.of(
List.of(AUDIO_ENG_DEFAULT, AUDIO_GER, SUB_ENG, SUB_GER),
arr(a("eng:ger")), "eng:ger",
Map.ofEntries(on(SUB_GER))
),
Arguments.of(
List.of(AUDIO_ENG_DEFAULT, AUDIO_GER, SUB_ENG_DEFAULT, SUB_GER),
arr(a("eng:OFF")), "eng:OFF",
Map.ofEntries(off(SUB_ENG_DEFAULT))
),
Arguments.of(
List.of(AUDIO_ENG_DEFAULT, AUDIO_GER, SUB_ENG_DEFAULT, SUB_GER),
arr(a("OFF:OFF")), "OFF:OFF",
Map.ofEntries(off(AUDIO_ENG_DEFAULT), off(SUB_ENG_DEFAULT))
),
Arguments.of(
List.of(AUDIO_ENG_DEFAULT, AUDIO_GER, SUB_GER),
arr(a("eng:eng"), a("eng:ger")), "eng:ger",
Map.ofEntries(on(SUB_GER))
)
);
}
@ParameterizedTest
@MethodSource("attributeConfigMatching")
void findDefaultMatchAndApplyChanges(List<TrackAttributes> tracks, AttributeConfig[] config, String expectedConfig, Map<TrackAttributes, Boolean> changes) {
InputConfig.getInstance().setPreferredSubtitles(new HashSet<>());
InputConfig.getInstance().setCommentaryKeywords(new HashSet<>());
InputConfig.getInstance().setForcedKeywords(new HashSet<>());
FileInfo fileInfo = new FileInfo(null);
fileInfo.addTracks(tracks);
AttributeProcessor.findDefaultMatchAndApplyChanges(fileInfo, config);
assertEquals(Strings.isBlank(expectedConfig), fileInfo.getMatchedConfig() == null);
assertEquals(expectedConfig, fileInfo.getMatchedConfig().toStringShort());
assertEquals(changes.size(), fileInfo.getChanges().getDefaultTrack().size());
changes.forEach((key, value) -> {
assertTrue(fileInfo.getChanges().getDefaultTrack().containsKey(key));
assertEquals(value, fileInfo.getChanges().getDefaultTrack().get(key));
});
}
private static AttributeConfig[] arr(AttributeConfig... configs) {
return configs;
}
private static AttributeConfig a(String config) {
String[] split = config.split(":");
return new AttributeConfig(split[0], split[1]);
}
private static Map.Entry<TrackAttributes, Boolean> on(TrackAttributes track) {
return Map.entry(track, true);
}
private static Map.Entry<TrackAttributes, Boolean> off(TrackAttributes track) {
return Map.entry(track, false);
}
private static Stream<Arguments> filterForPossibleDefaults() {
return Stream.of(
);
}
@ParameterizedTest
@MethodSource("filterForPossibleDefaults")
void filterForPossibleDefaults(List<TrackAttributes> tracks, Set<TrackAttributes> expected) {
}
private static Stream<Arguments> findForcedTracksAndApplyChanges() {
return Stream.of(
Arguments.of(List.of(withName(SUB_GER, "song & signs"), withName(SUB_GER, null)),
Set.of("song & signs"), false,
Map.ofEntries(on(withName(SUB_GER, "song & signs")))
),
Arguments.of(List.of(withName(SUB_GER, "song & signs")),
Set.of("song & signs"), false,
Map.ofEntries(on(withName(SUB_GER, "song & signs")))
),
Arguments.of(List.of(withName(SUB_GER_FORCED, "song & signs")),
Set.of("song & signs"), false,
Map.ofEntries()
),
Arguments.of(List.of(SUB_GER_FORCED, withName(SUB_GER, "song & signs")),
Set.of("song & signs"), true,
Map.ofEntries(off(SUB_GER_FORCED), on(withName(SUB_GER, "song & signs")))
)
);
}
@ParameterizedTest
@MethodSource("findForcedTracksAndApplyChanges")
void findForcedTracksAndApplyChanges(List<TrackAttributes> tracks, Set<String> keywords, boolean overwrite, Map<TrackAttributes, Boolean> changes) {
InputConfig.getInstance().setPreferredSubtitles(new HashSet<>());
InputConfig.getInstance().setCommentaryKeywords(new HashSet<>());
InputConfig.getInstance().setHearingImpaired(new HashSet<>());
InputConfig.getInstance().setForcedKeywords(keywords);
InputConfig.getInstance().setOverwriteForced(overwrite);
FileInfo fileInfo = new FileInfo(null);
fileInfo.addTracks(tracks);
AttributeProcessor.findForcedTracksAndApplyChanges(fileInfo);
assertEquals(changes.size(), fileInfo.getChanges().getForcedTrack().size());
changes.forEach((key, value) -> {
assertTrue(fileInfo.getChanges().getForcedTrack().containsKey(key));
assertEquals(value, fileInfo.getChanges().getForcedTrack().get(key));
});
}
private static Stream<Arguments> findCommentaryTracksAndApplyChanges() {
return Stream.of(
Arguments.of(List.of(withName(SUB_GER, "commentary"), withName(SUB_GER, null)),
Set.of("commentary"),
Map.ofEntries(on(withName(SUB_GER, "commentary")))
),
Arguments.of(List.of(withName(SUB_GER, "commentary")),
Set.of("commentary"),
Map.ofEntries(on(withName(SUB_GER, "commentary")))
),
Arguments.of(List.of(withName(AUDIO_GER_COMMENTARY, "commentary")),
Set.of("commentary"),
Map.ofEntries()
),
Arguments.of(List.of(AUDIO_GER_COMMENTARY, withName(SUB_GER, "commentary")),
Set.of("commentary"),
Map.ofEntries(on(withName(SUB_GER, "commentary")))
)
);
}
@ParameterizedTest
@MethodSource("findCommentaryTracksAndApplyChanges")
void findCommentaryTracksAndApplyChanges(List<TrackAttributes> tracks, Set<String> keywords, Map<TrackAttributes, Boolean> changes) {
InputConfig.getInstance().setPreferredSubtitles(new HashSet<>());
InputConfig.getInstance().setCommentaryKeywords(keywords);
InputConfig.getInstance().setHearingImpaired(new HashSet<>());
InputConfig.getInstance().setForcedKeywords(new HashSet<>());
FileInfo fileInfo = new FileInfo(null);
fileInfo.addTracks(tracks);
AttributeProcessor.findCommentaryTracksAndApplyChanges(fileInfo);
assertEquals(changes.size(), fileInfo.getChanges().getCommentaryTrack().size());
changes.forEach((key, value) -> {
assertTrue(fileInfo.getChanges().getCommentaryTrack().containsKey(key));
assertEquals(value, fileInfo.getChanges().getCommentaryTrack().get(key));
});
}
private static Stream<Arguments> findHearingImpairedTracksAndApplyChanges() {
return Stream.of(
Arguments.of(List.of(withName(SUB_GER, "SDH"), withName(SUB_GER, null)),
Set.of("SDH"),
Map.ofEntries(on(withName(SUB_GER, "SDH")))
),
Arguments.of(List.of(withName(SUB_GER, "SDH")),
Set.of("SDH"),
Map.ofEntries(on(withName(SUB_GER, "SDH")))
),
Arguments.of(List.of(withName(AUDIO_GER_COMMENTARY, "SDH")),
Set.of("SDH"),
Map.ofEntries()
),
Arguments.of(List.of(AUDIO_GER_HEARING, withName(SUB_GER, "SDH")),
Set.of("SDH"),
Map.ofEntries(on(withName(SUB_GER, "SDH")))
)
);
}
@ParameterizedTest
@MethodSource("findCommentaryTracksAndApplyChanges")
void findHearingImpairedTracksAndApplyChanges(List<TrackAttributes> tracks, Set<String> keywords, Map<TrackAttributes, Boolean> changes) {
InputConfig.getInstance().setPreferredSubtitles(new HashSet<>());
InputConfig.getInstance().setCommentaryKeywords(new HashSet<>());
InputConfig.getInstance().setHearingImpaired(keywords);
InputConfig.getInstance().setForcedKeywords(new HashSet<>());
FileInfo fileInfo = new FileInfo(null);
fileInfo.addTracks(tracks);
AttributeProcessor.findHearingImpairedTracksAndApplyChanges(fileInfo);
assertEquals(changes.size(), fileInfo.getChanges().getHearingImpairedTrack().size());
changes.forEach((key, value) -> {
assertTrue(fileInfo.getChanges().getHearingImpairedTrack().containsKey(key));
assertEquals(value, fileInfo.getChanges().getHearingImpairedTrack().get(key));
});
}
}