Implement multi threading to improve throughput

This commit is contained in:
2022-03-06 20:02:10 +01:00
parent bba612476b
commit 03efab657c
6 changed files with 59 additions and 36 deletions

View File

@@ -1,4 +1,6 @@
mkvtoolnixPath: /usr/bin mkvtoolnixPath: C:\Program Files\MKVToolNix
# Only edit this value if you know what you are doing, otherwise it may impact your performance negatively
threadCount: 2
config: config:
1: 1:
audio: audio:

View File

@@ -6,7 +6,7 @@
<groupId>MKVAudioSubtilesChanger</groupId> <groupId>MKVAudioSubtilesChanger</groupId>
<artifactId>MKVAudioSubtitlesChanger</artifactId> <artifactId>MKVAudioSubtitlesChanger</artifactId>
<version>1.0</version> <version>1.2</version>
<build> <build>
<defaultGoal>clean package</defaultGoal> <defaultGoal>clean package</defaultGoal>

View File

@@ -5,41 +5,57 @@ import at.pcgamingfreaks.mkvaudiosubtitlechanger.config.ConfigProcessor;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.intimpl.MkvFileCollector; import at.pcgamingfreaks.mkvaudiosubtitlechanger.intimpl.MkvFileCollector;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.FileAttribute; import at.pcgamingfreaks.mkvaudiosubtitlechanger.model.FileAttribute;
import at.pcgamingfreaks.mkvaudiosubtitlechanger.util.ConfigUtil; import at.pcgamingfreaks.mkvaudiosubtitlechanger.util.ConfigUtil;
import lombok.SneakyThrows;
import lombok.extern.log4j.Log4j2; import lombok.extern.log4j.Log4j2;
import java.io.File; import java.io.File;
import java.util.ArrayList;
import java.util.List; import java.util.List;
import java.util.concurrent.*;
@Log4j2 @Log4j2
public class AttributeUpdaterKernel { public class AttributeUpdaterKernel {
MkvFileCollector collector = new MkvFileCollector(); MkvFileCollector collector = new MkvFileCollector();
int filesChangedAmount = 0;
int filesNotChangedAmount = 0;
long runtime = 0;
@SneakyThrows
public void execute(String path) { public void execute(String path) {
List<AttributeConfig> configPattern = ConfigUtil.loadConfig(); List<AttributeConfig> configPattern = ConfigUtil.loadConfig();
List<File> allValidPaths = collector.loadFiles(path); List<File> allValidPaths = collector.loadFiles(path);
ExecutorService executor = Executors.newFixedThreadPool(ConfigUtil.getThreadCount());
long beforeTimer = System.currentTimeMillis();
if(allValidPaths != null && configPattern != null){ if(allValidPaths != null && configPattern != null){
for(File file : allValidPaths){ System.out.print("Running");
List<FileAttribute> attributes = collector.loadAttributes(file); allValidPaths.forEach(file -> executor.submit(() -> process(configPattern, file)));
if (attributes.isEmpty()) {
continue;
}
boolean fileHasChanged = false;
for(AttributeConfig config : configPattern){
/*
* Creating new ArrayList, because the method removes elements from the list by reference
*/
fileHasChanged = new ConfigProcessor(config).processConfig(file, new ArrayList<>(attributes));
if(fileHasChanged){
break;
}
}
if(! fileHasChanged){
log.info(file.getName() + " didn't change!");
}
}
}else{ }else{
log.error("Path is not valid or config has errors!"); log.error("Path is not valid or config has errors!");
} }
executor.shutdown();
executor.awaitTermination(1, TimeUnit.DAYS);
runtime = System.currentTimeMillis() - beforeTimer;
System.out.printf("%nFiles changed: %s%n", filesChangedAmount);
System.out.printf("Files not changed: %s%n", filesNotChangedAmount);
System.out.printf("Runtime: %ss%n", runtime / 1000);
}
private void process(List<AttributeConfig> configPattern, File file) {
List<FileAttribute> attributes = collector.loadAttributes(file);
boolean fileHasChanged = false;
if (attributes.isEmpty()) return;
for(AttributeConfig config : configPattern){
fileHasChanged = new ConfigProcessor(config).processConfig(file, attributes);
if(fileHasChanged) break;
}
if(!fileHasChanged){
log.info("File didn't change: {}", file.getName());
filesNotChangedAmount++;
} else {
filesChangedAmount++;
}
System.out.print(".");
} }
} }

View File

@@ -8,6 +8,7 @@ import lombok.extern.log4j.Log4j2;
import java.io.File; import java.io.File;
import java.io.IOException; import java.io.IOException;
import java.util.ArrayList;
import java.util.Iterator; import java.util.Iterator;
import java.util.List; import java.util.List;
@@ -31,10 +32,11 @@ public class ConfigProcessor {
public boolean processConfig(File file, List<FileAttribute> attributes) { public boolean processConfig(File file, List<FileAttribute> attributes) {
// check if size is bigger or equal 2 to make sure that there is at least one audio and subtitle line // check if size is bigger or equal 2 to make sure that there is at least one audio and subtitle line
// TODO: implement empty audio or subtitle line // TODO: implement empty audio or subtitle line
if(attributes.size() >= 2){ List<FileAttribute> attributesCopy = new ArrayList<>(attributes);
TransferObject transfer = filterAttributes(attributes); if(attributesCopy.size() >= 2){
if(! attributes.isEmpty()){ TransferObject transfer = filterAttributes(attributesCopy);
return updateFile(file, attributes, transfer); if(! attributesCopy.isEmpty()){
return updateFile(file, attributesCopy, transfer);
} }
} }
return false; return false;
@@ -112,7 +114,7 @@ public class ConfigProcessor {
* In this case the file would be change to the exact same audio and subtitle lines and we want to * In this case the file would be change to the exact same audio and subtitle lines and we want to
* avoid unnecessary changes to the file * avoid unnecessary changes to the file
*/ */
log.info(file.getName() + " already fits config!"); log.info("File already fits config: {}", file.getName());
return true; return true;
} }
try{ try{
@@ -124,7 +126,7 @@ public class ConfigProcessor {
* We return true even if there was an error. If there was an error, the chances that this file is still * We return true even if there was an error. If there was an error, the chances that this file is still
* busy later. * busy later.
*/ */
log.info(file.getName() + " was updated"); log.info("Updated {}", file.getName());
return true; return true;
}else{ }else{
return false; return false;

View File

@@ -37,4 +37,15 @@ public class ConfigUtil {
return null; return null;
} }
} }
public static int getThreadCount() {
try {
return Integer.parseInt(new YAML(new File("config.yaml")).getString("threadCount"));
} catch (YamlInvalidContentException | IOException e) {
e.printStackTrace();
} catch (YamlKeyNotFoundException e) {
throw new RuntimeException(e);
}
return 1;
}
} }

View File

@@ -1,12 +1,6 @@
Configuration: Configuration:
name: DefaultLogger name: DefaultLogger
Appenders: Appenders:
Console:
name: Console_Out
PatternLayout:
Pattern: "%d{DEFAULT} | %-5level | %thread | %msg %n %throwable"
ThresholdFilter:
level: debug
File: File:
name: FileAppender name: FileAppender
fileName: default.log fileName: default.log
@@ -18,11 +12,9 @@ Configuration:
Root: Root:
level: debug level: debug
AppenderRef: AppenderRef:
- ref: Console_Out
- ref: FileAppender - ref: FileAppender
Logger: Logger:
name: "com.zaxxer.hikari.HikariConfig" name: "com.zaxxer.hikari.HikariConfig"
level: info level: info
AppenderRef: AppenderRef:
- ref: Console_Out
- ref: FileAppender - ref: FileAppender