Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
pontusab committed Oct 15, 2024
1 parent 4c6583c commit 35e06b0
Show file tree
Hide file tree
Showing 21 changed files with 2,300 additions and 106 deletions.
17 changes: 17 additions & 0 deletions apps/dashboard/src/actions/invoice/schema.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,20 @@ import { z } from "zod";
export const deleteInvoiceSchema = z.object({
id: z.string(),
});

export const updateInvoiceSettingsSchema = z.object({
customerLabel: z.string().optional(),
fromLabel: z.string().optional(),
invoiceNoLabel: z.string().optional(),
issueDateLabel: z.string().optional(),
dueDateLabel: z.string().optional(),
descriptionLabel: z.string().optional(),
priceLabel: z.string().optional(),
quantityLabel: z.string().optional(),
totalLabel: z.string().optional(),
vatLabel: z.string().optional(),
taxLabel: z.string().optional(),
paymentDetailsLabel: z.string().optional(),
noteLabel: z.string().optional(),
logoUrl: z.string().optional(),
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
"use server";

import { authActionClient } from "@/actions/safe-action";
import { updateInvoiceSettingsSchema } from "./schema";

export const updateInvoiceSettingsAction = authActionClient
.metadata({
name: "update-invoice-settings",
})
.schema(updateInvoiceSettingsSchema)
.action(async ({ parsedInput: setting, ctx: { user, supabase } }) => {
const teamId = user.team_id;

const { data, error } = await supabase
.rpc("update_team_setting", {
team_id: teamId,
setting_key: "invoice",
setting_path: [setting],
new_value: setting,
create_missing: true,
})
.select("*")
.single();

console.log(data, error);

return data;
});
4 changes: 3 additions & 1 deletion apps/dashboard/src/components/editor/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,10 @@ import { TextButtons } from "./selectors/text-buttons";
type Props = {
initialContent?: JSONContent;
className?: string;
onChange?: (content: JSONContent) => void;
};

export function Editor({ initialContent, className }: Props) {
export function Editor({ initialContent, className, onChange }: Props) {
const [isFocused, setIsFocused] = useState(false);
const [openLink, setOpenLink] = useState(false);
const [content, setContent] = useState<JSONContent | undefined>(
Expand All @@ -41,6 +42,7 @@ export function Editor({ initialContent, className }: Props) {
onUpdate={({ editor }) => {
const json = editor.getJSON();
setContent(json);
onChange?.(json);
}}
onFocus={() => setIsFocused(true)}
onBlur={() => setIsFocused(false)}
Expand Down
11 changes: 1 addition & 10 deletions apps/dashboard/src/components/invoice/create-button.tsx
Original file line number Diff line number Diff line change
@@ -1,16 +1,7 @@
"use client";

import { Button } from "@midday/ui/button";
import { useFormContext } from "react-hook-form";
import type { InvoiceFormValues } from "./schema";

export function CreateButton() {
const { handleSubmit } = useFormContext<InvoiceFormValues>();

const onSubmit = handleSubmit((data) => {
// Handle form submission
console.log(data);
});

return <Button onClick={onSubmit}>Create</Button>;
return <Button>Create</Button>;
}
68 changes: 27 additions & 41 deletions apps/dashboard/src/components/invoice/customer-content.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,58 +2,44 @@

import { Editor } from "@/components/editor";
import type { JSONContent } from "novel";
import { Controller, useFormContext } from "react-hook-form";
import { LabelInput } from "./label-input";

const defaultContent: JSONContent = {
type: "paragraph",
content: [
{
type: "text",
text: "Acme inc",
},
{
type: "hardBreak",
},
{
type: "text",
text: "john.doe@acme.com",
},
{
type: "hardBreak",
},
{
type: "text",
text: "36182-4441",
},
{
type: "hardBreak",
},
{
type: "text",
text: "Street 56",
},
{
type: "hardBreak",
},
{
type: "text",
text: "243 21 California, USA",
},
{
type: "hardBreak",
},
{
type: "text",
text: "VAT ID: SE1246767676020",
},
{ type: "text", text: "Acme inc" },
{ type: "hardBreak" },
{ type: "text", text: "john.doe@acme.com" },
{ type: "hardBreak" },
{ type: "text", text: "36182-4441" },
{ type: "hardBreak" },
{ type: "text", text: "Street 56" },
{ type: "hardBreak" },
{ type: "text", text: "243 21 California, USA" },
{ type: "hardBreak" },
{ type: "text", text: "VAT ID: SE1246767676020" },
],
};

export function CustomerContent() {
const { control } = useFormContext();

return (
<div>
<LabelInput name="settings.customerContent" />
<Editor initialContent={defaultContent} className="h-[115px]" />
<LabelInput name="settings.customerLabel" />
<Controller
name="customerContent"
control={control}
defaultValue={defaultContent}
render={({ field }) => (
<Editor
initialContent={field.value}
onChange={field.onChange}
className="h-[115px]"
/>
)}
/>
</div>
);
}
2 changes: 1 addition & 1 deletion apps/dashboard/src/components/invoice/due-date.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ export function DueDate() {
return (
<div className="flex space-x-1 items-center">
<div className="flex items-center">
<LabelInput name="settings.dueDate" />
<LabelInput name="settings.dueDateLabel" />
<span className="text-[11px] text-[#878787] font-mono">:</span>
</div>
<Popover open={isOpen} onOpenChange={setIsOpen}>
Expand Down
45 changes: 28 additions & 17 deletions apps/dashboard/src/components/invoice/form.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import { zodResolver } from "@hookform/resolvers/zod";
import { Button } from "@midday/ui/button";
import { ScrollArea } from "@midday/ui/scroll-area";
import { FormProvider, useForm } from "react-hook-form";
import { CreateButton } from "./create-button";
Expand All @@ -13,41 +12,53 @@ import { PaymentDetails } from "./payment-details";
import { type InvoiceFormValues, invoiceSchema } from "./schema";
import { Summary } from "./summary";

export function Form() {
type Props = {
teamId: string;
};

export function Form({ teamId }: Props) {
const form = useForm<InvoiceFormValues>({
resolver: zodResolver(invoiceSchema),
defaultValues: {
settings: {
invoiceNo: "Invoice NO",
issueDate: "Issue Date",
dueDate: "Due Date",
customerContent: "To",
fromContent: "From",
description: "Description",
price: "Price",
quantity: "Quantity",
total: "Total",
vat: "VAT",
tax: "Tax",
paymentDetails: "Payment Details",
note: "Note",
customerLabel: "To",
fromLabel: "From",
invoiceNoLabel: "Invoice No",
issueDateLabel: "Issue Date",
dueDateLabel: "Due Date",
descriptionLabel: "Description",
priceLabel: "Price",
quantityLabel: "Quantity",
totalLabel: "Total",
vatLabel: "VAT",
taxLabel: "Tax",
paymentDetailsLabel: "Payment Details",
noteLabel: "Note",
logoUrl: undefined,
},
invoiceNumber: "INV-0001",
currency: "USD",
lineItems: [{ name: "", quantity: 0, price: 0 }],
},
});

const onSubmit = (data: InvoiceFormValues) => {
console.log(data);
};

return (
<FormProvider {...form}>
<form className="relative h-full antialiased">
<form
onSubmit={form.handleSubmit(onSubmit)}
className="relative h-full antialiased"
>
<ScrollArea
className="w-[544px] h-full max-h-[770px] bg-background"
hideScrollbar
>
<div className="p-8">
<div className="flex flex-col">
<Logo />
<Logo teamId={teamId} />
</div>

<div className="mt-8">
Expand Down
18 changes: 16 additions & 2 deletions apps/dashboard/src/components/invoice/from-content.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import { Editor } from "@/components/editor";
import type { JSONContent } from "novel";
import { Controller, useFormContext } from "react-hook-form";
import { LabelInput } from "./label-input";

const defaultContent: JSONContent = {
Expand Down Expand Up @@ -50,10 +51,23 @@ const defaultContent: JSONContent = {
};

export function FromContent() {
const { control } = useFormContext();

return (
<div>
<LabelInput name="settings.fromContent" />
<Editor initialContent={defaultContent} className="h-[115px]" />
<LabelInput name="settings.fromLabel" />
<Controller
name="fromContent"
control={control}
defaultValue={defaultContent}
render={({ field }) => (
<Editor
initialContent={field.value}
onChange={field.onChange}
className="h-[115px]"
/>
)}
/>
</div>
);
}
19 changes: 17 additions & 2 deletions apps/dashboard/src/components/invoice/invoice-no.tsx
Original file line number Diff line number Diff line change
@@ -1,14 +1,29 @@
import { updateInvoiceSettingsAction } from "@/actions/invoice/update-invoice-settings-action";
import { useAction } from "next-safe-action/hooks";
import { useFormContext } from "react-hook-form";
import { LabelInput } from "./label-input";

export function InvoiceNo() {
const { watch } = useFormContext();
const invoiceNumber = watch("invoiceNumber");

const updateInvoiceSettings = useAction(updateInvoiceSettingsAction);

return (
<div className="flex space-x-1 items-center">
<div className="flex items-center">
<LabelInput name="settings.invoiceNo" />
<LabelInput
name="settings.invoiceNoLabel"
onSave={(value) => {
updateInvoiceSettings.execute({
invoiceNoLabel: value,
});
}}
/>
<span className="text-[11px] text-[#878787] font-mono">:</span>
</div>
<span className="text-primary text-[11px] font-mono whitespace-nowrap">
INV-01
{invoiceNumber}
</span>
</div>
);
Expand Down
13 changes: 12 additions & 1 deletion apps/dashboard/src/components/invoice/issue-date.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
import { updateInvoiceSettingsAction } from "@/actions/invoice/update-invoice-settings-action";
import { Calendar } from "@midday/ui/calendar";
import { Popover, PopoverContent, PopoverTrigger } from "@midday/ui/popover";
import { format } from "date-fns";
import { useAction } from "next-safe-action/hooks";
import { useState } from "react";
import { useFormContext } from "react-hook-form";
import { LabelInput } from "./label-input";
Expand All @@ -18,10 +20,19 @@ export function IssueDate() {
}
};

const updateInvoiceSettings = useAction(updateInvoiceSettingsAction);

return (
<div className="flex space-x-1 items-center">
<div className="flex items-center">
<LabelInput name="settings.issueDate" />
<LabelInput
name="settings.issueDateLabel"
onSave={(value) => {
updateInvoiceSettings.execute({
invoiceNoLabel: value,
});
}}
/>
<span className="text-[11px] text-[#878787] font-mono">:</span>
</div>
<Popover open={isOpen} onOpenChange={setIsOpen}>
Expand Down
4 changes: 3 additions & 1 deletion apps/dashboard/src/components/invoice/label-input.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,10 @@ type Props = {
name: string;
required?: boolean;
className?: string;
onSave?: (value: string) => void;
};

export function LabelInput({ name, className }: Props) {
export function LabelInput({ name, className, onSave }: Props) {
const { setValue, watch } = useFormContext();
const value = watch(name);

Expand All @@ -22,6 +23,7 @@ export function LabelInput({ name, className }: Props) {
onBlur={(e) => {
const newValue = e.currentTarget.textContent || "";
setValue(name, newValue, { shouldValidate: true });
onSave?.(newValue);
}}
>
{value}
Expand Down
15 changes: 10 additions & 5 deletions apps/dashboard/src/components/invoice/line-items.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -42,13 +42,18 @@ export function LineItems() {
return (
<div className="space-y-4">
<div className="flex items-end mb-2">
<LabelInput name="settings.description" className="w-1/2 mr-4" />
<LabelInput name="settings.price" className="w-40 mr-4" />
<LabelInput name="settings.quantity" className="w-24 mr-4" />
<LabelInput name="settings.vat" className="w-24 text-right" />
<LabelInput name="settings.descriptionLabel" className="w-1/2 mr-4" />
<LabelInput name="settings.priceLabel" className="w-40 mr-4" />
<LabelInput name="settings.quantityLabel" className="w-24 mr-4" />
<LabelInput name="settings.vatLabel" className="w-24 text-right" />
</div>

<Reorder.Group axis="y" values={fields} onReorder={reorderList}>
<Reorder.Group
axis="y"
values={fields}
onReorder={reorderList}
className="!m-0"
>
{fields.map((field, index) => (
<LineItemRow
key={field.id}
Expand Down
Loading

0 comments on commit 35e06b0

Please sign in to comment.