From b44c988d5a79fc0788973f3b83be12f83a5e7997 Mon Sep 17 00:00:00 2001 From: extio-de Date: Sat, 30 May 2026 11:07:11 +0200 Subject: [PATCH] Enhance App model management: add model settings and argument handling --- apps.json | 2 +- lm-launcher.jar | Bin 2185218 -> 2188757 bytes models.json | 2 +- src/de/extio/lm_launcher/App.java | 86 +++++++++++++++++++++- src/de/extio/lm_launcher/Data.java | 17 ++++- src/de/extio/lm_launcher/LaunchFrame.java | 68 +++++++++++------ 6 files changed, 149 insertions(+), 26 deletions(-) diff --git a/apps.json b/apps.json index 2ca1a4c..7e32437 100644 --- a/apps.json +++ b/apps.json @@ -1 +1 @@ -{"apps":[{"path":"file:///home/sb/lm/koboldcpp-rocm/koboldcpp.py","interpreter":"file:///usr/bin/python","arguments":[],"appArguments":[{"argument":"--usecublas","optional":true,"default_":true},{"argument":"mmq","optional":true,"default_":false},{"argument":"lowvram","optional":true,"default_":false},{"argument":"0","optional":true,"default_":true},{"argument":"--gpulayers","optional":true,"default_":true},{"argument":"GPU_LAYERS","optional":true,"default_":true},{"argument":"--smartcontext","optional":true,"default_":false},{"argument":"--noshift","optional":true,"default_":false},{"argument":"--contextsize","optional":false,"default_":true},{"argument":"CONTEXT_SIZE","optional":false,"default_":true},{"argument":"--launch","optional":false,"default_":true},{"argument":"--host","optional":true,"default_":false},{"argument":"0.0.0.0","optional":true,"default_":false},{"argument":"--threads","optional":false,"default_":true},{"argument":"THREADS","optional":false,"default_":true},{"argument":"--model","optional":false,"default_":true},{"argument":"MODEL","optional":false,"default_":true}]},{"path":"file:///home/sb/lm/llama.cpp/llama-server","interpreter":null,"arguments":[],"appArguments":[{"argument":"-nkvo","optional":true,"default_":false},{"argument":"--parallel","optional":true,"default_":false},{"argument":"2","optional":true,"default_":false},{"argument":"4","optional":true,"default_":false},{"argument":"--host","optional":true,"default_":true},{"argument":"0.0.0.0","optional":true,"default_":true},{"argument":"--port","optional":false,"default_":true},{"argument":"5001","optional":false,"default_":true},{"argument":"-t","optional":false,"default_":true},{"argument":"THREADS","optional":false,"default_":true},{"argument":"-ngl","optional":false,"default_":true},{"argument":"GPU_LAYERS","optional":false,"default_":true},{"argument":"--ctx-size","optional":false,"default_":true},{"argument":"CONTEXT_SIZE","optional":false,"default_":true},{"argument":"-m","optional":false,"default_":true},{"argument":"MODEL","optional":false,"default_":true}]},{"path":"file:///home/sb/lm/SillyTavern/start.sh","interpreter":null,"arguments":[],"appArguments":[]},{"path":"file:///home/sb/lm/ollama-oai-bridge/start.sh","interpreter":null,"arguments":[],"appArguments":[]}]} \ No newline at end of file +{"apps":[{"path":"file:///home/sb/lm/koboldcpp-rocm/koboldcpp.py","interpreter":"file:///usr/bin/python","arguments":[],"appArguments":[{"argument":"--usecublas","optional":true,"default_":true},{"argument":"mmq","optional":true,"default_":false},{"argument":"lowvram","optional":true,"default_":false},{"argument":"0","optional":true,"default_":true},{"argument":"--gpulayers","optional":true,"default_":true},{"argument":"GPU_LAYERS","optional":true,"default_":true},{"argument":"--smartcontext","optional":true,"default_":false},{"argument":"--noshift","optional":true,"default_":false},{"argument":"--contextsize","optional":false,"default_":true},{"argument":"CONTEXT_SIZE","optional":false,"default_":true},{"argument":"--launch","optional":false,"default_":true},{"argument":"--host","optional":true,"default_":false},{"argument":"0.0.0.0","optional":true,"default_":false},{"argument":"--threads","optional":false,"default_":true},{"argument":"THREADS","optional":false,"default_":true},{"argument":"--model","optional":false,"default_":true},{"argument":"MODEL","optional":false,"default_":true}],"modelSettings":[]},{"path":"file:///home/sb/lm/llama.cpp/llama-server","interpreter":null,"arguments":[],"appArguments":[{"argument":"-nkvo","optional":true,"default_":false},{"argument":"--parallel","optional":true,"default_":false},{"argument":"2","optional":true,"default_":false},{"argument":"4","optional":true,"default_":false},{"argument":"--host","optional":true,"default_":true},{"argument":"0.0.0.0","optional":true,"default_":true},{"argument":"--port","optional":false,"default_":true},{"argument":"5001","optional":false,"default_":true},{"argument":"-t","optional":false,"default_":true},{"argument":"THREADS","optional":false,"default_":true},{"argument":"-ngl","optional":false,"default_":true},{"argument":"GPU_LAYERS","optional":false,"default_":true},{"argument":"--ctx-size","optional":false,"default_":true},{"argument":"CONTEXT_SIZE","optional":false,"default_":true},{"argument":"-m","optional":false,"default_":true},{"argument":"MODEL","optional":false,"default_":true}],"modelSettings":[{"modelPath":"/mnt/data/data/lm/models/gguf/m/Qwen3.6-35B-A3B-UD-Q5_K_XL-mtp.gguf","appArguments":[{"argument":"-nkvo","optional":true,"default_":false},{"argument":"--parallel","optional":true,"default_":true},{"argument":"2","optional":true,"default_":true},{"argument":"4","optional":true,"default_":false},{"argument":"--host","optional":true,"default_":true},{"argument":"0.0.0.0","optional":true,"default_":true},{"argument":"--port","optional":false,"default_":true},{"argument":"5001","optional":false,"default_":true},{"argument":"-t","optional":false,"default_":true},{"argument":"THREADS","optional":false,"default_":true},{"argument":"-ngl","optional":false,"default_":true},{"argument":"GPU_LAYERS","optional":false,"default_":true},{"argument":"--ctx-size","optional":false,"default_":true},{"argument":"CONTEXT_SIZE","optional":false,"default_":true},{"argument":"-m","optional":false,"default_":true},{"argument":"MODEL","optional":false,"default_":true}]}]},{"path":"file:///home/sb/lm/SillyTavern/start.sh","interpreter":null,"arguments":[],"appArguments":[],"modelSettings":[]},{"path":"file:///home/sb/lm/ollama-oai-bridge/start.sh","interpreter":null,"arguments":[],"appArguments":[],"modelSettings":[]}]} \ No newline at end of file diff --git a/lm-launcher.jar b/lm-launcher.jar index e30a2abcc80ff6edb7a31df7bc2a4fd63e0ca34e..f020a6993fa1fa1a7eb86ed803499c28214a0162 100644 GIT binary patch delta 33634 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 delta 29990 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 arguments, List appArguments) { +record App(Path path, Path interpreter, @Deprecated List arguments, List appArguments, List modelSettings) { + + public App { + arguments = arguments == null ? new ArrayList<>() : arguments; + appArguments = appArguments == null ? new ArrayList<>() : appArguments; + modelSettings = modelSettings == null ? new ArrayList<>() : modelSettings; + } static Map> PLACEHOLDERS = Map.of( "MODEL", m -> m.path(), @@ -32,6 +40,31 @@ record App(Path path, Path interpreter, @Deprecated List arguments, List showAll); } + List argumentsForModel(final String modelPath) { + if (modelPath == null || modelPath.isBlank()) { + return copyArguments(this.appArguments); + } + final AppModelSettings savedSettings = this.findModelSettings(modelPath); + if (savedSettings == null) { + return copyArguments(this.appArguments); + } + return this.mergeArguments(savedSettings.appArguments()); + } + + void saveArgumentsForModel(final String modelPath, final List selectedArguments) { + if (modelPath == null || modelPath.isBlank()) { + return; + } + final AppModelSettings updatedSettings = new AppModelSettings(modelPath, copyArguments(selectedArguments)); + for (int i = 0; i < this.modelSettings.size(); i++) { + if (this.modelSettings.get(i).modelPath().equals(modelPath)) { + this.modelSettings.set(i, updatedSettings); + return; + } + } + this.modelSettings.add(updatedSettings); + } + private String argumentsToStringByArgs(final Stream args, boolean showAll) { return args .filter(arg -> showAll || (arg.optional() ? arg.default_() : true)) @@ -39,6 +72,50 @@ record App(Path path, Path interpreter, @Deprecated List arguments, List .collect(Collectors.joining(" ")); } + private List mergeArguments(final List savedArguments) { + if (savedArguments == null || savedArguments.isEmpty()) { + return copyArguments(this.appArguments); + } + final Map occurrences = new HashMap<>(); + final List mergedArguments = new ArrayList<>(this.appArguments.size()); + for (final AppArgument baseArgument : this.appArguments) { + final int occurrenceIndex = occurrences.getOrDefault(baseArgument.argument(), 0); + occurrences.put(baseArgument.argument(), occurrenceIndex + 1); + final AppArgument savedArgument = nthArgument(savedArguments, baseArgument.argument(), occurrenceIndex); + mergedArguments.add(savedArgument == null + ? new AppArgument(baseArgument.argument(), baseArgument.optional(), baseArgument.default_()) + : new AppArgument(baseArgument.argument(), baseArgument.optional(), baseArgument.optional() ? savedArgument.default_() : baseArgument.default_())); + } + return mergedArguments; + } + + private AppModelSettings findModelSettings(final String modelPath) { + return this.modelSettings.stream() + .filter(settings -> settings.modelPath().equals(modelPath)) + .findFirst() + .orElse(null); + } + + private static AppArgument nthArgument(final List arguments, final String argument, final int occurrenceIndex) { + int matchIndex = 0; + for (final AppArgument candidate : arguments) { + if (!candidate.argument().equals(argument)) { + continue; + } + if (matchIndex == occurrenceIndex) { + return candidate; + } + matchIndex++; + } + return null; + } + + private static List copyArguments(final List arguments) { + return arguments.stream() + .map(argument -> new AppArgument(argument.argument(), argument.optional(), argument.default_())) + .collect(Collectors.toCollection(ArrayList::new)); + } + void run(final Model model, final List argumentOverrides) throws IOException, IllegalArgumentException { String interpreterStr = ""; if (this.interpreter() != null) { @@ -62,4 +139,11 @@ record App(Path path, Path interpreter, @Deprecated List arguments, List null, this.path().toAbsolutePath().getParent().toFile()); } + + static record AppModelSettings(String modelPath, List appArguments) { + + public AppModelSettings { + appArguments = appArguments == null ? new ArrayList<>() : appArguments; + } + } } diff --git a/src/de/extio/lm_launcher/Data.java b/src/de/extio/lm_launcher/Data.java index 9b064d4..516e96a 100644 --- a/src/de/extio/lm_launcher/Data.java +++ b/src/de/extio/lm_launcher/Data.java @@ -65,10 +65,13 @@ public class Data { // Migration for (int i = 0; i < appData.apps.size(); i++) { final App app = appData.apps.get(i); - if (app.appArguments() == null) { + if (app.appArguments().isEmpty() && !app.arguments().isEmpty()) { final List arguments = new ArrayList<>(app.arguments().size()); app.arguments().stream().map(argument -> new AppArgument(argument, false, true)).forEach(arguments::add); - appData.apps.set(i, new App(app.path(), app.interpreter(), new ArrayList<>(), arguments)); + appData.apps.set(i, new App(app.path(), app.interpreter(), new ArrayList<>(), arguments, new ArrayList<>(app.modelSettings()))); + } + else if (!app.arguments().isEmpty()) { + appData.apps.set(i, new App(app.path(), app.interpreter(), new ArrayList<>(), new ArrayList<>(app.appArguments()), new ArrayList<>(app.modelSettings()))); } } } @@ -147,6 +150,16 @@ public class Data { .orElse(null); } + static void upsertModel(final Model model) { + for (int i = 0; i < modelData.models().size(); i++) { + if (modelData.models().get(i).path().equals(model.path())) { + modelData.models().set(i, model); + return; + } + } + modelData.models().add(model); + } + static Model defaultModel(final String path) { long ctime = 0; try { diff --git a/src/de/extio/lm_launcher/LaunchFrame.java b/src/de/extio/lm_launcher/LaunchFrame.java index 7601e47..c17321f 100644 --- a/src/de/extio/lm_launcher/LaunchFrame.java +++ b/src/de/extio/lm_launcher/LaunchFrame.java @@ -225,15 +225,7 @@ public class LaunchFrame extends JFrame { this.list.setSelectionMode(ListSelectionModel.SINGLE_SELECTION); this.list.getSelectionModel().addListSelectionListener(e -> { if (!e.getValueIsAdjusting()) { - if (this.table.getCellEditor() != null) { - this.table.getCellEditor().stopCellEditing(); - } - this.appArgumentsTableModel.setRowCount(0); - final DefaultListSelectionModel selectionModel = (DefaultListSelectionModel) e.getSource(); - if (selectionModel.getMinSelectionIndex() > -1) { - final App app = Data.appData.apps().get(selectionModel.getMinSelectionIndex()); - app.appArguments().forEach(arg -> this.appArgumentsTableModel.addRow(new Object[] { arg })); - } + LaunchFrame.this.refreshSelectedAppArguments(); } }); this.scrollPane.setViewportView(this.list); @@ -279,6 +271,7 @@ public class LaunchFrame extends JFrame { final Model model = saved != null ? saved : Data.defaultModel(p.toString()); this.refreshModelSliders(model); } + LaunchFrame.this.refreshSelectedAppArguments(); }); this.scrollPane_1.setViewportView(this.modelTree); @@ -469,7 +462,7 @@ public class LaunchFrame extends JFrame { interpreter = fileChooser.getSelectedFile().toPath(); } - final App app = new App(executable, interpreter, new ArrayList<>(), new ArrayList<>()); + final App app = new App(executable, interpreter, new ArrayList<>(), new ArrayList<>(), new ArrayList<>()); Data.appData.apps().add(app); final AppPropertiesDialog appPropertiesDialog = new AppPropertiesDialog(LaunchFrame.this, app, () -> { @@ -537,7 +530,7 @@ public class LaunchFrame extends JFrame { } final App app = Data.appData.apps().get(index); - Data.appData.apps().add(index, new App(app.path(), app.interpreter(), new ArrayList<>(app.arguments()), new ArrayList<>(app.appArguments()))); + Data.appData.apps().add(index, new App(app.path(), app.interpreter(), new ArrayList<>(app.arguments()), new ArrayList<>(app.appArguments()), new ArrayList<>(app.modelSettings()))); Data.saveApps(); LaunchFrame.this.refresh(); @@ -581,19 +574,19 @@ public class LaunchFrame extends JFrame { template.ctime()); } - final List argumentOverrides = new ArrayList<>(); - if (LaunchFrame.this.table.getCellEditor() != null) { - LaunchFrame.this.table.getCellEditor().stopCellEditing(); - } - for (int i = 0; i < LaunchFrame.this.appArgumentsTableModel.getRowCount(); i++) { - final AppArgument appArgument = (AppArgument) LaunchFrame.this.appArgumentsTableModel.getValueAt(i, 0); - if (appArgument.optional()) { - argumentOverrides.add(appArgument); - } - } + final List selectedArguments = LaunchFrame.this.currentTableArguments(); + final List argumentOverrides = selectedArguments.stream().filter(AppArgument::optional).toList(); try { app.run(model, argumentOverrides); + if (model != null) { + Data.upsertModel(model); + Data.saveModels(); + app.saveArgumentsForModel(selectedPath, selectedArguments); + Data.saveApps(); + LaunchFrame.this.refreshModelSliders(model); + LaunchFrame.this.refreshSelectedAppArguments(); + } } catch (final IllegalArgumentException iae) { JOptionPane.showMessageDialog(LaunchFrame.this, iae.getMessage(), "Error Message", JOptionPane.WARNING_MESSAGE); @@ -631,6 +624,38 @@ public class LaunchFrame extends JFrame { return null; } + private App getSelectedApp() { + final int selectedIndex = this.list.getSelectedIndex(); + if (selectedIndex < 0) { + return null; + } + return Data.appData.apps().get(selectedIndex); + } + + private void refreshSelectedAppArguments() { + if (this.table.getCellEditor() != null) { + this.table.getCellEditor().stopCellEditing(); + } + this.appArgumentsTableModel.setRowCount(0); + final App selectedApp = this.getSelectedApp(); + if (selectedApp == null) { + return; + } + selectedApp.argumentsForModel(this.getSelectedModelPath()) + .forEach(argument -> this.appArgumentsTableModel.addRow(new Object[] { argument })); + } + + private List currentTableArguments() { + if (this.table.getCellEditor() != null) { + this.table.getCellEditor().stopCellEditing(); + } + final List selectedArguments = new ArrayList<>(this.appArgumentsTableModel.getRowCount()); + for (int i = 0; i < this.appArgumentsTableModel.getRowCount(); i++) { + selectedArguments.add((AppArgument) this.appArgumentsTableModel.getValueAt(i, 0)); + } + return selectedArguments; + } + private void refreshModelSliders(final Model model) { this.slider_context.setMaximum(model.maxContextSize()); this.slider_context.setMajorTickSpacing(Math.max(1, model.maxContextSize() / 4)); @@ -712,6 +737,7 @@ public class LaunchFrame extends JFrame { this.modelTree.setModel(new DefaultTreeModel(root)); } + this.refreshSelectedAppArguments(); this.repaint(); }