Trying this...
All checks were successful
Docker Deploy / build-and-push (push) Successful in 4m3s

This commit is contained in:
2026-01-16 17:24:50 -07:00
parent 15b903f1af
commit 5aa9388678
25 changed files with 4353 additions and 32 deletions

View File

@@ -0,0 +1,153 @@
---
import DashboardLayout from '../../../../layouts/DashboardLayout.astro';
import { Icon } from 'astro-icon/components';
import { db } from '../../../../db';
import { invoices, members } from '../../../../db/schema';
import { eq, and } from 'drizzle-orm';
const { id } = Astro.params;
const user = Astro.locals.user;
if (!user || !id) {
return Astro.redirect('/dashboard/invoices');
}
// Fetch invoice
const invoice = await db.select()
.from(invoices)
.where(eq(invoices.id, id))
.get();
if (!invoice) {
return Astro.redirect('/404');
}
// Verify membership
const membership = await db.select()
.from(members)
.where(and(
eq(members.userId, user.id),
eq(members.organizationId, invoice.organizationId)
))
.get();
if (!membership) {
return Astro.redirect('/dashboard');
}
// Format dates for input[type="date"]
const issueDateStr = invoice.issueDate.toISOString().split('T')[0];
const dueDateStr = invoice.dueDate.toISOString().split('T')[0];
---
<DashboardLayout title={`Edit ${invoice.number} - Chronus`}>
<div class="max-w-3xl mx-auto">
<div class="mb-6">
<a href={`/dashboard/invoices/${invoice.id}`} class="btn btn-ghost btn-sm gap-2 pl-0 hover:bg-transparent text-base-content/60">
<Icon name="heroicons:arrow-left" class="w-4 h-4" />
Back to Invoice
</a>
<h1 class="text-3xl font-bold mt-2">Edit Details</h1>
</div>
<form method="POST" action={`/api/invoices/${invoice.id}/update`} class="card bg-base-100 shadow-xl border border-base-200">
<div class="card-body gap-6">
<div class="grid grid-cols-1 md:grid-cols-2 gap-6">
<!-- Number -->
<div class="form-control">
<label class="label">
<span class="label-text font-semibold">Number</span>
</label>
<input
type="text"
name="number"
class="input input-bordered font-mono"
value={invoice.number}
required
/>
</div>
<!-- Currency -->
<div class="form-control">
<label class="label">
<span class="label-text font-semibold">Currency</span>
</label>
<select name="currency" class="select select-bordered w-full">
<option value="USD" selected={invoice.currency === 'USD'}>USD ($)</option>
<option value="EUR" selected={invoice.currency === 'EUR'}>EUR (€)</option>
<option value="GBP" selected={invoice.currency === 'GBP'}>GBP (£)</option>
<option value="CAD" selected={invoice.currency === 'CAD'}>CAD ($)</option>
<option value="AUD" selected={invoice.currency === 'AUD'}>AUD ($)</option>
</select>
</div>
<!-- Issue Date -->
<div class="form-control">
<label class="label">
<span class="label-text font-semibold">Issue Date</span>
</label>
<input
type="date"
name="issueDate"
class="input input-bordered"
value={issueDateStr}
required
/>
</div>
<!-- Due Date -->
<div class="form-control">
<label class="label">
<span class="label-text font-semibold">Due Date</span>
</label>
<input
type="date"
name="dueDate"
class="input input-bordered"
value={dueDateStr}
required
/>
</div>
<!-- Tax Rate -->
<div class="form-control">
<label class="label">
<span class="label-text font-semibold">Tax Rate (%)</span>
</label>
<input
type="number"
name="taxRate"
step="0.01"
min="0"
max="100"
class="input input-bordered"
value={invoice.taxRate}
/>
</div>
</div>
<!-- Notes -->
<div class="form-control">
<label class="label">
<span class="label-text font-semibold">Notes / Terms</span>
</label>
<textarea
name="notes"
class="textarea textarea-bordered h-32 font-mono text-sm"
placeholder="Payment terms, bank details, or thank you notes..."
>{invoice.notes}</textarea>
</div>
<div class="divider"></div>
<div class="card-actions justify-end">
<a href={`/dashboard/invoices/${invoice.id}`} class="btn btn-ghost">Cancel</a>
<button type="submit" class="btn btn-primary">
Save Changes
</button>
</div>
</div>
</form>
</div>
</DashboardLayout>