From 4ac43048629b9bb2a393ff7d47253770c8371d07 Mon Sep 17 00:00:00 2001 From: Lars Hampe Date: Thu, 10 Oct 2024 22:07:42 +0200 Subject: [PATCH] feat(app): extend version create/update with status and releasedAt date --- apps/app/src/hooks/useChangelog.ts | 40 +++ .../src/routes/changelog.$id.index.lazy.tsx | 14 +- .../changelog.$id.version.$versionId.tsx | 228 +++++++++++++++++- .../changelog.$id.versionCreate.lazy.tsx | 112 ++++++++- 4 files changed, 373 insertions(+), 21 deletions(-) diff --git a/apps/app/src/hooks/useChangelog.ts b/apps/app/src/hooks/useChangelog.ts index 1e0b681..5b5379f 100644 --- a/apps/app/src/hooks/useChangelog.ts +++ b/apps/app/src/hooks/useChangelog.ts @@ -131,3 +131,43 @@ export const useChangelogVersionCreate = () => { }, }) } + +export const useChangelogVersionById = ({ id }: { id: string }) => { + const { getToken } = useAuth() + + return useQuery({ + queryKey: ['changelogVersionById', id], + queryFn: async (): Promise> => + await queryFetch({ + path: `changelog/version/${id}`, + method: 'get', + token: await getToken(), + }), + }) +} + +export const useChangelogVersionUpdate = () => { + const { getToken } = useAuth() + const queryClient = useQueryClient() + + return useMutation({ + mutationFn: async ({ + id, + payload, + }: { + id: string + payload: VersionUpdate + }): Promise> => + await queryFetch({ + path: `changelog/version/${id}`, + data: payload, + method: 'put', + token: await getToken(), + }), + onSuccess: (data) => { + queryClient.invalidateQueries({ + queryKey: ['changelogById', data.id], + }) + }, + }) +} diff --git a/apps/app/src/routes/changelog.$id.index.lazy.tsx b/apps/app/src/routes/changelog.$id.index.lazy.tsx index 2f83ded..065749c 100644 --- a/apps/app/src/routes/changelog.$id.index.lazy.tsx +++ b/apps/app/src/routes/changelog.$id.index.lazy.tsx @@ -7,21 +7,9 @@ import { } from '@boring.tools/ui' import { Link, createLazyFileRoute } from '@tanstack/react-router' import { PlusCircleIcon } from 'lucide-react' +import { VersionStatus } from '../components/Changelog/VersionStatus' import { useChangelogById } from '../hooks/useChangelog' -const VersionStatus = ({ status }: { status: string }) => { - switch (status) { - case 'draft': - return
- case 'published': - return
- case 'review': - return
- default: - return
- } -} - const Component = () => { const { id } = Route.useParams() const { data, isPending } = useChangelogById({ id }) diff --git a/apps/app/src/routes/changelog.$id.version.$versionId.tsx b/apps/app/src/routes/changelog.$id.version.$versionId.tsx index c80eb84..f700570 100644 --- a/apps/app/src/routes/changelog.$id.version.$versionId.tsx +++ b/apps/app/src/routes/changelog.$id.version.$versionId.tsx @@ -1,10 +1,80 @@ -import { Button } from '@boring.tools/ui' -import { createFileRoute } from '@tanstack/react-router' -import { useChangelogById } from '../hooks/useChangelog' +import { VersionUpdateInput } from '@boring.tools/schema' +import { + Button, + Calendar, + Form, + FormControl, + FormField, + FormItem, + FormLabel, + FormMessage, + Popover, + PopoverContent, + PopoverTrigger, + Select, + SelectContent, + SelectItem, + SelectTrigger, + SelectValue, + cn, +} from '@boring.tools/ui' +import { zodResolver } from '@hookform/resolvers/zod' +import { + BlockTypeSelect, + BoldItalicUnderlineToggles, + ListsToggle, + MDXEditor, + type MDXEditorMethods, + UndoRedo, + headingsPlugin, + listsPlugin, + quotePlugin, + thematicBreakPlugin, + toolbarPlugin, +} from '@mdxeditor/editor' +import { createFileRoute, useNavigate } from '@tanstack/react-router' +import { useForm } from 'react-hook-form' +import type { z } from 'zod' +import { + useChangelogVersionById, + useChangelogVersionUpdate, +} from '../hooks/useChangelog' +import '@mdxeditor/editor/style.css' +import { format } from 'date-fns' +import { CalendarIcon } from 'lucide-react' +import { useEffect, useRef } from 'react' +import { VersionStatus } from '../components/Changelog/VersionStatus' const Component = () => { - const { id } = Route.useParams() - const { data, error, isPending, refetch } = useChangelogById({ id }) + const { id, versionId } = Route.useParams() + const mdxEditorRef = useRef(null) + const navigate = useNavigate({ from: `/changelog/${id}/versionCreate` }) + const versionUpdate = useChangelogVersionUpdate() + const { data, error, isPending, refetch } = useChangelogVersionById({ + id: versionId, + }) + const form = useForm>({ + resolver: zodResolver(VersionUpdateInput), + defaultValues: data, + }) + + const onSubmit = (values: z.infer) => { + versionUpdate.mutate( + { id: versionId, payload: values }, + { + onSuccess() { + navigate({ to: '/changelog/$id', params: { id } }) + }, + }, + ) + } + + useEffect(() => { + if (data) { + mdxEditorRef.current?.setMarkdown(data.markdown) + form.reset(data) + } + }, [data, form.reset]) if (error) { return ( @@ -19,7 +89,153 @@ const Component = () => { return (
- {!isPending && data &&
version page
} +
+ {!isPending && data && ( +
+

Version: {data.version}

+
+ + ( + + Notes + + ( + <> + + + + + + ), + }), + ]} + /> + {' '} + + + )} + /> + +
+ ( + + Status + + + + )} + /> + + ( + + Released at + + + + + + + + field.onChange(date)} + weekStartsOn={1} + /> + + + + + )} + /> +
+ +
+ + +
+ + +
+ )}
) } diff --git a/apps/app/src/routes/changelog.$id.versionCreate.lazy.tsx b/apps/app/src/routes/changelog.$id.versionCreate.lazy.tsx index a572c99..bceec4d 100644 --- a/apps/app/src/routes/changelog.$id.versionCreate.lazy.tsx +++ b/apps/app/src/routes/changelog.$id.versionCreate.lazy.tsx @@ -1,6 +1,7 @@ import { VersionCreateInput } from '@boring.tools/schema' import { Button, + Calendar, Form, FormControl, FormField, @@ -8,6 +9,15 @@ import { FormLabel, FormMessage, Input, + Popover, + PopoverContent, + PopoverTrigger, + Select, + SelectContent, + SelectItem, + SelectTrigger, + SelectValue, + cn, } from '@boring.tools/ui' import { zodResolver } from '@hookform/resolvers/zod' import { @@ -28,6 +38,9 @@ import { useForm } from 'react-hook-form' import type { z } from 'zod' import { useChangelogVersionCreate } from '../hooks/useChangelog' import '@mdxeditor/editor/style.css' +import { format } from 'date-fns' +import { CalendarIcon } from 'lucide-react' +import { VersionStatus } from '../components/Changelog/VersionStatus' const Component = () => { const { id } = Route.useParams() @@ -39,6 +52,7 @@ const Component = () => { changelogId: id, version: '', markdown: '', + status: 'draft', }, }) @@ -52,7 +66,8 @@ const Component = () => { return (
-

New version

+
+

New version

{ )} /> - +
+ ( + + Status + + + + )} + /> + + ( + + Released at + + + + + + + + field.onChange(date)} + weekStartsOn={1} + /> + + + + + )} + /> +
+ +
+ + +