diff --git a/README.md b/README.md index 4f88691..1e7b8a0 100644 --- a/README.md +++ b/README.md @@ -570,6 +570,74 @@ export default async function Page(props: { } ``` +## Error handling +Error handling works in `TypeScript` the same way like in JS. +```tsx +try{ + await sql`DELETE FROM invoices WHERE id = ${id}`; +} catch (error){ + console.error(error); +} +``` + +> Redirects have to be outside of a try & catch block, becuase a redirect would cause to trigger a error each time it's executed. + +A error also can be thrown manually by using `throw`. +```tsx +throw new Error('Failed to delete invoice.'); +``` + +To show an error also to the user instead only on the server you can add a `error.tsx` file. This file needs to be a client component. + +Here is a simple example for a such error page: +```tsx +'use client'; + +import { useEffect } from 'react'; + +export default function Error({ + error, + reset, +}: { + error: Error & { digest?: string }; + reset: () => void; +}) { + useEffect(() => { + // Optionally log the error to an error reporting service + console.error(error); + }, [error]); + + return ( +
+

Something went wrong!

+ +
+ ); +} +``` + +It's also possible to create separate error pages for specific errors. An example would be a not found page. + +A redirect to a not found page can be implemented with `notFound` from `next/navigation`. + +```tsx +import { notFound } from 'next/navigation'; + +if(!invoice){ + notFound(); +} +``` + +Therefor the file `not-found.tsx` should be created with the UI you want to show, when something is not found. +Thoose specific error pages will be shown before the general error page. ## Ressources diff --git a/dashboard-app-course/app/dashboard/invoices/[id]/edit/not-found.tsx b/dashboard-app-course/app/dashboard/invoices/[id]/edit/not-found.tsx new file mode 100644 index 0000000..1373306 --- /dev/null +++ b/dashboard-app-course/app/dashboard/invoices/[id]/edit/not-found.tsx @@ -0,0 +1,18 @@ +import Link from 'next/link'; +import { FaceFrownIcon } from '@heroicons/react/24/outline'; + +export default function NotFound() { + return ( +
+ +

404 Not Found

+

Could not find the requested invoice.

+ + Go Back + +
+ ); +} \ No newline at end of file diff --git a/dashboard-app-course/app/dashboard/invoices/[id]/edit/page.tsx b/dashboard-app-course/app/dashboard/invoices/[id]/edit/page.tsx index fab5787..f6a97f6 100644 --- a/dashboard-app-course/app/dashboard/invoices/[id]/edit/page.tsx +++ b/dashboard-app-course/app/dashboard/invoices/[id]/edit/page.tsx @@ -1,6 +1,7 @@ import Form from '@/app/ui/invoices/edit-form'; import Breadcrumbs from '@/app/ui/invoices/breadcrumbs'; import { fetchCustomers, fetchInvoiceById } from '@/app/lib/data'; +import { notFound } from 'next/navigation'; export default async function Page(props: { params: Promise<{ @@ -14,6 +15,10 @@ export default async function Page(props: { fetchCustomers(), ]); + if(!invoice){ + notFound(); + } + return (
void; +}) { + useEffect(() => { + // Optionally log the error to an error reporting service + console.error(error); + }, [error]); + + return ( +
+

Something went wrong!

+ +
+ ); +} \ No newline at end of file diff --git a/dashboard-app-course/app/lib/actions.ts b/dashboard-app-course/app/lib/actions.ts index fd3435d..baa0f40 100644 --- a/dashboard-app-course/app/lib/actions.ts +++ b/dashboard-app-course/app/lib/actions.ts @@ -27,10 +27,14 @@ export async function createInvoice(formData: FormData){ const amountInCents = amount * 100; const date = new Date().toISOString().split('T')[0]; - await sql` - INSERT INTO invoices (customer_Id, amount, status, date) - VALUES (${customerId}, ${amountInCents}, ${status}, ${date}) - `; + try{ + await sql` + INSERT INTO invoices (customer_Id, amount, status, date) + VALUES (${customerId}, ${amountInCents}, ${status}, ${date}) + `; + } catch(error){ + console.error(error); + } revalidatePath('/dashboard/invoices'); redirect('/dashboard/invoices'); @@ -46,17 +50,27 @@ export async function updateInvoice(id: string, formData: FormData){ }); const amountInCents = amount * 100; - await sql` + + try{ + await sql` UPDATE invoices SET customer_id = ${customerId}, amount = ${amountInCents}, status = ${status} WHERE id = ${id} - `; + `; + } catch(error){ + console.error(error); + } revalidatePath('/dashboard/invoices'); redirect('/dashboard/invoices'); } -export async function deleteInvoice(id: string){ - await sql`DELETE FROM invoices WHERE id = ${id}`; +export async function deleteInvoice(id: string){ + try{ + await sql`DELETE FROM invoices WHERE id = ${id}`; + } catch (error){ + console.error(error); + } + revalidatePath('/dashboard/invoices'); } \ No newline at end of file