feat(11.1-01): DB migration, API routes, schema type updates for agent initials storage

- Add agentInitialsData text column to users table (drizzle/0009_luxuriant_catseye.sql)
- Add 'agent-initials' to SignatureFieldType union in schema.ts
- Update isClientVisibleField() to exclude both agent-signature and agent-initials
- Create GET/PUT /api/agent/initials route with auth guard and 50KB size limit
This commit is contained in:
Chandler Copeland
2026-03-21 14:58:39 -06:00
parent ae17e017d3
commit 33f499c61b
5 changed files with 521 additions and 2 deletions

View File

@@ -0,0 +1,36 @@
import { auth } from '@/lib/auth';
import { db } from '@/lib/db';
import { users } from '@/lib/db/schema';
import { eq } from 'drizzle-orm';
export async function GET() {
const session = await auth();
if (!session?.user?.id) return new Response('Unauthorized', { status: 401 });
const user = await db.query.users.findFirst({
where: eq(users.id, session.user.id),
columns: { agentInitialsData: true },
});
return Response.json({ agentInitialsData: user?.agentInitialsData ?? null });
}
export async function PUT(req: Request) {
const session = await auth();
if (!session?.user?.id) return new Response('Unauthorized', { status: 401 });
const { dataURL } = await req.json() as { dataURL: string };
if (!dataURL || !dataURL.startsWith('data:image/png;base64,')) {
return Response.json({ error: 'Invalid initials data' }, { status: 422 });
}
if (dataURL.length > 50_000) {
return Response.json({ error: 'Initials data too large' }, { status: 422 });
}
await db.update(users)
.set({ agentInitialsData: dataURL })
.where(eq(users.id, session.user.id));
return Response.json({ ok: true });
}

View File

@@ -7,7 +7,8 @@ export type SignatureFieldType =
| 'text'
| 'checkbox'
| 'date'
| 'agent-signature';
| 'agent-signature'
| 'agent-initials';
export interface SignatureFieldData {
id: string;
@@ -34,7 +35,8 @@ export function getFieldType(field: SignatureFieldData): SignatureFieldType {
* surface to the client as required unsigned fields.
*/
export function isClientVisibleField(field: SignatureFieldData): boolean {
return getFieldType(field) !== 'agent-signature';
const t = getFieldType(field);
return t !== 'agent-signature' && t !== 'agent-initials';
}
export const users = pgTable("users", {
@@ -43,6 +45,7 @@ export const users = pgTable("users", {
passwordHash: text("password_hash").notNull(),
createdAt: timestamp("created_at").defaultNow().notNull(),
agentSignatureData: text("agent_signature_data"),
agentInitialsData: text("agent_initials_data"),
});
export const documentStatusEnum = pgEnum("document_status", [