From 1d76aa3b5718a28025748aaaa6239f286732afae Mon Sep 17 00:00:00 2001 From: itsmegood Date: Thu, 1 Feb 2024 13:41:25 +0530 Subject: [PATCH] update --- app/components/error-boundary.tsx | 2 +- app/components/forms.tsx | 39 +++++++++++----------- app/root.tsx | 31 +++++++++--------- app/utils/db.server.ts | 12 +++---- app/utils/misc.tsx | 2 +- package-lock.json | 54 ++++++++++++++++--------------- package.json | 10 +++--- 7 files changed, 77 insertions(+), 73 deletions(-) diff --git a/app/components/error-boundary.tsx b/app/components/error-boundary.tsx index 80c1406..715b8c8 100644 --- a/app/components/error-boundary.tsx +++ b/app/components/error-boundary.tsx @@ -39,7 +39,7 @@ export function GeneralErrorBoundary({ ? (statusHandlers?.[error.status] ?? defaultStatusHandler)({ error, params, - }) + }) : unexpectedErrorHandler(error)} ) diff --git a/app/components/forms.tsx b/app/components/forms.tsx index fc2f6af..131c33b 100644 --- a/app/components/forms.tsx +++ b/app/components/forms.tsx @@ -1,5 +1,5 @@ -import { useInputEvent } from '@conform-to/react' -import React, { useId, useRef } from 'react' +import { useInputControl } from '@conform-to/react' +import React, { useId } from 'react' import { Checkbox, type CheckboxProps } from './ui/checkbox.tsx' import { Input } from './ui/input.tsx' import { Label } from './ui/label.tsx' @@ -94,42 +94,45 @@ export function CheckboxField({ className, }: { labelProps: JSX.IntrinsicElements['label'] - buttonProps: CheckboxProps + buttonProps: CheckboxProps & { + name: string + form: string + value?: string + } errors?: ListOfErrors className?: string }) { + const { key, defaultChecked, ...checkboxProps } = buttonProps const fallbackId = useId() - const buttonRef = useRef(null) - // To emulate native events that Conform listen to: - // See https://conform.guide/integrations - const control = useInputEvent({ - // Retrieve the checkbox element by name instead as Radix does not expose the internal checkbox element - // See https://github.com/radix-ui/primitives/discussions/874 - ref: () => - buttonRef.current?.form?.elements.namedItem(buttonProps.name ?? ''), - onFocus: () => buttonRef.current?.focus(), + const checkedValue = buttonProps.value ?? 'on' + const input = useInputControl({ + key, + name: buttonProps.name, + formId: buttonProps.form, + initialValue: defaultChecked ? checkedValue : undefined, }) - const id = buttonProps.id ?? buttonProps.name ?? fallbackId + const id = buttonProps.id ?? fallbackId const errorId = errors?.length ? `${id}-error` : undefined + return (
{ - control.change(Boolean(state.valueOf())) + input.change(state.valueOf() ? checkedValue : '') buttonProps.onCheckedChange?.(state) }} onFocus={event => { - control.focus() + input.focus() buttonProps.onFocus?.(event) }} onBlur={event => { - control.blur() + input.blur() buttonProps.onBlur?.(event) }} type="button" diff --git a/app/root.tsx b/app/root.tsx index 5f77f6f..85dd15c 100644 --- a/app/root.tsx +++ b/app/root.tsx @@ -1,5 +1,5 @@ -import { useForm } from '@conform-to/react' -import { parse } from '@conform-to/zod' +import { getFormProps, useForm } from '@conform-to/react' +import { invariantResponse } from '@epic-web/invariant' import { cssBundleHref } from '@remix-run/css-bundle' import { json, @@ -25,7 +25,6 @@ import { withSentry } from '@sentry/remix' import { HoneypotProvider } from 'remix-utils/honeypot/react' import { z } from 'zod' import { GeneralErrorBoundary } from './components/error-boundary.tsx' -import { ErrorList } from './components/forms.tsx' import { EpicProgress } from './components/progress-bar.tsx' import { useToast } from './components/toaster.tsx' import { Icon, href as iconsHref } from './components/ui/icon.tsx' @@ -42,6 +41,7 @@ import { useRequestInfo } from './utils/request-info.ts' import { type Theme, setTheme, getTheme } from './utils/theme.server.ts' import { makeTimings, time } from './utils/timing.server.ts' import { getToast } from './utils/toast.server.ts' +import { parseWithZod } from '@conform-to/zod' export const links: LinksFunction = () => { return [ @@ -153,21 +153,18 @@ const ThemeFormSchema = z.object({ export async function action({ request }: ActionFunctionArgs) { const formData = await request.formData() - const submission = parse(formData, { + const submission = parseWithZod(formData, { schema: ThemeFormSchema, }) - if (submission.intent !== 'submit') { - return json({ status: 'idle', submission } as const) - } - if (!submission.value) { - return json({ status: 'error', submission } as const, { status: 400 }) - } + + invariantResponse(submission.status === 'success', 'Invalid theme received') + const { theme } = submission.value const responseInit = { headers: { 'set-cookie': setTheme(theme) }, } - return json({ success: true, submission }, responseInit) + return json({ result: submission.reply() }, responseInit) } function Document({ @@ -282,10 +279,13 @@ export function useOptimisticThemeMode() { const themeFetcher = fetchers.find(f => f.formAction === '/') if (themeFetcher && themeFetcher.formData) { - const submission = parse(themeFetcher.formData, { + const submission = parseWithZod(themeFetcher.formData, { schema: ThemeFormSchema, }) - return submission.value?.theme + + if (submission.status === 'success') { + return submission.value.theme + } } } @@ -294,7 +294,7 @@ function ThemeSwitch({ userPreference }: { userPreference?: Theme | null }) { const [form] = useForm({ id: 'theme-switch', - lastSubmission: fetcher.data?.submission, + lastResult: fetcher.data?.result, }) const optimisticMode = useOptimisticThemeMode() @@ -320,7 +320,7 @@ function ThemeSwitch({ userPreference }: { userPreference?: Theme | null }) { } return ( - +
-
) } diff --git a/app/utils/db.server.ts b/app/utils/db.server.ts index fdbad3c..9f48a96 100644 --- a/app/utils/db.server.ts +++ b/app/utils/db.server.ts @@ -22,12 +22,12 @@ export const prisma = remember('prisma', () => { e.duration < logThreshold * 1.1 ? 'green' : e.duration < logThreshold * 1.2 - ? 'blue' - : e.duration < logThreshold * 1.3 - ? 'yellow' - : e.duration < logThreshold * 1.4 - ? 'redBright' - : 'red' + ? 'blue' + : e.duration < logThreshold * 1.3 + ? 'yellow' + : e.duration < logThreshold * 1.4 + ? 'redBright' + : 'red' const dur = chalk[color](`${e.duration}ms`) console.info(`prisma:query - ${dur} - ${e.query}`) }) diff --git a/app/utils/misc.tsx b/app/utils/misc.tsx index f6190db..57832f6 100644 --- a/app/utils/misc.tsx +++ b/app/utils/misc.tsx @@ -216,7 +216,7 @@ export function useDoubleCheck() { : e => { e.preventDefault() setDoubleCheck(true) - } + } const onKeyUp: React.ButtonHTMLAttributes['onKeyUp'] = e => { diff --git a/package-lock.json b/package-lock.json index c34b319..81aade4 100644 --- a/package-lock.json +++ b/package-lock.json @@ -6,8 +6,8 @@ "": { "name": "bookbreeze-5848", "dependencies": { - "@conform-to/react": "^0.9.1", - "@conform-to/zod": "^0.9.1", + "@conform-to/react": "^1.0.0", + "@conform-to/zod": "^1.0.0", "@epic-web/cachified": "^4.0.0", "@epic-web/client-hints": "^1.2.2", "@epic-web/invariant": "^1.0.0", @@ -82,7 +82,7 @@ "@remix-run/serve": "^2.5.1", "@remix-run/testing": "^2.5.1", "@sly-cli/sly": "^1.8.0", - "@testing-library/jest-dom": "^6.4.0", + "@testing-library/jest-dom": "^6.4.1", "@testing-library/react": "^14.2.0", "@testing-library/user-event": "^14.5.2", "@total-typescript/ts-reset": "^0.5.1", @@ -95,9 +95,9 @@ "@types/fs-extra": "^11.0.4", "@types/glob": "^8.1.0", "@types/morgan": "^1.9.9", - "@types/node": "^20.11.13", + "@types/node": "^20.11.14", "@types/qrcode": "^1.5.5", - "@types/react": "^18.2.48", + "@types/react": "^18.2.50", "@types/react-dom": "^18.2.18", "@types/set-cookie-parser": "^2.4.7", "@types/source-map-support": "^0.5.10", @@ -980,27 +980,29 @@ } }, "node_modules/@conform-to/dom": { - "version": "0.9.1", - "resolved": "https://registry.npmjs.org/@conform-to/dom/-/dom-0.9.1.tgz", - "integrity": "sha512-+T6QgpLDPZ29j4y5nWW61WMe8qj0cQBymyzbi5sq1f3CcBO3wBbR0VPI7mbm+rLoErHWM3ghhdNlIkw0UPoLLA==" + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@conform-to/dom/-/dom-1.0.0.tgz", + "integrity": "sha512-KG0Ee2G9BcFLdqtpcexdht48QNM2F9ddAyJFSHNG4V3e2QOmVEAM7M6R/iWWykpTVQljWmKd2J7U4ep/7/XRrA==" }, "node_modules/@conform-to/react": { - "version": "0.9.1", - "resolved": "https://registry.npmjs.org/@conform-to/react/-/react-0.9.1.tgz", - "integrity": "sha512-SibYHk86IFh60LRPk4aJHJOgyLTgb3JYphKvG4vcemyuntdOwncd5YM/GDoccVzeCTmJi4Os/fDtOOAaDcSa9w==", + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@conform-to/react/-/react-1.0.0.tgz", + "integrity": "sha512-TlMMmNDhYJhKJP9EOyV2RbUEqjwR68GTO1KaO3LOI4WeVLx7aZ78k73qIuFMRjjZgsWOL4edD1CZtkKBRztmqw==", "dependencies": { - "@conform-to/dom": "0.9.1" + "@conform-to/dom": "1.0.0" }, "peerDependencies": { - "react": ">=16.8" + "react": ">=18" } }, "node_modules/@conform-to/zod": { - "version": "0.9.1", - "resolved": "https://registry.npmjs.org/@conform-to/zod/-/zod-0.9.1.tgz", - "integrity": "sha512-4hWBGzRpSd4RrlBFRXjS6QQ2MWFpMZDbDwz8H/xiq38Xl5yaL1RSZMhOJ4pmsmy8CIKghs78qvaD8ltTFlrNvQ==", + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@conform-to/zod/-/zod-1.0.0.tgz", + "integrity": "sha512-oWOfqEpCRZpOY7mxJe73oluy6Fvjbw8tYhXfDqZqFb0ePf+bFkF7g1Wzfkgz76LvWJHb0PNykn+o5f423aqb+w==", + "dependencies": { + "@conform-to/dom": "1.0.0" + }, "peerDependencies": { - "@conform-to/dom": "0.9.1", "zod": "^3.21.0" } }, @@ -5215,9 +5217,9 @@ "dev": true }, "node_modules/@testing-library/jest-dom": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/@testing-library/jest-dom/-/jest-dom-6.4.0.tgz", - "integrity": "sha512-GgGT3OR8qhIjk2SBMy51AYDWoMnAyR/cwjZO4SttuBmIQ9wWy9QmVOeaSbgT5Bm0J6qLBaf4+dsJWfisvafoaA==", + "version": "6.4.1", + "resolved": "https://registry.npmjs.org/@testing-library/jest-dom/-/jest-dom-6.4.1.tgz", + "integrity": "sha512-Z7qMM3J2Zw5H/nC2/5CYx5YcuaD56JmDFKNIozZ89VIo6o6Y9FMhssics4e2madEKYDNEpZz3+glPGz0yWMOag==", "dev": true, "dependencies": { "@adobe/css-tools": "^4.3.2", @@ -5608,9 +5610,9 @@ "dev": true }, "node_modules/@types/node": { - "version": "20.11.13", - "resolved": "https://registry.npmjs.org/@types/node/-/node-20.11.13.tgz", - "integrity": "sha512-5G4zQwdiQBSWYTDAH1ctw2eidqdhMJaNsiIDKHFr55ihz5Trl2qqR8fdrT732yPBho5gkNxXm67OxWFBqX9aPg==", + "version": "20.11.14", + "resolved": "https://registry.npmjs.org/@types/node/-/node-20.11.14.tgz", + "integrity": "sha512-w3yWCcwULefjP9DmDDsgUskrMoOy5Z8MiwKHr1FvqGPtx7CvJzQvxD7eKpxNtklQxLruxSXWddyeRtyud0RcXQ==", "dev": true, "dependencies": { "undici-types": "~5.26.4" @@ -5644,9 +5646,9 @@ "dev": true }, "node_modules/@types/react": { - "version": "18.2.48", - "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.48.tgz", - "integrity": "sha512-qboRCl6Ie70DQQG9hhNREz81jqC1cs9EVNcjQ1AU+jH6NFfSAhVVbrrY/+nSF+Bsk4AOwm9Qa61InvMCyV+H3w==", + "version": "18.2.50", + "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.50.tgz", + "integrity": "sha512-y0XIDJkqp9HynS1VBktZG9mUziHTK5WZTAFDP/UfzSq+poV1drUKsr4VkjMyHTbqMz26BwgLZVYdx/EgPm7EkQ==", "dev": true, "dependencies": { "@types/prop-types": "*", diff --git a/package.json b/package.json index 09e0fdc..186588c 100644 --- a/package.json +++ b/package.json @@ -38,8 +38,8 @@ "/server-build" ], "dependencies": { - "@conform-to/react": "^0.9.1", - "@conform-to/zod": "^0.9.1", + "@conform-to/react": "^1.0.0", + "@conform-to/zod": "^1.0.0", "@epic-web/cachified": "^4.0.0", "@epic-web/client-hints": "^1.2.2", "@epic-web/invariant": "^1.0.0", @@ -114,7 +114,7 @@ "@remix-run/serve": "^2.5.1", "@remix-run/testing": "^2.5.1", "@sly-cli/sly": "^1.8.0", - "@testing-library/jest-dom": "^6.4.0", + "@testing-library/jest-dom": "^6.4.1", "@testing-library/react": "^14.2.0", "@testing-library/user-event": "^14.5.2", "@total-typescript/ts-reset": "^0.5.1", @@ -127,9 +127,9 @@ "@types/fs-extra": "^11.0.4", "@types/glob": "^8.1.0", "@types/morgan": "^1.9.9", - "@types/node": "^20.11.13", + "@types/node": "^20.11.14", "@types/qrcode": "^1.5.5", - "@types/react": "^18.2.48", + "@types/react": "^18.2.50", "@types/react-dom": "^18.2.18", "@types/set-cookie-parser": "^2.4.7", "@types/source-map-support": "^0.5.10",