Web: reload the last-rendered image on SocketIO notification

This commit is contained in:
Sybren A. Stüvel 2022-06-30 18:36:16 +02:00
parent 0fc5ba0bc6
commit 84d598c813
4 changed files with 69 additions and 15 deletions

View File

@ -13,7 +13,7 @@ const websocketURL = ws();
export default { export default {
emits: [ emits: [
// Data from Flamenco Manager: // Data from Flamenco Manager:
"jobUpdate", "taskUpdate", "taskLogUpdate", "message", "workerUpdate", "jobUpdate", "taskUpdate", "taskLogUpdate", "message", "workerUpdate", "lastRenderedUpdate",
// SocketIO events: // SocketIO events:
"sioReconnected", "sioDisconnected" "sioReconnected", "sioDisconnected"
], ],
@ -132,6 +132,13 @@ export default {
this.$emit("jobUpdate", apiJobUpdate); this.$emit("jobUpdate", apiJobUpdate);
}); });
this.socket.on("/last-rendered", (update) => {
// Convert to API object, in order to have the same parsing of data as
// when we'd do an API call.
const apiUpdate = API.SocketIOLastRenderedUpdate.constructFromObject(update)
this.$emit("lastRenderedUpdate", apiUpdate);
});
this.socket.on("/task", (taskUpdate) => { this.socket.on("/task", (taskUpdate) => {
// Convert to API object, in order to have the same parsing of data as // Convert to API object, in order to have the same parsing of data as
// when we'd do an API call. // when we'd do an API call.

View File

@ -2,7 +2,7 @@
<h2 class="column-title">Job Details</h2> <h2 class="column-title">Job Details</h2>
<template v-if="hasJobData"> <template v-if="hasJobData">
<last-rendered-image :jobID="jobData.id" /> <last-rendered-image ref="lastRenderedImage" :jobID="jobData.id" />
<dl> <dl>
<dt class="field-id">ID</dt> <dt class="field-id">ID</dt>
@ -112,6 +112,13 @@ export default {
}, },
}, },
methods: { methods: {
/**
* @param {API.SocketIOLastRenderedUpdate} lastRenderedUpdate
*/
refreshLastRenderedImage(lastRenderedUpdate) {
this.$refs.lastRenderedImage.refreshLastRenderedImage(lastRenderedUpdate);
},
_refreshJobSettings(newJobData) { _refreshJobSettings(newJobData) {
if (objectEmpty(newJobData)) { if (objectEmpty(newJobData)) {
this._clearJobSettings(); this._clearJobSettings();

View File

@ -1,7 +1,7 @@
<script setup> <script setup>
import { ref, watch } from 'vue' import { ref, watch } from 'vue'
import { api } from '@/urls'; import { api } from '@/urls';
import { JobsApi } from '@/manager-api'; import { JobsApi, JobLastRenderedImageInfo, SocketIOLastRenderedUpdate } from '@/manager-api';
import { apiClient } from '@/stores/api-query-count'; import { apiClient } from '@/stores/api-query-count';
const props = defineProps(['jobID']); const props = defineProps(['jobID']);
@ -9,28 +9,58 @@ const imageURL = ref('');
const jobsApi = new JobsApi(apiClient); const jobsApi = new JobsApi(apiClient);
/**
* Fetches the last-rendered info for the given job, then updates the <img> tag for it.
*/
function fetchImageURL(jobID) { function fetchImageURL(jobID) {
jobsApi.fetchJobLastRenderedInfo(jobID) jobsApi.fetchJobLastRenderedInfo(jobID)
.then((info) => { .then(setImageURL)
// info is an api.JobLastRenderedImageInfo object.
for (let suffix of info.suffixes) {
if (!suffix.includes("-tiny")) continue;
let url = new URL(api());
url.pathname = info.base + "/" + suffix
imageURL.value = url.toString();
break;
}
})
.catch((error) => { console.warn("error fetching last-rendered image info:", error) }); .catch((error) => { console.warn("error fetching last-rendered image info:", error) });
} }
/**
* @param {JobLastRenderedImageInfo} thumbnailInfo
*/
function setImageURL(thumbnailInfo) {
// Set the image URL to something appropriate.
for (let suffix of thumbnailInfo.suffixes) {
if (!suffix.includes("-tiny")) continue;
let url = new URL(api());
url.pathname = thumbnailInfo.base + "/" + suffix
url.search = new Date().getTime(); // This forces the image to be reloaded.
imageURL.value = url.toString();
break;
}
}
/**
* @param {SocketIOLastRenderedUpdate} lastRenderedUpdate
*/
function refreshLastRenderedImage(lastRenderedUpdate) {
if (lastRenderedUpdate.job_id != props.jobID) {
console.log(
"LastRenderedImage.vue: refreshLastRenderedImage() received update for job",
lastRenderedUpdate.job_id,
"but this component is showing job", props.jobID);
return;
}
setImageURL(lastRenderedUpdate.thumbnail);
}
// Call fetchImageURL(jobID) whenever the job ID prop changes value.
watch(() => props.jobID, (newJobID) => { watch(() => props.jobID, (newJobID) => {
console.log("Last-Rendered Image: new job ID: ", newJobID); console.log("Last-Rendered Image: new job ID: ", newJobID);
fetchImageURL(newJobID); fetchImageURL(newJobID);
}); });
fetchImageURL(props.jobID); fetchImageURL(props.jobID);
// Expose refreshLastRenderedImage() so that it can be called from the parent
// component in response to SocketIO messages.
defineExpose({
refreshLastRenderedImage,
});
</script> </script>
<template> <template>

View File

@ -3,7 +3,7 @@
<jobs-table ref="jobsTable" :activeJobID="jobID" @tableRowClicked="onTableJobClicked" /> <jobs-table ref="jobsTable" :activeJobID="jobID" @tableRowClicked="onTableJobClicked" />
</div> </div>
<div class="col col-2" id="col-job-details"> <div class="col col-2" id="col-job-details">
<job-details :jobData="jobs.activeJob" @reshuffled="_recalcTasksTableHeight" /> <job-details ref="jobDetails" :jobData="jobs.activeJob" @reshuffled="_recalcTasksTableHeight" />
<tasks-table v-if="hasJobData" ref="tasksTable" :jobID="jobID" :taskID="taskID" @tableRowClicked="onTableTaskClicked" /> <tasks-table v-if="hasJobData" ref="tasksTable" :jobID="jobID" :taskID="taskID" @tableRowClicked="onTableTaskClicked" />
</div> </div>
<div class="col col-3"> <div class="col col-3">
@ -16,6 +16,7 @@
<update-listener ref="updateListener" mainSubscription="allJobs" <update-listener ref="updateListener" mainSubscription="allJobs"
:subscribedJobID="jobID" :subscribedTaskID="taskID" :subscribedJobID="jobID" :subscribedTaskID="taskID"
@jobUpdate="onSioJobUpdate" @taskUpdate="onSioTaskUpdate" @taskLogUpdate="onSioTaskLogUpdate" @jobUpdate="onSioJobUpdate" @taskUpdate="onSioTaskUpdate" @taskLogUpdate="onSioTaskLogUpdate"
@lastRenderedUpdate="onSioLastRenderedUpdate"
@message="onChatMessage" @message="onChatMessage"
@sioReconnected="onSIOReconnected" @sioDisconnected="onSIODisconnected" /> @sioReconnected="onSIOReconnected" @sioDisconnected="onSIODisconnected" />
</template> </template>
@ -154,6 +155,15 @@ export default {
this.taskLog.addTaskLogUpdate(taskLogUpdate); this.taskLog.addTaskLogUpdate(taskLogUpdate);
}, },
/**
* Event handler for SocketIO "last-rendered" updates.
* @param {API.SocketIOLastRenderedUpdate} lastRenderedUpdate
*/
onSioLastRenderedUpdate(lastRenderedUpdate) {
console.log('lastRenderedUpdate:', lastRenderedUpdate);
this.$refs.jobDetails.refreshLastRenderedImage(lastRenderedUpdate);
},
/** /**
* @param {string} jobID job ID to navigate to, can be empty string for "no active job". * @param {string} jobID job ID to navigate to, can be empty string for "no active job".
*/ */