feat: document templates with auto-fill (P1)

This commit is contained in:
m
2026-03-30 11:29:23 +02:00
17 changed files with 1568 additions and 89 deletions

View File

@@ -31,9 +31,15 @@ func New(db *sqlx.DB, authMW *auth.Middleware, cfg *config.Config, calDAVSvc *se
storageCli := services.NewStorageClient(cfg.SupabaseURL, cfg.SupabaseServiceKey)
documentSvc := services.NewDocumentService(db, storageCli, auditSvc)
assignmentSvc := services.NewCaseAssignmentService(db)
<<<<<<< HEAD
timeEntrySvc := services.NewTimeEntryService(db, auditSvc)
billingRateSvc := services.NewBillingRateService(db, auditSvc)
invoiceSvc := services.NewInvoiceService(db, auditSvc)
||||||| 8e65463
>>>>>>> mai/pike/p0-role-based
=======
templateSvc := services.NewTemplateService(db, auditSvc)
>>>>>>> mai/ritchie/p1-document-templates
// AI service (optional — only if API key is configured)
var aiH *handlers.AIHandler
@@ -68,9 +74,14 @@ func New(db *sqlx.DB, authMW *auth.Middleware, cfg *config.Config, calDAVSvc *se
eventH := handlers.NewCaseEventHandler(db)
docH := handlers.NewDocumentHandler(documentSvc)
assignmentH := handlers.NewCaseAssignmentHandler(assignmentSvc)
<<<<<<< HEAD
timeEntryH := handlers.NewTimeEntryHandler(timeEntrySvc)
billingRateH := handlers.NewBillingRateHandler(billingRateSvc)
invoiceH := handlers.NewInvoiceHandler(invoiceSvc)
||||||| 8e65463
=======
templateH := handlers.NewTemplateHandler(templateSvc, caseSvc, partySvc, deadlineSvc, tenantSvc)
>>>>>>> mai/ritchie/p1-document-templates
// Public routes
mux.HandleFunc("GET /health", handleHealth(db))
@@ -138,7 +149,7 @@ func New(db *sqlx.DB, authMW *auth.Middleware, cfg *config.Config, calDAVSvc *se
// Deadline calculator — all can use
scoped.HandleFunc("POST /api/deadlines/calculate", calcH.Calculate)
// Appointments — all can manage (PermManageAppointments granted to all)
// Appointments — all can manage
scoped.HandleFunc("GET /api/appointments/{id}", apptH.Get)
scoped.HandleFunc("GET /api/appointments", apptH.List)
scoped.HandleFunc("POST /api/appointments", perm(auth.PermManageAppointments, apptH.Create))
@@ -162,15 +173,49 @@ func New(db *sqlx.DB, authMW *auth.Middleware, cfg *config.Config, calDAVSvc *se
// Dashboard — all can view
scoped.HandleFunc("GET /api/dashboard", dashboardH.Get)
<<<<<<< HEAD
// Audit log — view requires PermViewAuditLog
scoped.HandleFunc("GET /api/audit-log", perm(auth.PermViewAuditLog, auditH.List))
||||||| 8e65463
<<<<<<< HEAD
// Audit log
scoped.HandleFunc("GET /api/audit-log", auditH.List)
=======
// Audit log
scoped.HandleFunc("GET /api/audit-log", auditH.List)
>>>>>>> mai/ritchie/p1-document-templates
<<<<<<< HEAD
// Documents — all can upload, delete checked in handler (own vs all)
||||||| 8e65463
// Documents
||||||| 82878df
// Documents
=======
// Documents — all can upload, delete checked in handler (own vs all)
>>>>>>> mai/pike/p0-role-based
=======
// Documents — all can upload, delete checked in handler
>>>>>>> mai/ritchie/p1-document-templates
scoped.HandleFunc("GET /api/cases/{id}/documents", docH.ListByCase)
scoped.HandleFunc("POST /api/cases/{id}/documents", perm(auth.PermUploadDocuments, docH.Upload))
scoped.HandleFunc("GET /api/documents/{docId}", docH.Download)
scoped.HandleFunc("GET /api/documents/{docId}/meta", docH.GetMeta)
<<<<<<< HEAD
scoped.HandleFunc("DELETE /api/documents/{docId}", docH.Delete)
||||||| 8e65463
scoped.HandleFunc("DELETE /api/documents/{docId}", docH.Delete) // permission check inside handler
=======
scoped.HandleFunc("DELETE /api/documents/{docId}", docH.Delete)
// Document templates — all can view, create/edit needs PermCreateCase
scoped.HandleFunc("GET /api/templates", templateH.List)
scoped.HandleFunc("GET /api/templates/{id}", templateH.Get)
scoped.HandleFunc("POST /api/templates", perm(auth.PermCreateCase, templateH.Create))
scoped.HandleFunc("PUT /api/templates/{id}", perm(auth.PermCreateCase, templateH.Update))
scoped.HandleFunc("DELETE /api/templates/{id}", perm(auth.PermCreateCase, templateH.Delete))
scoped.HandleFunc("POST /api/templates/{id}/render", templateH.Render)
>>>>>>> mai/ritchie/p1-document-templates
// AI endpoints (rate limited: 5 req/min burst 10 per IP)
if aiH != nil {
@@ -189,7 +234,18 @@ func New(db *sqlx.DB, authMW *auth.Middleware, cfg *config.Config, calDAVSvc *se
scoped.HandleFunc("PUT /api/notification-preferences", notifH.UpdatePreferences)
}
<<<<<<< HEAD
// CalDAV sync endpoints — settings permission required
||||||| 8e65463
// CalDAV sync endpoints
||||||| 82878df
// CalDAV sync endpoints
=======
// CalDAV sync endpoints — settings permission required
>>>>>>> mai/pike/p0-role-based
=======
// CalDAV sync endpoints
>>>>>>> mai/ritchie/p1-document-templates
if calDAVSvc != nil {
calDAVH := handlers.NewCalDAVHandler(calDAVSvc)
scoped.HandleFunc("POST /api/caldav/sync", perm(auth.PermManageSettings, calDAVH.TriggerSync))