Add built-in scheduler when running --webui

Also:
- Default to webui

Close #16
This commit is contained in:
2025-03-04 20:03:34 +01:00
parent 1f81d48aad
commit 0196476370
12 changed files with 239 additions and 86 deletions

View File

@@ -150,6 +150,10 @@ iframe { display: block; width: 100%; border: none; height: 60vh; }
.parser-desc { display: block; padding: 0 .8rem;
font-size: .85em; white-space: pre-wrap; }
#wrap.setup-required { grid-template-columns: 1fr 450px 1fr; justify-content: center; }
.setup-required aside { grid-column: 2; width: 450px; margin: auto; }
.setup-required main { display: none; }
/***
* Slider
* Thanks: mrhyddenn

View File

@@ -45,7 +45,7 @@ class App {
async generateSidebar() {
this.aside.appendChild(this.generateTextElement("h2", this.tls.settings)); // TODO
this.aside.appendChild(this.generateTextElement("h2", this.tls.settings));
// Set up fields
const instanceLinkArea = this.generateLabelInput("instance-link",
@@ -304,6 +304,36 @@ class App {
}
manageUpload() {
const transferOverlay = document.createElement("div");
transferOverlay.id = "transfer-overlay";
transferOverlay.classList.add("transfer-overlay");
const hl = document.createElement("div");
hl.classList.add("transfer-overlay-hl");
hl.appendChild(this.generateTextElement("h3", this.tls.upload));
const closeB = document.createElement("span");
closeB.classList.add("overlay-close");
hl.appendChild(closeB);
closeB.addEventListener('click', function() { location.reload(); });
// closeB.addEventListener('click', function() { transferOverlay.parentElement.removeChild(transferOverlay); });
transferOverlay.appendChild(hl);
const transferMsgs = document.createElement("div");
transferMsgs.classList.add("transfer-msgs");
transferOverlay.appendChild(transferMsgs);
this.wrap.appendChild(transferOverlay);
const iframe = document.createElement("iframe");
iframe.src = "/trigger-upload";
transferOverlay.appendChild(iframe);
}
generateActionsMenu() {
if (this.uploadableFiles.metadata.length === 0 && this.uploadableFiles.media_files.length === 0) {
@@ -316,35 +346,29 @@ class App {
const app = this;
uploadTrigger.addEventListener('click', function() {
const transferOverlay = document.createElement("div");
transferOverlay.id = "transfer-overlay";
transferOverlay.classList.add("transfer-overlay");
const hl = document.createElement("div");
hl.classList.add("transfer-overlay-hl");
hl.appendChild(app.generateTextElement("h3", app.tls.upload));
const closeB = document.createElement("span");
closeB.classList.add("overlay-close");
hl.appendChild(closeB);
closeB.addEventListener('click', function() { location.reload(); });
// closeB.addEventListener('click', function() { transferOverlay.parentElement.removeChild(transferOverlay); });
transferOverlay.appendChild(hl);
const transferMsgs = document.createElement("div");
transferMsgs.classList.add("transfer-msgs");
transferOverlay.appendChild(transferMsgs);
app.wrap.appendChild(transferOverlay);
const iframe = document.createElement("iframe");
iframe.src = "/trigger-upload";
transferOverlay.appendChild(iframe);
app.manageUpload();
}, {once: true});
// Handle next auto upload
const nextAutoUpload = document.createElement("span");
const startTimeStr = "Next scheduled check: ";
this.actionsArea.appendChild(nextAutoUpload);
const options1 = {
year: 'numeric',
month: '2-digit',
day: '2-digit',
hour: '2-digit',
minute: '2-digit',
};
const dateTimeFormat1 = new Intl.DateTimeFormat(this.lang, options1);
const nextUploadTime = Date.parse(this.config.next_auto_upload);
const now = new Date();
const diffMs = nextUploadTime - now;
const diffMins = Math.round((diffMs % 86400000) / 60000); // minutes
nextAutoUpload.textContent = dateTimeFormat1.format(nextUploadTime) + " (in " + diffMins + " mins)";
}
@@ -377,7 +401,7 @@ class App {
render() {
if (this.config.setup_required === true) {
wrap.classList.add("one-column");
wrap.classList.add("setup-required");
this.generateSidebar();
}
else {

View File

@@ -5,18 +5,29 @@ import (
"fmt"
"net/http"
"gitea.armuli.eu/museum-digital/museum-digital-webdav-uploader/src/configloader"
"gitea.armuli.eu/museum-digital/museum-digital-webdav-uploader/src/meta"
)
type getSettingsApiResponse struct {
Version string `json:"version"`
SetupRequired bool `json:"setup_required"`
Settings configloader.MDWebDavUploaderConfig `json:"settings"`
NextAutoUpload string `json:"next_auto_upload"`
}
// Generates the API output for listing current settings.
func serveApiGetSettings(w http.ResponseWriter, r *http.Request) {
var nextAutoUpOut string
nextAutoUp, err := scheduledUpload.NextRun()
if err != nil {
nextAutoUpOut = "";
} else {
nextAutoUpOut = nextAutoUp.Format("2006-01-02 15:04:05")
}
setHeadersForJson(w)
output := getSettingsApiResponse{SetupRequired: setupRequired, Settings: config}
output := getSettingsApiResponse{SetupRequired: setupRequired, Settings: config, Version: meta.GetVersion(), NextAutoUpload: nextAutoUpOut}
outputJson, encodeErr := json.Marshal(output)
if encodeErr != nil {

View File

@@ -18,14 +18,14 @@ func serveApiListUploadable(w http.ResponseWriter, r *http.Request) {
setHeadersForJson(w)
var output listUploadableApiResponse
if setupRequired == true {
fmt.Fprint(w, "{'metadata': '', 'media_files': []}")
return
output = listUploadableApiResponse{Metadata: []string{}, MediaFiles: []string{}}
} else {
uploadableMetadata, uploadableMedia := uploadsrcdir.GetUploadableFiles(config)
output = listUploadableApiResponse{Metadata: uploadableMetadata, MediaFiles: uploadableMedia}
}
uploadableMetadata, uploadableMedia := uploadsrcdir.GetUploadableFiles(config)
output := listUploadableApiResponse{Metadata: uploadableMetadata, MediaFiles: uploadableMedia}
outputJson, encodeErr := json.Marshal(output)
if encodeErr != nil {
panic("Failed to create JSON")

View File

@@ -6,11 +6,16 @@ import (
"net/http"
"os/exec"
"runtime"
"time"
"github.com/go-co-op/gocron/v2"
"gitea.armuli.eu/museum-digital/museum-digital-webdav-uploader/src/cli"
"gitea.armuli.eu/museum-digital/museum-digital-webdav-uploader/src/configloader"
)
var config configloader.MDWebDavUploaderConfig
var setupRequired bool
var scheduler gocron.Scheduler
var scheduledUpload gocron.Job
// Opens the application in the default browser.
func openInBrowser(port string) {
@@ -33,6 +38,37 @@ func openInBrowser(port string) {
}
func scheduleUploads() {
s, err := gocron.NewScheduler()
defer func() { _ = s.Shutdown() }()
if err != nil {
panic("Failed to set up scheduler")
}
j, jobErr := s.NewJob(
gocron.DurationJob(
3 * time.Hour,
),
gocron.NewTask(
func() {
fmt.Println("Checking if an upload should be done")
fmt.Println(time.Now().Format("20060102150405"))
cli.Upload()
},
),
)
if jobErr != nil {
panic("Failed to set up scheduler job")
}
scheduledUpload = j
s.Start()
select {}
}
// Sets up the server and manages routing.
func Run() {
@@ -46,7 +82,6 @@ func Run() {
http.HandleFunc("/list-parsers", serveApiListParsers) // API to list available parsers.
http.HandleFunc("/update-settings", serveApiUpdateSettings) // API for updating settings
http.HandleFunc("/trigger-upload", serveApiTriggerUpload) // Serve page for specific files
// http.HandleFunc("/contribute.json", ) // Serve page for specific files
http.HandleFunc("/md-uploader.css", serveCss) // Main CSS file.
http.HandleFunc("/md-uploader.js", serveJs) // Main JS file.
http.HandleFunc("/logo.svg", serveLogo) // Logo.
@@ -63,8 +98,11 @@ func Run() {
}();
go func() {
time.Sleep(5)
openInBrowser(port)
}();
select {}
go scheduleUploads()
select{}
}