diff --git a/src/app/jams/(manip)/delete/content/[contentid]/components/form.tsx b/src/app/jams/(manip)/delete/content/[contentid]/components/form.tsx
new file mode 100644
index 0000000..e474a1c
--- /dev/null
+++ b/src/app/jams/(manip)/delete/content/[contentid]/components/form.tsx
@@ -0,0 +1,31 @@
+'use client';
+import React from "react";
+import { useFormik } from "formik";
+import { useRouter } from "next/navigation";
+
+export function Form({contentID}:{contentID:string}) {
+ const router = useRouter();
+ const formik = useFormik({
+ initialValues: {},
+ onSubmit: async (values) => {
+ const submitRequest = await fetch(`/jams/api/content/${contentID}`, {
+ method: "DELETE"
+ });
+
+ if (submitRequest.ok) {
+ router.push(`/jams/`);
+ } else {
+ formik.setSubmitting(false);
+ }
+ },
+ });
+
+ return (
+
+ );
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/delete/content/[contentid]/page.tsx b/src/app/jams/(manip)/delete/content/[contentid]/page.tsx
new file mode 100644
index 0000000..04f48b9
--- /dev/null
+++ b/src/app/jams/(manip)/delete/content/[contentid]/page.tsx
@@ -0,0 +1,67 @@
+
+import { Conditional, ConditionalNull } from "@/components/utility/Conditional";
+import { MainLayout } from "@/layout/MainLayout/MainLayout";
+import { db } from "@/lib/mastoauth/kysely";
+import { JSONContentTable, JSONJamTable } from "@/lib/mastoauth/realtypes";
+import { cookies } from "next/headers";
+import { notFound, redirect } from "next/navigation";
+import { Form } from "./components/form";
+
+export default async function Home({
+ params
+}: {
+ params: {
+ contentid: string
+ }
+}) {
+ const cookieStore = cookies();
+ const token = cookieStore.get('token')?.value;
+ let existingUser;
+ if (token != null) {
+ let existingToken = await db
+ .selectFrom('tokens')
+ .where('tokens.id', '=', token)
+ .select('owner')
+ .executeTakeFirst();
+
+ if (existingToken != null) {
+ existingUser = await db
+ .selectFrom('users')
+ .where('users.id', '=', existingToken.owner)
+ .selectAll()
+ .executeTakeFirst();
+ }
+ }
+
+ if (existingUser == null) return redirect("/jams/");
+
+ const contentid = params.contentid;
+
+ if (contentid == null) return notFound();
+
+ // It's a JSONJamTable. I don't know why TS hates `number` => `string` conversion.
+ let editingContent = await db
+ .selectFrom('content')
+ .where('content.id', '=', contentid)
+ .selectAll()
+ .executeTakeFirst() as unknown as JSONContentTable;
+
+ if (editingContent == null) return notFound();
+
+ if (!existingUser.admin && editingContent.author_id != existingUser.id) return (
+
+ Can't delete this submission
+ You do not own this submission
+
+ );
+
+ return (
+
+ Deleting {editingContent.name}
+
+ Logged in as {existingUser?.username}@{existingUser?.instance}
+
+
+
+ )
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/delete/jam/[jamid]/components/form.tsx b/src/app/jams/(manip)/delete/jam/[jamid]/components/form.tsx
new file mode 100644
index 0000000..aac4aeb
--- /dev/null
+++ b/src/app/jams/(manip)/delete/jam/[jamid]/components/form.tsx
@@ -0,0 +1,31 @@
+'use client';
+import React from "react";
+import { useFormik } from "formik";
+import { useRouter } from "next/navigation";
+
+export function Form({jamID}:{jamID:string}) {
+ const router = useRouter();
+ const formik = useFormik({
+ initialValues: {},
+ onSubmit: async (values) => {
+ const submitRequest = await fetch(`/jams/api/jams/${jamID}`, {
+ method: "DELETE"
+ });
+
+ if (submitRequest.ok) {
+ router.push(`/jams/`);
+ } else {
+ formik.setSubmitting(false);
+ }
+ },
+ });
+
+ return (
+
+ );
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/delete/jam/[jamid]/page.tsx b/src/app/jams/(manip)/delete/jam/[jamid]/page.tsx
new file mode 100644
index 0000000..c270bb7
--- /dev/null
+++ b/src/app/jams/(manip)/delete/jam/[jamid]/page.tsx
@@ -0,0 +1,67 @@
+
+import { Conditional, ConditionalNull } from "@/components/utility/Conditional";
+import { MainLayout } from "@/layout/MainLayout/MainLayout";
+import { db } from "@/lib/mastoauth/kysely";
+import { JSONContentTable, JSONJamTable } from "@/lib/mastoauth/realtypes";
+import { cookies } from "next/headers";
+import { notFound, redirect } from "next/navigation";
+import { Form } from "./components/form";
+
+export default async function Home({
+ params
+}: {
+ params: {
+ jamid: string
+ }
+}) {
+ const cookieStore = cookies();
+ const token = cookieStore.get('token')?.value;
+ let existingUser;
+ if (token != null) {
+ let existingToken = await db
+ .selectFrom('tokens')
+ .where('tokens.id', '=', token)
+ .select('owner')
+ .executeTakeFirst();
+
+ if (existingToken != null) {
+ existingUser = await db
+ .selectFrom('users')
+ .where('users.id', '=', existingToken.owner)
+ .selectAll()
+ .executeTakeFirst();
+ }
+ }
+
+ if (existingUser == null) return redirect("/jams/");
+
+ const jamid = params.jamid;
+
+ if (jamid == null) return notFound();
+
+ // It's a JSONJamTable. I don't know why TS hates `number` => `string` conversion.
+ let editingJam = await db
+ .selectFrom('jams')
+ .where('jams.id', '=', jamid)
+ .selectAll()
+ .executeTakeFirst() as unknown as JSONJamTable;
+
+ if (editingJam == null) return notFound();
+
+ if (!existingUser.admin && editingJam.author_id != existingUser.id) return (
+
+ Can't delete this Jam
+ You do not own this Jam
+
+ );
+
+ return (
+
+ Deleting {editingJam.name}
+
+ Logged in as {existingUser?.username}@{existingUser?.instance}
+
+
+
+ )
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/delete/judgement/[judgementid]/components/form.tsx b/src/app/jams/(manip)/delete/judgement/[judgementid]/components/form.tsx
new file mode 100644
index 0000000..2d8a759
--- /dev/null
+++ b/src/app/jams/(manip)/delete/judgement/[judgementid]/components/form.tsx
@@ -0,0 +1,31 @@
+'use client';
+import React from "react";
+import { useFormik } from "formik";
+import { useRouter } from "next/navigation";
+
+export function Form({judgementID, contentID}:{judgementID:string, contentID:string}) {
+ const router = useRouter();
+ const formik = useFormik({
+ initialValues: {},
+ onSubmit: async (values) => {
+ const submitRequest = await fetch(`/jams/api/content/${contentID}/judgements/${judgementID}`, {
+ method: "DELETE"
+ });
+
+ if (submitRequest.ok) {
+ router.push(`/jams/`);
+ } else {
+ formik.setSubmitting(false);
+ }
+ },
+ });
+
+ return (
+
+ );
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/delete/judgement/[judgementid]/page.tsx b/src/app/jams/(manip)/delete/judgement/[judgementid]/page.tsx
new file mode 100644
index 0000000..530ff3e
--- /dev/null
+++ b/src/app/jams/(manip)/delete/judgement/[judgementid]/page.tsx
@@ -0,0 +1,67 @@
+
+import { Conditional, ConditionalNull } from "@/components/utility/Conditional";
+import { MainLayout } from "@/layout/MainLayout/MainLayout";
+import { db } from "@/lib/mastoauth/kysely";
+import { JSONContentTable, JSONJamTable, JSONJudgementTable } from "@/lib/mastoauth/realtypes";
+import { cookies } from "next/headers";
+import { notFound, redirect } from "next/navigation";
+import { Form } from "./components/form";
+
+export default async function Home({
+ params
+}: {
+ params: {
+ judgementid: string
+ }
+}) {
+ const cookieStore = cookies();
+ const token = cookieStore.get('token')?.value;
+ let existingUser;
+ if (token != null) {
+ let existingToken = await db
+ .selectFrom('tokens')
+ .where('tokens.id', '=', token)
+ .select('owner')
+ .executeTakeFirst();
+
+ if (existingToken != null) {
+ existingUser = await db
+ .selectFrom('users')
+ .where('users.id', '=', existingToken.owner)
+ .selectAll()
+ .executeTakeFirst();
+ }
+ }
+
+ if (existingUser == null) return redirect("/jams/");
+
+ const judgementid = params.judgementid;
+
+ if (judgementid == null) return notFound();
+
+ // It's a JSONJamTable. I don't know why TS hates `number` => `string` conversion.
+ let editingJudgement = await db
+ .selectFrom('judgements')
+ .where('judgements.id', '=', judgementid)
+ .selectAll()
+ .executeTakeFirst() as unknown as JSONJudgementTable;
+
+ if (editingJudgement == null) return notFound();
+
+ if (!existingUser.admin && editingJudgement.author_id != existingUser.id) return (
+
+ Can't delete this judgement
+ You did not publish this judgement
+
+ );
+
+ return (
+
+ Deleting "{editingJudgement.content} "
+
+ Logged in as {existingUser?.username}@{existingUser?.instance}
+
+
+
+ )
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/edit/content/[contentid]/components/form.tsx b/src/app/jams/(manip)/edit/content/[contentid]/components/form.tsx
new file mode 100644
index 0000000..6fb6f98
--- /dev/null
+++ b/src/app/jams/(manip)/edit/content/[contentid]/components/form.tsx
@@ -0,0 +1,87 @@
+'use client';
+import React from "react";
+import { ErrorMessage, useFormik } from "formik";
+import { useRouter } from "next/navigation";
+import { ConditionalNull } from "@/components/utility/Conditional";
+import { JSONContentTable } from "@/lib/mastoauth/realtypes";
+
+export function Form({contentID, preset}:{contentID:string, preset:Partial}) {
+ const router = useRouter();
+ const formik = useFormik({
+ initialValues: preset,
+ onSubmit: async (values) => {
+ const submitRequest = await fetch(`/jams/api/content/${contentID}`, {
+ method: "PATCH",
+ body: JSON.stringify(values)
+ });
+
+ if (submitRequest.ok) {
+ router.push(`/jams/content/${contentID}/`);
+ } else {
+ formik.setSubmitting(false);
+ if (submitRequest.status == 400) {
+ let errors:string[]|null = null;
+ try {
+ errors = await submitRequest.json();
+ } catch (err) { }; // No body. Skill issue
+ if (errors == null) return;
+ let transformedErrors:{[key:string]:string} = {};
+ errors.forEach((string) => transformedErrors[string] = "Something's wrong here");
+ formik.setErrors(transformedErrors);
+ } else {
+ formik.setErrors({
+ name: "Something went wrong..."
+ });
+ }
+ }
+ },
+ });
+
+ return (
+
+ );
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/edit/content/[contentid]/page.tsx b/src/app/jams/(manip)/edit/content/[contentid]/page.tsx
index e69de29..5a75795 100644
--- a/src/app/jams/(manip)/edit/content/[contentid]/page.tsx
+++ b/src/app/jams/(manip)/edit/content/[contentid]/page.tsx
@@ -0,0 +1,67 @@
+
+import { Conditional, ConditionalNull } from "@/components/utility/Conditional";
+import { MainLayout } from "@/layout/MainLayout/MainLayout";
+import { db } from "@/lib/mastoauth/kysely";
+import { JSONContentTable, JSONJamTable } from "@/lib/mastoauth/realtypes";
+import { cookies } from "next/headers";
+import { notFound, redirect } from "next/navigation";
+import { Form } from "./components/form";
+
+export default async function Home({
+ params
+}: {
+ params: {
+ contentid: string
+ }
+}) {
+ const cookieStore = cookies();
+ const token = cookieStore.get('token')?.value;
+ let existingUser;
+ if (token != null) {
+ let existingToken = await db
+ .selectFrom('tokens')
+ .where('tokens.id', '=', token)
+ .select('owner')
+ .executeTakeFirst();
+
+ if (existingToken != null) {
+ existingUser = await db
+ .selectFrom('users')
+ .where('users.id', '=', existingToken.owner)
+ .selectAll()
+ .executeTakeFirst();
+ }
+ }
+
+ if (existingUser == null) return redirect("/jams/");
+
+ const contentid = params.contentid;
+
+ if (contentid == null) return notFound();
+
+ // It's a JSONJamTable. I don't know why TS hates `number` => `string` conversion.
+ let editingContent = await db
+ .selectFrom('content')
+ .where('content.id', '=', contentid)
+ .select(['id','name','description','url'])
+ .executeTakeFirst() as unknown as JSONContentTable;
+
+ if (editingContent == null) return notFound();
+
+ if (!existingUser.admin && editingContent.author_id != existingUser.id) return (
+
+ Can't edit this submission
+ You do not own this submission
+
+ );
+
+ return (
+
+ Editing {editingContent.name}
+
+ Logged in as {existingUser?.username}@{existingUser?.instance}
+
+
+
+ )
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/edit/jam/[jamid]/components/form.tsx b/src/app/jams/(manip)/edit/jam/[jamid]/components/form.tsx
new file mode 100644
index 0000000..c4176ff
--- /dev/null
+++ b/src/app/jams/(manip)/edit/jam/[jamid]/components/form.tsx
@@ -0,0 +1,115 @@
+'use client';
+import React from "react";
+import { ErrorMessage, useFormik } from "formik";
+import { useRouter } from "next/navigation";
+import { ConditionalNull } from "@/components/utility/Conditional";
+import { JSONContentTable, JSONJamTable } from "@/lib/mastoauth/realtypes";
+
+export function Form({jamID, preset}:{jamID:string, preset:{
+ name: string,
+ description: string,
+ date_start: string,
+ date_end: string
+}}) {
+ const correctPreset = {
+ ...preset,
+ date_start: new Date(parseInt(preset.date_start)).toISOString().slice(0, -8),
+ date_end: new Date(parseInt(preset.date_end)).toISOString().slice(0, -8)
+ }
+ const router = useRouter();
+ const formik = useFormik({
+ initialValues: correctPreset,
+ onSubmit: async (values) => {
+ const correctValues = {
+ ...values,
+ date_start: new Date(values.date_start).getTime(),
+ date_end: new Date(values.date_end).getTime(),
+ }
+ const submitRequest = await fetch(`/jams/api/jams/${jamID}`, {
+ method: "PATCH",
+ body: JSON.stringify(correctValues)
+ });
+
+ if (submitRequest.ok) {
+ router.push(`/jams/jam/${jamID}/`);
+ } else {
+ formik.setSubmitting(false);
+ if (submitRequest.status == 400) {
+ let errors:string[]|null = null;
+ try {
+ errors = await submitRequest.json();
+ } catch (err) { }; // No body. Skill issue
+ if (errors == null) return;
+ let transformedErrors:{[key:string]:string} = {};
+ errors.forEach((string) => transformedErrors[string] = "Something's wrong here");
+ formik.setErrors(transformedErrors);
+ } else {
+ formik.setErrors({
+ name: "Something went wrong..."
+ });
+ }
+ }
+ },
+ });
+
+ return (
+
+
+
Name
+
+
+ Error: {formik.errors.name}
+
+
+
+
Description
+
+
+ Error: {formik.errors.description}
+
+
+
+
Date Start
+
+
+ Error: {formik.errors.date_start}
+
+
+
+
Date End
+
+
+ Error: {formik.errors.date_end}
+
+
+
+
+
+ );
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/edit/jam/[jamid]/page.tsx b/src/app/jams/(manip)/edit/jam/[jamid]/page.tsx
index e69de29..a7d5a8f 100644
--- a/src/app/jams/(manip)/edit/jam/[jamid]/page.tsx
+++ b/src/app/jams/(manip)/edit/jam/[jamid]/page.tsx
@@ -0,0 +1,67 @@
+
+import { Conditional, ConditionalNull } from "@/components/utility/Conditional";
+import { MainLayout } from "@/layout/MainLayout/MainLayout";
+import { db } from "@/lib/mastoauth/kysely";
+import { JSONContentTable, JSONJamTable } from "@/lib/mastoauth/realtypes";
+import { cookies } from "next/headers";
+import { notFound, redirect } from "next/navigation";
+import { Form } from "./components/form";
+
+export default async function Home({
+ params
+}: {
+ params: {
+ jamid: string
+ }
+}) {
+ const cookieStore = cookies();
+ const token = cookieStore.get('token')?.value;
+ let existingUser;
+ if (token != null) {
+ let existingToken = await db
+ .selectFrom('tokens')
+ .where('tokens.id', '=', token)
+ .select('owner')
+ .executeTakeFirst();
+
+ if (existingToken != null) {
+ existingUser = await db
+ .selectFrom('users')
+ .where('users.id', '=', existingToken.owner)
+ .selectAll()
+ .executeTakeFirst();
+ }
+ }
+
+ if (existingUser == null) return redirect("/jams/");
+
+ const jamid = params.jamid;
+
+ if (jamid == null) return notFound();
+
+ // It's a JSONJamTable. I don't know why TS hates `number` => `string` conversion.
+ let editingJam = await db
+ .selectFrom('jams')
+ .where('jams.id', '=', jamid)
+ .select(['id','name','description','date_start','date_end'])
+ .executeTakeFirst() as unknown as JSONJamTable;
+
+ if (editingJam == null) return notFound();
+
+ if (!existingUser.admin && editingJam.author_id != existingUser.id) return (
+
+ Can't edit this Jam
+ You do not own this Jam
+
+ );
+
+ return (
+
+ Editing {editingJam.name}
+
+ Logged in as {existingUser?.username}@{existingUser?.instance}
+
+
+
+ )
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/edit/judgement/[judgementid]/components/form.tsx b/src/app/jams/(manip)/edit/judgement/[judgementid]/components/form.tsx
new file mode 100644
index 0000000..1cc7b1c
--- /dev/null
+++ b/src/app/jams/(manip)/edit/judgement/[judgementid]/components/form.tsx
@@ -0,0 +1,62 @@
+'use client';
+import React from "react";
+import { ErrorMessage, useFormik } from "formik";
+import { useRouter } from "next/navigation";
+import { ConditionalNull } from "@/components/utility/Conditional";
+import { JSONContentTable, JSONJudgementTable } from "@/lib/mastoauth/realtypes";
+
+export function Form({judgementID, preset}:{judgementID:string, preset:JSONJudgementTable}) {
+ const router = useRouter();
+ const formik = useFormik({
+ initialValues: {
+ content: preset.content
+ },
+ onSubmit: async (values) => {
+ const submitRequest = await fetch(`/jams/api/content/${preset.content_id}/judgements/${judgementID}`, {
+ method: "PATCH",
+ body: JSON.stringify(values)
+ });
+
+ if (submitRequest.ok) {
+ router.push(`/jams/content/${preset.content_id}?since=${preset.published}`);
+ } else {
+ formik.setSubmitting(false);
+ if (submitRequest.status == 400) {
+ let errors:string[]|null = null;
+ try {
+ errors = await submitRequest.json();
+ } catch (err) { }; // No body. Skill issue
+ if (errors == null) return;
+ let transformedErrors:{[key:string]:string} = {};
+ errors.forEach((string) => transformedErrors[string] = "Something's wrong here");
+ formik.setErrors(transformedErrors);
+ } else {
+ formik.setErrors({
+ content: "Something went wrong..."
+ });
+ }
+ }
+ },
+ });
+
+ return (
+
+
+
Content
+
+
+ Error: {formik.errors.content}
+
+
+
+
+ );
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/edit/judgement/[judgementid]/page.tsx b/src/app/jams/(manip)/edit/judgement/[judgementid]/page.tsx
index e69de29..d416cc9 100644
--- a/src/app/jams/(manip)/edit/judgement/[judgementid]/page.tsx
+++ b/src/app/jams/(manip)/edit/judgement/[judgementid]/page.tsx
@@ -0,0 +1,67 @@
+
+import { Conditional, ConditionalNull } from "@/components/utility/Conditional";
+import { MainLayout } from "@/layout/MainLayout/MainLayout";
+import { db } from "@/lib/mastoauth/kysely";
+import { JSONContentTable, JSONJamTable, JSONJudgementTable } from "@/lib/mastoauth/realtypes";
+import { cookies } from "next/headers";
+import { notFound, redirect } from "next/navigation";
+import { Form } from "./components/form";
+
+export default async function Home({
+ params
+}: {
+ params: {
+ judgementid: string
+ }
+}) {
+ const cookieStore = cookies();
+ const token = cookieStore.get('token')?.value;
+ let existingUser;
+ if (token != null) {
+ let existingToken = await db
+ .selectFrom('tokens')
+ .where('tokens.id', '=', token)
+ .select('owner')
+ .executeTakeFirst();
+
+ if (existingToken != null) {
+ existingUser = await db
+ .selectFrom('users')
+ .where('users.id', '=', existingToken.owner)
+ .selectAll()
+ .executeTakeFirst();
+ }
+ }
+
+ if (existingUser == null) return redirect("/jams/");
+
+ const judgementid = params.judgementid;
+
+ if (judgementid == null) return notFound();
+
+ // It's a JSONJamTable. I don't know why TS hates `number` => `string` conversion.
+ let editingJudgement = await db
+ .selectFrom('judgements')
+ .where('judgements.id', '=', judgementid)
+ .select(['content_id', 'content', 'published'])
+ .executeTakeFirst() as unknown as JSONJudgementTable;
+
+ if (editingJudgement == null) return notFound();
+
+ if (!existingUser.admin && editingJudgement.author_id != existingUser.id) return (
+
+ Can't edit this judgement
+ You do not own this judgement
+
+ );
+
+ return (
+
+ Editing judgement "{editingJudgement.content} "
+
+ Logged in as {existingUser?.username}@{existingUser?.instance}
+
+
+
+ )
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/new/content/[jamid]/components/form.tsx b/src/app/jams/(manip)/new/content/[jamid]/components/form.tsx
index 0750f30..15c6ba6 100644
--- a/src/app/jams/(manip)/new/content/[jamid]/components/form.tsx
+++ b/src/app/jams/(manip)/new/content/[jamid]/components/form.tsx
@@ -1,36 +1,94 @@
'use client';
import React from "react";
-import { useFormik } from "formik";
+import { ErrorMessage, useFormik } from "formik";
+import { useRouter } from "next/navigation";
+import { ConditionalNull } from "@/components/utility/Conditional";
-export function Form() {
+export function Form({jamID}:{jamID:string}) {
+ const router = useRouter();
const formik = useFormik({
initialValues: {
- email: '',
+ name: '',
+ description: '',
+ url: '',
},
- onSubmit: values => {
- alert(JSON.stringify(values, null, 2));
+ onSubmit: async (values) => {
+ const submitRequest = await fetch(`/jams/api/jams/${jamID}/content`, {
+ method: "POST",
+ body: JSON.stringify(values)
+ });
+
+ if (submitRequest.ok) {
+ let id:string = await submitRequest.text();
+
+ if (id == null) return;
+
+ router.push(`/jams/content/${id}/`);
+ } else {
+ formik.setSubmitting(false);
+ if (submitRequest.status == 400) {
+ let errors:string[]|null = null;
+ try {
+ errors = await submitRequest.json();
+ } catch (err) { }; // No body. Skill issue
+ if (errors == null) return;
+ let transformedErrors:{[key:string]:string} = {};
+ errors.forEach((string) => transformedErrors[string] = "Something's wrong here");
+ formik.setErrors(transformedErrors);
+ } else {
+ formik.setErrors({
+ name: "Something went wrong..."
+ });
+ }
+ }
},
});
return (
- Email Address
-
-
-
- Submit
+
+
Name
+
+
+ Error: {formik.errors.name}
+
+
+
+
Description
+
+
+ Error: {formik.errors.description}
+
+
+
+
URL
+
+
+ Error: {formik.errors.url}
+
+
+
+
);
}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/new/content/[jamid]/page.tsx b/src/app/jams/(manip)/new/content/[jamid]/page.tsx
index 02ea9f7..56ada28 100644
--- a/src/app/jams/(manip)/new/content/[jamid]/page.tsx
+++ b/src/app/jams/(manip)/new/content/[jamid]/page.tsx
@@ -33,6 +33,8 @@ export default async function Home({
}
}
+ if (existingUser == null) return redirect("/jams/");
+
const jamid = params.jamid;
if (jamid == null) return notFound();
@@ -43,15 +45,15 @@ export default async function Home({
.where('jams.id', '=', jamid)
.selectAll()
.executeTakeFirst() as unknown as JSONJamTable;
+
+ if (parentJam == null) return notFound();
- // const started = Date.now() >= parseInt(parentJam.date_start);
- // const ended = Date.now() >= parseInt(parentJam.date_end);
- const started = true;
- const ended = false;
+ const started = Date.now() >= parseInt(parentJam.date_start);
+ const ended = Date.now() >= parseInt(parentJam.date_end);
if (!started || ended) return (
- Can't submit to this jam
+ Can't submit to this Jam
The jam starts at {new Date(parseInt(parentJam.date_start)).toLocaleString('en-us', {
timeZoneName: "long"
@@ -65,15 +67,13 @@ export default async function Home({
);
- if (existingUser == null) return redirect("/jams/");
-
return (
- Submit something to {parentJam.name}
+ Submit something to {parentJam.name}
Logged in as {existingUser?.username}@{existingUser?.instance}
-
+
)
}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/new/jam/components/form.tsx b/src/app/jams/(manip)/new/jam/components/form.tsx
new file mode 100644
index 0000000..8bfa9c2
--- /dev/null
+++ b/src/app/jams/(manip)/new/jam/components/form.tsx
@@ -0,0 +1,113 @@
+'use client';
+import React from "react";
+import { ErrorMessage, useFormik } from "formik";
+import { useRouter } from "next/navigation";
+import { ConditionalNull } from "@/components/utility/Conditional";
+
+export function Form() {
+ const router = useRouter();
+ const formik = useFormik({
+ initialValues: {
+ name: '',
+ description: '',
+ date_start: '',
+ date_end: '',
+ },
+ onSubmit: async (values) => {
+ const correctValues = {
+ ...values,
+ date_start: new Date(values.date_start).getTime(),
+ date_end: new Date(values.date_end).getTime(),
+ }
+ const submitRequest = await fetch(`/jams/api/jams`, {
+ method: "POST",
+ body: JSON.stringify(correctValues)
+ });
+
+ if (submitRequest.ok) {
+ let id:string = await submitRequest.text();
+
+ if (id == null) return;
+
+ router.push(`/jams/jam/${id}/`);
+ } else {
+ formik.setSubmitting(false);
+ if (submitRequest.status == 400) {
+ let errors:string[]|null = null;
+ try {
+ errors = await submitRequest.json();
+ } catch (err) { }; // No body. Skill issue
+ if (errors == null) return;
+ let transformedErrors:{[key:string]:string} = {};
+ errors.forEach((string) => transformedErrors[string] = "Something's wrong here");
+ formik.setErrors(transformedErrors);
+ } else {
+ formik.setErrors({
+ name: "Something went wrong..."
+ });
+ }
+ }
+ },
+ });
+
+ return (
+
+
+
Name
+
+
+ Error: {formik.errors.name}
+
+
+
+
Description
+
+
+ Error: {formik.errors.description}
+
+
+
+
Date Start
+
+
+ Error: {formik.errors.date_start}
+
+
+
+
Date End
+
+
+ Error: {formik.errors.date_end}
+
+
+
+
+
+ );
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/new/jam/page.tsx b/src/app/jams/(manip)/new/jam/page.tsx
index e69de29..2b96bc5 100644
--- a/src/app/jams/(manip)/new/jam/page.tsx
+++ b/src/app/jams/(manip)/new/jam/page.tsx
@@ -0,0 +1,48 @@
+
+import { Conditional, ConditionalNull } from "@/components/utility/Conditional";
+import { MainLayout } from "@/layout/MainLayout/MainLayout";
+import { db } from "@/lib/mastoauth/kysely";
+import { JSONJamTable } from "@/lib/mastoauth/realtypes";
+import { cookies } from "next/headers";
+import { notFound, redirect } from "next/navigation";
+import { Form } from "./components/form";
+
+export default async function Home() {
+ const cookieStore = cookies();
+ const token = cookieStore.get('token')?.value;
+ let existingUser;
+ if (token != null) {
+ let existingToken = await db
+ .selectFrom('tokens')
+ .where('tokens.id', '=', token)
+ .select('owner')
+ .executeTakeFirst();
+
+ if (existingToken != null) {
+ existingUser = await db
+ .selectFrom('users')
+ .where('users.id', '=', existingToken.owner)
+ .selectAll()
+ .executeTakeFirst();
+ }
+ }
+
+ if (existingUser == null) return redirect("/jams/");
+
+ if (!existingUser.admin) return (
+
+ Can't create a new Jam
+ Non-admins cannot create Jams.
+
+ );
+
+ return (
+
+ Create a new Jam.
+
+ Logged in as {existingUser?.username}@{existingUser?.instance}
+
+
+
+ )
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/new/judgement/[contentid]/components/form.tsx b/src/app/jams/(manip)/new/judgement/[contentid]/components/form.tsx
new file mode 100644
index 0000000..743cc6b
--- /dev/null
+++ b/src/app/jams/(manip)/new/judgement/[contentid]/components/form.tsx
@@ -0,0 +1,65 @@
+'use client';
+import React from "react";
+import { ErrorMessage, useFormik } from "formik";
+import { useRouter } from "next/navigation";
+import { ConditionalNull } from "@/components/utility/Conditional";
+
+export function Form({contentID}:{contentID:string}) {
+ const router = useRouter();
+ const formik = useFormik({
+ initialValues: {
+ content: '',
+ },
+ onSubmit: async (values) => {
+ const submitRequest = await fetch(`/jams/api/content/${contentID}/judgements`, {
+ method: "POST",
+ body: JSON.stringify(values)
+ });
+
+ if (submitRequest.ok) {
+ let id:string = await submitRequest.text();
+
+ if (id == null) return;
+
+ router.push(`/jams/content/${contentID}/`);
+ } else {
+ formik.setSubmitting(false);
+ if (submitRequest.status == 400) {
+ let errors:string[]|null = null;
+ try {
+ errors = await submitRequest.json();
+ } catch (err) { }; // No body. Skill issue
+ if (errors == null) return;
+ let transformedErrors:{[key:string]:string} = {};
+ errors.forEach((string) => transformedErrors[string] = "Something's wrong here");
+ formik.setErrors(transformedErrors);
+ } else {
+ formik.setErrors({
+ content: "Something went wrong..."
+ });
+ }
+ }
+ },
+ });
+
+ return (
+
+
+
Content
+
+
+ Error: {formik.errors.content}
+
+
+
+
+ );
+}
\ No newline at end of file
diff --git a/src/app/jams/(manip)/new/judgement/[contentid]/page.tsx b/src/app/jams/(manip)/new/judgement/[contentid]/page.tsx
index e69de29..aba8d96 100644
--- a/src/app/jams/(manip)/new/judgement/[contentid]/page.tsx
+++ b/src/app/jams/(manip)/new/judgement/[contentid]/page.tsx
@@ -0,0 +1,60 @@
+
+import { Conditional, ConditionalNull } from "@/components/utility/Conditional";
+import { MainLayout } from "@/layout/MainLayout/MainLayout";
+import { db } from "@/lib/mastoauth/kysely";
+import { JSONContentTable, JSONJamTable } from "@/lib/mastoauth/realtypes";
+import { cookies } from "next/headers";
+import { notFound, redirect } from "next/navigation";
+import { Form } from "./components/form";
+
+export default async function Home({
+ params
+}: {
+ params: {
+ contentid: string
+ }
+}) {
+ const cookieStore = cookies();
+ const token = cookieStore.get('token')?.value;
+ let existingUser;
+ if (token != null) {
+ let existingToken = await db
+ .selectFrom('tokens')
+ .where('tokens.id', '=', token)
+ .select('owner')
+ .executeTakeFirst();
+
+ if (existingToken != null) {
+ existingUser = await db
+ .selectFrom('users')
+ .where('users.id', '=', existingToken.owner)
+ .selectAll()
+ .executeTakeFirst();
+ }
+ }
+
+ if (existingUser == null) return redirect("/jams/");
+
+ const contentid = params.contentid;
+
+ if (contentid == null) return notFound();
+
+ // It's a JSONJamTable. I don't know why TS hates `number` => `string` conversion.
+ let parentContent = await db
+ .selectFrom('content')
+ .where('content.id', '=', contentid)
+ .selectAll()
+ .executeTakeFirst() as unknown as JSONContentTable;
+
+ if (parentContent == null) return notFound();
+
+ return (
+
+ Judge {parentContent.name}
+
+ Logged in as {existingUser?.username}@{existingUser?.instance}
+
+
+
+ )
+}
\ No newline at end of file
diff --git a/src/app/jams/api/content/[content]/judgements/[judgement]/route.ts b/src/app/jams/api/content/[content]/judgements/[judgement]/route.ts
index 6b9e383..ca9fdfa 100644
--- a/src/app/jams/api/content/[content]/judgements/[judgement]/route.ts
+++ b/src/app/jams/api/content/[content]/judgements/[judgement]/route.ts
@@ -78,20 +78,20 @@ export async function PATCH(request: NextRequest, {params}: {params: {content:st
status: 401
});
- const id = params.content;
+ const id = params.judgement;
if (id == null) return new Response('', {
status: 400
});
let updatingJudgement = await db
- .selectFrom('judgements')
- .where('judgements.content_id', '=', cid)
- .where('judgements.id', '=', id)
- .select(['author_id'])
- .executeTakeFirst();
+ .selectFrom('judgements')
+ .where('judgements.content_id', '=', cid)
+ .where('judgements.id', '=', id)
+ .select(['author_id'])
+ .executeTakeFirst();
- console.log(updatingJudgement, existingUser)
+ console.log(cid, id, updatingJudgement, existingUser)
if (updatingJudgement == null) return new Response('', {
status: 400
@@ -193,7 +193,7 @@ export async function DELETE(request: NextRequest, {params}: {params: {content:s
status: 401
});
- console.log(deletingJudgement, existingUser)
+ console.log(cid, id, deletingJudgement, existingUser)
if (deletingJudgement == null) return new Response('', {
status: 400
diff --git a/src/app/jams/api/content/[content]/route.ts b/src/app/jams/api/content/[content]/route.ts
index 103bf55..686a444 100644
--- a/src/app/jams/api/content/[content]/route.ts
+++ b/src/app/jams/api/content/[content]/route.ts
@@ -183,6 +183,14 @@ export async function DELETE(request: NextRequest, {params}: {params: {content:s
status: 401
});
+ try {
+ await db
+ .deleteFrom('judgements')
+ .where('judgements.content_id', '=', id)
+ .execute();
+ } catch (err) {
+ }
+
try {
await db
.deleteFrom('content')
diff --git a/src/app/jams/api/jams/[jam]/route.ts b/src/app/jams/api/jams/[jam]/route.ts
index ce8d9fc..cdb5931 100644
--- a/src/app/jams/api/jams/[jam]/route.ts
+++ b/src/app/jams/api/jams/[jam]/route.ts
@@ -156,6 +156,15 @@ export async function DELETE(request: NextRequest, {params}: {params: {jam:strin
status: 401
});
+ try {
+ await db
+ .updateTable('content')
+ .set('content.jam_id', '')
+ .where('content.jam_id', '=', id)
+ .execute();
+ } catch (err) {
+ }
+
try {
await db
.deleteFrom('jams')
diff --git a/src/app/jams/api/jams/route.ts b/src/app/jams/api/jams/route.ts
index 304de8e..f90fa09 100644
--- a/src/app/jams/api/jams/route.ts
+++ b/src/app/jams/api/jams/route.ts
@@ -77,19 +77,21 @@ export async function POST(request: NextRequest) {
let newBody:JamTable = body;
+ let curBody = {
+ id: nanoid(21),
+ author_id: existingUser.id,
+ name: newBody.name,
+ description: newBody.description,
+ date_start: newBody.date_start,
+ date_end: newBody.date_end,
+ created: Date.now()
+ };
+
let res;
try {
res = await db
.insertInto('jams')
- .values({
- id: nanoid(21),
- author_id: existingUser.id,
- name: newBody.name,
- description: newBody.description,
- date_start: newBody.date_start,
- date_end: newBody.date_end,
- created: Date.now()
- })
+ .values(curBody)
.executeTakeFirstOrThrow();
} catch (err) {
return new Response('', {
@@ -97,7 +99,7 @@ export async function POST(request: NextRequest) {
});
}
- return new Response(null, {
- status: 204
+ return new Response(curBody.id, {
+ status: 200
})
}
\ No newline at end of file
diff --git a/src/app/jams/content/[content]/page.tsx b/src/app/jams/content/[content]/page.tsx
index db77a57..86a6457 100644
--- a/src/app/jams/content/[content]/page.tsx
+++ b/src/app/jams/content/[content]/page.tsx
@@ -84,13 +84,18 @@ export default async function Home({
{content.name}
{content.url}
+
Submitted by {`${contentOwner.username}@${contentOwner.instance}`} to {submittedJam.name} - {new Date(parseInt(content.submitted)).toDateString()}
+
+
+ Submitted by {`${contentOwner.username}@${contentOwner.instance}`} {new Date(parseInt(content.submitted)).toDateString()}
+
{content.description}
@@ -110,7 +115,7 @@ export default async function Home({
Published {new Date(parseInt(judgement.published)).toDateString()}
@@ -119,7 +124,7 @@ export default async function Home({
})}
- Later
+ Later
{/*
*/}
Earlier
diff --git a/src/app/jams/jam/[jam]/page.tsx b/src/app/jams/jam/[jam]/page.tsx
index 983abc8..1d385b5 100644
--- a/src/app/jams/jam/[jam]/page.tsx
+++ b/src/app/jams/jam/[jam]/page.tsx
@@ -108,7 +108,7 @@ export default async function Home({
})}
- Later
+ Later
{/*
*/}
Earlier
diff --git a/src/app/jams/page.tsx b/src/app/jams/page.tsx
index b5300f5..8cdc4c2 100644
--- a/src/app/jams/page.tsx
+++ b/src/app/jams/page.tsx
@@ -85,7 +85,7 @@ export default async function Home({
})}
- Later
+ Later
{/*
*/}
Earlier
diff --git a/src/app/jams/user/[user]/page.tsx b/src/app/jams/user/[user]/page.tsx
index 04e745a..1d41c93 100644
--- a/src/app/jams/user/[user]/page.tsx
+++ b/src/app/jams/user/[user]/page.tsx
@@ -138,7 +138,7 @@ export default async function Home({
})}
{/*
- Later
+ Later
Earlier
*/}
diff --git a/src/lib/mastoauth/mastoauth.ts b/src/lib/mastoauth/mastoauth.ts
index 1209c88..b04a7c9 100644
--- a/src/lib/mastoauth/mastoauth.ts
+++ b/src/lib/mastoauth/mastoauth.ts
@@ -25,8 +25,8 @@ export class MastoAuth {
async newApplication() {
let formData = new FormData();
formData.append('client_name', 'abtmtr.link Jams');
- // formData.append('redirect_uris', 'https://abtmtr.link/jams/oauth/code');
- formData.append('redirect_uris', 'http://localhost:3000/jams/oauth/code');
+ formData.append('redirect_uris', 'https://abtmtr.link/jams/oauth/code');
+ // formData.append('redirect_uris', 'http://localhost:3000/jams/oauth/code');
formData.append('scopes', 'read');
formData.append('website', 'https://abtmtr.link/jams');
diff --git a/src/styles/style.css b/src/styles/style.css
index 093ef6f..cfe44d4 100644
--- a/src/styles/style.css
+++ b/src/styles/style.css
@@ -74,6 +74,16 @@ button {
transition: all 0.125s;
}
+input:not([type="submit"]),
+textarea {
+ width: 100%;
+ font-family: monospace;
+ text-align: left;
+}
+
+textarea {
+ resize: vertical;
+}
button:hover {
opacity: 0.75;
}