diff options
Diffstat (limited to 'app/src')
-rw-r--r-- | app/src/app.d.ts | 3 | ||||
-rw-r--r-- | app/src/hooks.server.ts | 13 | ||||
-rw-r--r-- | app/src/lib/common/assignments.ts | 18 | ||||
-rw-r--r-- | app/src/lib/server/assignments.ts | 27 | ||||
-rw-r--r-- | app/src/lib/server/beanstalkd.ts | 19 | ||||
-rw-r--r-- | app/src/routes/assignments/+page.svelte | 19 | ||||
-rw-r--r-- | app/src/routes/assignments/[assignmentId]/+page.server.ts | 8 | ||||
-rw-r--r-- | app/src/routes/assignments/[assignmentId]/+page.svelte | 4 |
8 files changed, 83 insertions, 28 deletions
diff --git a/app/src/app.d.ts b/app/src/app.d.ts index 6dba3f1..71e7b15 100644 --- a/app/src/app.d.ts +++ b/app/src/app.d.ts @@ -1,5 +1,6 @@ import type { User } from "$lib/server/users"; import type { S3Client } from "@aws-sdk/client-s3"; +import type BeanstalkdClient from "beanstalkd"; import type { PoolClient } from "pg"; // See https://svelte.dev/docs/kit/types#app.d.ts @@ -12,6 +13,8 @@ declare global { s3Client: S3Client; + beanstalkdClient: BeanstalkdClient; + /** * The user, if they are logged in. * diff --git a/app/src/hooks.server.ts b/app/src/hooks.server.ts index f342e03..78342cd 100644 --- a/app/src/hooks.server.ts +++ b/app/src/hooks.server.ts @@ -1,21 +1,23 @@ -import { getDbConnection } from "$lib/server/db"; +import { getDbClient } from "$lib/server/db"; import { getS3Client } from "$lib/server/s3"; import { validateSessionToken } from "$lib/server/sessions"; import { type Handle } from "@sveltejs/kit"; import { sequence } from "@sveltejs/kit/hooks"; +import { beanstalkdHandle } from "$lib/server/beanstalkd"; const dbHandle = (async ({ event, resolve }) => { - const dbConn = await getDbConnection(); - event.locals.dbConn = dbConn; + const dbClient = await getDbClient(); + event.locals.dbClient = dbClient; try { return await resolve(event); } finally { - dbConn.release(); + dbClient.release(); } }) satisfies Handle; // FIXME: Kind of stupid to load for every request. Should probs move handler to $lib and import for relevant routes. +// Same goes for beanstalkd. const s3Handle = (async ({ event, resolve }) => { const s3Client = getS3Client(); event.locals.s3Client = s3Client; @@ -39,4 +41,5 @@ const sessionHandle = (async ({ event, resolve }) => { return resolve(event); }) satisfies Handle; -export const handle = sequence(dbHandle, s3Handle, sessionHandle); +// FIXME: Kind of stupid to load for every request. Should probs move handler to $lib and import for relevant routes. +export const handle = sequence(dbHandle, s3Handle, beanstalkdHandle, sessionHandle); diff --git a/app/src/lib/common/assignments.ts b/app/src/lib/common/assignments.ts index 79553cd..6e9d574 100644 --- a/app/src/lib/common/assignments.ts +++ b/app/src/lib/common/assignments.ts @@ -7,12 +7,12 @@ export interface CemetaryPlot { } /** Corresponds to `assignment_state`. */ -export type AssignmentState = "AWAITING_GARDENER_NOTIFICATION" - | "AWAITING_FINISH" - | "AWAITING_WATERMARKING" - | "AWAITING_OWNER_NOTIFICATION" - | "DONE" - ; +export type AssignmentState = + | "AWAITING_GARDENER_NOTIFICATION" + | "AWAITING_FINISH" + | "AWAITING_WATERMARKING" + | "AWAITING_OWNER_NOTIFICATION" + | "DONE"; /** A row from the `assignments` table. */ export interface Assignment { @@ -23,10 +23,10 @@ export interface Assignment { state: AssignmentState; } - // FIXME: We have ORM at home. A more clearly defined (OOP) model layer. /** Checks whether the state of the assignment allows it to be "finished". */ export function canBeFinished(assignment: Assignment): boolean { - return (assignment.state === "AWAITING_GARDENER_NOTIFICATION" || - assignment.state === "AWAITING_FINISH") + return ( + assignment.state === "AWAITING_GARDENER_NOTIFICATION" || assignment.state === "AWAITING_FINISH" + ); } diff --git a/app/src/lib/server/assignments.ts b/app/src/lib/server/assignments.ts index c66f25c..9c28cff 100644 --- a/app/src/lib/server/assignments.ts +++ b/app/src/lib/server/assignments.ts @@ -1,6 +1,7 @@ -import { PutObjectCommand, type S3Client } from "@aws-sdk/client-s3"; /*=;* / +import { PutObjectCommand, type S3Client } from "@aws-sdk/client-s3"; /*=;*/ import type { ClientBase } from "pg"; -import type { CemetaryPlot, Assignment, AssignmentState } from "../common/assignments"; +import type { CemetaryPlot, Assignment } from "../common/assignments"; +import type BeanstalkdClient from "beanstalkd"; /** * Retrieves all assignments for the given user. @@ -73,17 +74,24 @@ export async function getAssignmentAndCemetaryById( } export interface FinishAssignmentArgs { + dbClient: ClientBase; + s3Client: S3Client; + beanstalkdClient: BeanstalkdClient; + images: { bytes: Uint8Array; name: string }[]; note?: string; assignmentId: number; } // TODO: Error recovery. -export async function finishAssignment( - dbClient: ClientBase, - s3Client: S3Client, - { images, note, assignmentId }: FinishAssignmentArgs, -): Promise<void> { +export async function finishAssignment({ + dbClient, + s3Client, + beanstalkdClient, + images, + note, + assignmentId, +}: FinishAssignmentArgs): Promise<void> { // Upload to S3, returning path // FIXME: Should be factored out? const uploadPromises = images.map(async (image) => { @@ -101,7 +109,10 @@ export async function finishAssignment( }); const uploadedImages = await Promise.all(uploadPromises); - // TODO: Add beanstalkd job + // Instruct background worker to do watermarking. + // FIXME: magic constants yay how fun + await beanstalkdClient.use("watermarking"); + console.debug(await beanstalkdClient.put(0, 0, 60, JSON.stringify({ assignmentId }))); await dbClient.query("BEGIN"); diff --git a/app/src/lib/server/beanstalkd.ts b/app/src/lib/server/beanstalkd.ts new file mode 100644 index 0000000..10f392a --- /dev/null +++ b/app/src/lib/server/beanstalkd.ts @@ -0,0 +1,19 @@ +import pkg from "beanstalkd"; +import type { Handle } from "@sveltejs/kit"; + +// Annoying CommonJS interop issue (vitejs/vite#2139) which combines with incorrect typings from DefinitelyTyped project :( +// @ts-ignore +const BeanstalkdClient = pkg.default as typeof pkg; + +export const beanstalkdHandle = (async ({ event, resolve }) => { + // FIXME: Should obv. read from env. + const beanstalkdClient = new BeanstalkdClient("localhost", 11300); + await beanstalkdClient.connect(); + + event.locals.beanstalkdClient = beanstalkdClient; + try { + return await resolve(event); + } finally { + beanstalkdClient.quit(); + } +}) satisfies Handle; diff --git a/app/src/routes/assignments/+page.svelte b/app/src/routes/assignments/+page.svelte index f43767d..5a3a4cb 100644 --- a/app/src/routes/assignments/+page.svelte +++ b/app/src/routes/assignments/+page.svelte @@ -1,15 +1,19 @@ <!-- The /assignments index page gives an overview of assignments --> <script lang="ts"> + import { canBeFinished } from "$lib/common/assignments"; import type { PageProps } from "./$types"; const { data }: PageProps = $props(); + const unfinishedAssignments = $derived(data.assignments.filter(canBeFinished)); + const finishedAssignments = $derived(data.assignments.filter((a) => !canBeFinished(a))); </script> -<h1>Kommende opgaver for {data.user.firstName}</h1> +<h1>{data.user.firstName}s opgaver</h1> +<h2>Kommende opgaver</h2> <ol> - {#each data.assignments as assignment} + {#each unfinishedAssignments as assignment} <li> <span>{assignment.date}</span> <a href={`/assignments/${assignment.id}`}>Mere info</a> @@ -17,5 +21,12 @@ {/each} </ol> -<style> -</style> +<h2>Færdiggjorte opgaver</h2> +<ol> + {#each finishedAssignments as assignment} + <li> + <span>{assignment.date}</span> + <a href={`/assignments/${assignment.id}`}>Mere info</a> + </li> + {/each} +</ol> diff --git a/app/src/routes/assignments/[assignmentId]/+page.server.ts b/app/src/routes/assignments/[assignmentId]/+page.server.ts index 3b53a7c..b6634f0 100644 --- a/app/src/routes/assignments/[assignmentId]/+page.server.ts +++ b/app/src/routes/assignments/[assignmentId]/+page.server.ts @@ -42,7 +42,13 @@ export const actions = { })), ); - await finishAssignment(locals.dbClient, locals.s3Client, { + const { beanstalkdClient, dbClient, s3Client } = locals; + + await finishAssignment({ + beanstalkdClient, + dbClient, + s3Client, + images, note, assignmentId: +params.assignmentId, // We have parsing at home... diff --git a/app/src/routes/assignments/[assignmentId]/+page.svelte b/app/src/routes/assignments/[assignmentId]/+page.svelte index 6b24f38..bf955f9 100644 --- a/app/src/routes/assignments/[assignmentId]/+page.svelte +++ b/app/src/routes/assignments/[assignmentId]/+page.svelte @@ -30,7 +30,9 @@ </label> <label> Ekstra bemærkninger: - <textarea name="notes" placeholder="F.eks.: Vi løb tør for roser (?). De kommer i overmorgen :)" + <textarea + name="notes" + placeholder="F.eks.: Vi løb tør for roser (?). De kommer i overmorgen :)" ></textarea> </label> <button>Færddigør job</button> |