about summary refs log tree commit diff
diff options
context:
space:
mode:
authorFrederick Muriuki Muriithi2026-01-08 14:17:41 -0600
committerFrederick Muriuki Muriithi2026-01-08 14:17:41 -0600
commit8e8218e4737f251adaf6c2977d0e1e1775dfed93 (patch)
tree88a791cd119bc28e7c453cc929726eae70a8bec8
parentf33d4ded8cefa3ac884c295120ddff00100266c2 (diff)
downloadgn-uploader-8e8218e4737f251adaf6c2977d0e1e1775dfed93.tar.gz
Stop a background job manually.
-rw-r--r--uploader/background_jobs.py30
-rw-r--r--uploader/templates/background-jobs/stop-job.html61
2 files changed, 91 insertions, 0 deletions
diff --git a/uploader/background_jobs.py b/uploader/background_jobs.py
index 16d372c..ac6c033 100644
--- a/uploader/background_jobs.py
+++ b/uploader/background_jobs.py
@@ -194,3 +194,33 @@ def delete_single(job_id: uuid.UUID):
                 "background-jobs.job_summary", job_id=job_id))
         except JobNotFound as _jnf:
             return render_template("jobs/job-not-found.html", job_id=job_id)
+
+
+@background_jobs_bp.route("/stop/<uuid:job_id>", methods=["GET", "POST"])
+@require_login
+def stop_job(job_id: uuid.UUID):
+    """Stop a running job."""
+    with sqlite3.connection(app.config["ASYNCHRONOUS_JOBS_SQLITE_DB"]) as conn:
+        try:
+            job = jobs.job(conn, job_id, fulldetails=True)
+            status = job["metadata"]["status"]
+            if status != "running":
+                flash("Cannot stop a job that is not running.", "alert alert-danger")
+                return redirect(url_for(
+                    "background-jobs.job_summary", job_id=job_id))
+
+            if request.method == "GET":
+                return render_template("background-jobs/stop-job.html",
+                                       job=job,
+                                       display_datetime=make_datetime_formatter())
+
+            if request.form["btn-confirm-stop"] == "stop":
+                jobs.kill_job(conn, job_id)
+                flash("Job was stopped successfully.", "alert alert-success")
+                return redirect(url_for(
+                    "background-jobs.job_summary", job_id=job_id))
+            flash("Stop cancelled.", "alert alert-info")
+            return redirect(url_for(
+                "background-jobs.job_summary", job_id=job_id))
+        except JobNotFound as _jnf:
+            return render_template("jobs/job-not-found.html", job_id=job_id)
diff --git a/uploader/templates/background-jobs/stop-job.html b/uploader/templates/background-jobs/stop-job.html
new file mode 100644
index 0000000..fc190ac
--- /dev/null
+++ b/uploader/templates/background-jobs/stop-job.html
@@ -0,0 +1,61 @@
+{%extends "background-jobs/base.html"%}
+{%from "flash_messages.html" import flash_all_messages%}
+{%from "background-jobs/macro-display-job-details.html" import display_job_details%}
+
+{%block title%}Background Jobs{%endblock%}
+
+{%block pagetitle%}Background Jobs{%endblock%}
+
+{%block breadcrumbs%}
+{{super()}}
+<li class="breadcrumb-item">
+  <a href="{{url_for('background-jobs.job_summary', job_id=job.job_id)}}">
+    summary
+  </a>
+</li>
+{%endblock%}
+
+{%block contents%}
+{{flash_all_messages()}}
+
+<div class="row">
+  <h2 class="heading">background jobs: stop?</h2>
+
+  <p class="text-danger">Are you sure you want to stop the job below?</p>
+
+  {{display_job_details(job, display_datetime)}}
+</div>
+
+<div class="row">
+  <form id="frm-stop-job"
+        method="POST"
+        action="{{url_for('background-jobs.stop_job', job_id=job.job_id)}}">
+    <div class="row">
+      <div class="col">
+        <input type="submit"
+               class="btn btn-info"
+               value="cancel"
+               name="btn-confirm-stop" />
+      </div>
+      <div class="col">
+        <input type="submit"
+               class="btn btn-danger"
+               value="stop"
+               name="btn-confirm-stop" />
+      </div>
+    </div>
+  </form>
+</div>
+{%endblock%}
+
+
+{%block sidebarcontents%}
+<div class="row">
+  <h6 class="subheading">What is this?</h6>
+</div>
+<div class="row">
+  <p>Confirm whether or not you want to stop job
+    <strong>{{job.job_id}}</strong>.</p>
+</div>
+{{super()}}
+{%endblock%}