From 66e3eb4a38f4a6f48d4dc77f6547acd6b17b9223 Mon Sep 17 00:00:00 2001 From: Oliver Bryan <04oliverbryan@gmail.com> Date: Mon, 12 Jan 2026 03:05:32 +0000 Subject: [PATCH] introduced sprint selection to the create issue dialog --- packages/backend/src/db/queries/issues.ts | 2 ++ packages/backend/src/routes/issue/create.ts | 4 ++- .../frontend/src/components/create-issue.tsx | 25 ++++++++++++++++--- .../frontend/src/lib/server/issue/create.ts | 3 +++ packages/frontend/src/pages/App.tsx | 1 + 5 files changed, 31 insertions(+), 4 deletions(-) diff --git a/packages/backend/src/db/queries/issues.ts b/packages/backend/src/db/queries/issues.ts index 7a6af55..591bb73 100644 --- a/packages/backend/src/db/queries/issues.ts +++ b/packages/backend/src/db/queries/issues.ts @@ -7,6 +7,7 @@ export async function createIssue( title: string, description: string, creatorId: number, + sprintId?: number, assigneeId?: number, status?: string, ) { @@ -30,6 +31,7 @@ export async function createIssue( description, number: nextNumber, creatorId, + sprintId, assigneeId, ...(status && { status }), }) diff --git a/packages/backend/src/routes/issue/create.ts b/packages/backend/src/routes/issue/create.ts index 5478fce..dadc370 100644 --- a/packages/backend/src/routes/issue/create.ts +++ b/packages/backend/src/routes/issue/create.ts @@ -23,11 +23,13 @@ export default async function issueCreate(req: AuthedRequest) { const title = url.searchParams.get("title") || "Untitled Issue"; const description = url.searchParams.get("description") || ""; + const sprintIdParam = url.searchParams.get("sprintId"); + const sprintId = sprintIdParam ? Number(sprintIdParam) : undefined; const assigneeIdParam = url.searchParams.get("assigneeId"); const assigneeId = assigneeIdParam ? Number(assigneeIdParam) : undefined; const status = url.searchParams.get("status") || undefined; - const issue = await createIssue(project.id, title, description, req.userId, assigneeId, status); + const issue = await createIssue(project.id, title, description, req.userId, sprintId, assigneeId, status); return Response.json(issue); } diff --git a/packages/frontend/src/components/create-issue.tsx b/packages/frontend/src/components/create-issue.tsx index 603c08e..76ddcd3 100644 --- a/packages/frontend/src/components/create-issue.tsx +++ b/packages/frontend/src/components/create-issue.tsx @@ -1,4 +1,10 @@ -import { ISSUE_DESCRIPTION_MAX_LENGTH, ISSUE_TITLE_MAX_LENGTH, type UserRecord } from "@issue/shared"; +import { + ISSUE_DESCRIPTION_MAX_LENGTH, + ISSUE_TITLE_MAX_LENGTH, + type SprintRecord, + type UserRecord, +} from "@issue/shared"; + import { type FormEvent, useState } from "react"; import { useAuthenticatedSession } from "@/components/session-provider"; import { StatusSelect } from "@/components/status-select"; @@ -18,15 +24,18 @@ import { SelectTrigger } from "@/components/ui/select"; import { UserSelect } from "@/components/user-select"; import { issue } from "@/lib/server"; import { cn } from "@/lib/utils"; +import { SprintSelect } from "./sprint-select"; export function CreateIssue({ projectId, + sprints, members, statuses, trigger, completeAction, }: { projectId?: number; + sprints?: SprintRecord[]; members?: UserRecord[]; statuses: Record; trigger?: React.ReactNode; @@ -37,6 +46,7 @@ export function CreateIssue({ const [open, setOpen] = useState(false); const [title, setTitle] = useState(""); const [description, setDescription] = useState(""); + const [sprintId, setSprintId] = useState("unassigned"); const [assigneeId, setAssigneeId] = useState("unassigned"); const [status, setStatus] = useState(Object.keys(statuses)[0] ?? ""); const [submitAttempted, setSubmitAttempted] = useState(false); @@ -46,6 +56,7 @@ export function CreateIssue({ const reset = () => { setTitle(""); setDescription(""); + setSprintId("unassigned"); setAssigneeId("unassigned"); setStatus(statuses?.[0] ?? ""); setSubmitAttempted(false); @@ -90,6 +101,7 @@ export function CreateIssue({ projectId, title, description, + sprintId: sprintId === "unassigned" ? null : Number(sprintId), assigneeId: assigneeId === "unassigned" ? null : Number(assigneeId), status: status.trim() === "" ? undefined : status, onSuccess: async (data) => { @@ -131,7 +143,7 @@ export function CreateIssue({
{statuses && Object.keys(statuses).length > 0 && ( -
+
+ {sprints && sprints.length > 0 && ( +
+ + +
+ )} + {members && members.length > 0 && ( -
+
diff --git a/packages/frontend/src/lib/server/issue/create.ts b/packages/frontend/src/lib/server/issue/create.ts index ede26c3..9c62ec3 100644 --- a/packages/frontend/src/lib/server/issue/create.ts +++ b/packages/frontend/src/lib/server/issue/create.ts @@ -5,6 +5,7 @@ export async function create({ projectId, title, description, + sprintId, assigneeId, status, onSuccess, @@ -13,6 +14,7 @@ export async function create({ projectId: number; title: string; description: string; + sprintId?: number | null; assigneeId?: number | null; status?: string; } & ServerQueryInput) { @@ -20,6 +22,7 @@ export async function create({ url.searchParams.set("projectId", `${projectId}`); url.searchParams.set("title", title.trim()); if (description.trim() !== "") url.searchParams.set("description", description.trim()); + if (sprintId != null) url.searchParams.set("sprintId", `${sprintId}`); if (assigneeId != null) url.searchParams.set("assigneeId", `${assigneeId}`); if (status != null && status.trim() !== "") url.searchParams.set("status", status.trim()); diff --git a/packages/frontend/src/pages/App.tsx b/packages/frontend/src/pages/App.tsx index c74c070..92de73e 100644 --- a/packages/frontend/src/pages/App.tsx +++ b/packages/frontend/src/pages/App.tsx @@ -419,6 +419,7 @@ export default function App() { <> {