diff --git a/client/src/main/java/ctbrec/ui/RecordedModelsTab.java b/client/src/main/java/ctbrec/ui/RecordedModelsTab.java index 8c5f7160..87ccfef8 100644 --- a/client/src/main/java/ctbrec/ui/RecordedModelsTab.java +++ b/client/src/main/java/ctbrec/ui/RecordedModelsTab.java @@ -174,7 +174,7 @@ public class RecordedModelsTab extends Tab implements TabSelectionListener { priority.setPrefWidth(90); priority.setEditable(true); priority.setOnEditStart(e -> cellEditing = true); - priority.setOnEditCommit(this::updatePriority); + priority.setOnEditCommit(this::onUpdatePriority); priority.setOnEditCancel(e -> cellEditing = false); TableColumn notes = new TableColumn<>("Notes"); notes.setCellValueFactory(cdf -> { @@ -277,26 +277,31 @@ public class RecordedModelsTab extends Tab implements TabSelectionListener { restoreState(); } - private void updatePriority(CellEditEvent evt) { + private void onUpdatePriority(CellEditEvent evt) { try { int prio = Optional.ofNullable(evt.getNewValue()).map(Number::intValue).orElse(-1); - if (prio < 0 || prio > 100) { - String msg = "Priority has to be between 0 and 100"; - Dialogs.showError(table.getScene(), "Invalid value", msg, null); - } else { - evt.getRowValue().setPriority(prio); - try { - Config.getInstance().save(); - } catch (IOException e) { - LOG.warn("Couldn't save updated priority value {} for {} - {}", evt.getNewValue(), evt.getRowValue().getName(), e.getMessage()); - } - } + JavaFxModel m = evt.getRowValue(); + updatePriority(m, prio); table.refresh(); } finally { cellEditing = false; } } + private void updatePriority(JavaFxModel model, int priority) { + try { + if (priority < 0 || priority > 100) { + String msg = "Priority has to be between 0 and 100"; + Dialogs.showError(table.getScene(), "Invalid value", msg, null); + } else { + model.setPriority(priority); + recorder.priorityChanged(model.getDelegate()); + } + } catch (InvalidKeyException | NoSuchAlgorithmException | IOException e) { + Dialogs.showError(table.getScene(), "Couldn't update priority", e.getMessage(), e); + } + } + private void addModel(ActionEvent e) { String input = model.getText(); if (StringUtil.isBlank(input)) { @@ -735,11 +740,7 @@ public class RecordedModelsTab extends Tab implements TabSelectionListener { } prio = Math.min(Math.max(0, prio), 100); m.setPriority(prio); - try { - Config.getInstance().save(); - } catch (IOException e) { - LOG.warn("Couldn't save updated priority value {} for {} - {}", prio, m.getName(), e.getMessage()); - } + updatePriority(m, prio); } }); diff --git a/common/src/main/java/ctbrec/recorder/NextGenLocalRecorder.java b/common/src/main/java/ctbrec/recorder/NextGenLocalRecorder.java index 02ca0075..a9ff35bd 100644 --- a/common/src/main/java/ctbrec/recorder/NextGenLocalRecorder.java +++ b/common/src/main/java/ctbrec/recorder/NextGenLocalRecorder.java @@ -657,4 +657,23 @@ public class NextGenLocalRecorder implements Recorder { } LOG.error("Recording {} not found. Can't rerun post-processing", recording); } + + @Override + public void priorityChanged(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException { + recorderLock.lock(); + try { + if (models.contains(model)) { + int index = models.indexOf(model); + models.get(index).setPriority(model.getPriority()); + config.save(); + } else { + LOG.warn("Couldn't change priority for model {}. Not found in list", model.getName()); + return; + } + } catch (IOException e) { + LOG.error("Couldn't save config", e); + } finally { + recorderLock.unlock(); + } + } } diff --git a/common/src/main/java/ctbrec/recorder/Recorder.java b/common/src/main/java/ctbrec/recorder/Recorder.java index 06dbea27..f7b191a9 100644 --- a/common/src/main/java/ctbrec/recorder/Recorder.java +++ b/common/src/main/java/ctbrec/recorder/Recorder.java @@ -11,11 +11,11 @@ import ctbrec.Recording; import ctbrec.io.HttpClient; public interface Recorder { - public void startRecording(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException, IllegalStateException; + public void startRecording(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException; - public void stopRecording(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException, IllegalStateException; + public void stopRecording(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException; - public void switchStreamSource(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException, IllegalStateException; + public void switchStreamSource(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException; /** * Returns true, if a model is in the list of models to record. This does not reflect, if there currently is a recording running. The model might be offline @@ -30,14 +30,14 @@ public interface Recorder { */ public List getModels(); - public List getRecordings() throws IOException, InvalidKeyException, NoSuchAlgorithmException, IllegalStateException; + public List getRecordings() throws IOException, InvalidKeyException, NoSuchAlgorithmException; - public void delete(Recording recording) throws IOException, InvalidKeyException, NoSuchAlgorithmException, IllegalStateException; + public void delete(Recording recording) throws IOException, InvalidKeyException, NoSuchAlgorithmException; public void shutdown(); - public void suspendRecording(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException, IllegalStateException; - public void resumeRecording(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException, IllegalStateException; + public void suspendRecording(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException; + public void resumeRecording(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException; public boolean isSuspended(Model model); @@ -55,7 +55,7 @@ public interface Recorder { * @throws NoSuchAlgorithmException * @throws InvalidKeyException */ - public default List getCurrentlyRecording() throws InvalidKeyException, NoSuchAlgorithmException, IllegalStateException, IOException { + public default List getCurrentlyRecording() throws InvalidKeyException, NoSuchAlgorithmException, IOException { List recordings = getRecordings(); return getModels().stream().filter(m -> { for (Recording recording : recordings) { @@ -92,5 +92,15 @@ public interface Recorder { * @throws InvalidKeyException * @throws IOException */ - public void rerunPostProcessing(Recording recording) throws IOException, InvalidKeyException, NoSuchAlgorithmException, IllegalStateException; + public void rerunPostProcessing(Recording recording) throws IOException, InvalidKeyException, NoSuchAlgorithmException; + + /** + * Tells the recorder, that the recrodng priority for the given model has changed + * + * @param model the model with changed priority. The new value can be retrieved with {@link Model#getPriority()} + * @throws IOException + * @throws InvalidKeyException + * @throws NoSuchAlgorithmException + */ + public void priorityChanged(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException; } diff --git a/common/src/main/java/ctbrec/recorder/RemoteRecorder.java b/common/src/main/java/ctbrec/recorder/RemoteRecorder.java index 49bdcdab..891c27dc 100644 --- a/common/src/main/java/ctbrec/recorder/RemoteRecorder.java +++ b/common/src/main/java/ctbrec/recorder/RemoteRecorder.java @@ -138,7 +138,7 @@ public class RemoteRecorder implements Recorder { @Override public List getModels() { if (!lastSync.equals(Instant.EPOCH) && lastSync.isBefore(Instant.now().minusSeconds(60))) { - throw new RuntimeException("Last sync was over a minute ago"); + throw new IllegalStateException("Last sync was over a minute ago"); } return new ArrayList<>(models); } @@ -149,6 +149,9 @@ public class RemoteRecorder implements Recorder { } private class SyncThread extends Thread { + private static final String SERVER_RETURNED_ERROR = "Server returned error: {} - {}"; + private static final String COULDNT_SYNCHRONIZE_WITH_SERVER = "Couldn't synchronize with server"; + private static final String COULDNT_SYNCHRONIZE_WITH_SERVER_HTTP_STATUS = "Couldn't synchronize with server. HTTP status: {} - {}"; private volatile boolean running = false; public SyncThread() { @@ -182,11 +185,11 @@ public class RemoteRecorder implements Recorder { spaceTotal = resp.getLong("spaceTotal"); spaceFree = resp.getLong("spaceFree"); } else { - LOG.error("Couldn't synchronize with server. HTTP status: {} - {}", response.code(), json); + LOG.error(COULDNT_SYNCHRONIZE_WITH_SERVER_HTTP_STATUS, response.code(), json); } } } catch (IOException | InvalidKeyException | NoSuchAlgorithmException | IllegalStateException e) { - LOG.error("Couldn't synchronize with server", e); + LOG.error(COULDNT_SYNCHRONIZE_WITH_SERVER, e); } } @@ -212,14 +215,14 @@ public class RemoteRecorder implements Recorder { } lastSync = Instant.now(); } else { - LOG.error("Server returned error: {} - {}", resp.status, resp.msg); + LOG.error(SERVER_RETURNED_ERROR, resp.status, resp.msg); } } else { - LOG.error("Couldn't synchronize with server. HTTP status: {} - {}", response.code(), json); + LOG.error(COULDNT_SYNCHRONIZE_WITH_SERVER_HTTP_STATUS, response.code(), json); } } } catch (IOException | InvalidKeyException | NoSuchAlgorithmException | IllegalStateException e) { - LOG.error("Couldn't synchronize with server", e); + LOG.error(COULDNT_SYNCHRONIZE_WITH_SERVER, e); } } @@ -244,14 +247,14 @@ public class RemoteRecorder implements Recorder { } } } else { - LOG.error("Server returned error: {} - {}", resp.status, resp.msg); + LOG.error(SERVER_RETURNED_ERROR, resp.status, resp.msg); } } else { - LOG.error("Couldn't synchronize with server. HTTP status: {} - {}", response.code(), json); + LOG.error(COULDNT_SYNCHRONIZE_WITH_SERVER_HTTP_STATUS, response.code(), json); } } } catch (IOException | InvalidKeyException | NoSuchAlgorithmException | IllegalStateException e) { - LOG.error("Couldn't synchronize with server", e); + LOG.error(COULDNT_SYNCHRONIZE_WITH_SERVER, e); } } @@ -284,14 +287,14 @@ public class RemoteRecorder implements Recorder { } recordings = newRecordings; } else { - LOG.error("Server returned error: {} - {}", resp.status, resp.msg); + LOG.error(SERVER_RETURNED_ERROR, resp.status, resp.msg); } } else { - LOG.error("Couldn't synchronize with server. HTTP status: {} - {}", response.code(), json); + LOG.error(COULDNT_SYNCHRONIZE_WITH_SERVER_HTTP_STATUS, response.code(), json); } } } catch (IOException | InvalidKeyException | NoSuchAlgorithmException | IllegalStateException e) { - LOG.error("Couldn't synchronize with server", e); + LOG.error(COULDNT_SYNCHRONIZE_WITH_SERVER, e); } } @@ -479,4 +482,9 @@ public class RemoteRecorder implements Recorder { } } } + + @Override + public void priorityChanged(Model model) throws IOException, InvalidKeyException, NoSuchAlgorithmException { + sendRequest("changePriority", model); + } } diff --git a/server/src/main/java/ctbrec/recorder/server/RecorderServlet.java b/server/src/main/java/ctbrec/recorder/server/RecorderServlet.java index 685ba692..da9dd7dd 100644 --- a/server/src/main/java/ctbrec/recorder/server/RecorderServlet.java +++ b/server/src/main/java/ctbrec/recorder/server/RecorderServlet.java @@ -168,6 +168,11 @@ public class RecorderServlet extends AbstractCtbrecServlet { response = "{\"status\": \"success\", \"spaceTotal\": "+recorder.getTotalSpaceBytes()+", \"spaceFree\": "+recorder.getFreeSpaceBytes()+"}"; resp.getWriter().write(response); break; + case "changePriority": + recorder.priorityChanged(request.model); + response = "{\"status\": \"success\"}"; + resp.getWriter().write(response); + break; default: resp.setStatus(SC_BAD_REQUEST); response = "{\"status\": \"error\", \"msg\": \"Unknown action ["+request.action+"]\"}";