mirror of
https://github.com/Sea-Haven-Industries/seahaven-ap.git
synced 2026-09-30 13:53:18 +00:00
* feat(api): serve portal-shaped health and error envelope
Move liveness to GET /api/health { stage, sha } with a Node 24 image on 8080 so ALB probes and deploy verify do not need auth or a database ping.
* feat(api): switch live auth to host cookie BFF
Replace Bearer as the documented session path with Cognito hosted UI plus __Host-ap_* cookies so the SPA can call /api with credentials include.
* feat(web): add unused cookie SPA API client
Land a credentials-include fetch helper and hand-synced health/me types without wiring pages or domain hooks, so mocks stay the default data path.
* feat(api): add master-data OpenAPI and Hono stubs
* feat(api): add invoice, line, and document stubs
* feat(api): add approval policy, inbox, and activity stubs
* test(web): fix SPA client fetch mock types
* test(web): cast fetch mock call args for tsc
* fix(api): do not default DEV_AUTH_BYPASS outside local migrate
* fix(api): replace invoice lines in a single transaction
* fix(api): create invoices and lines in one transaction
* fix(api): inline GIT_SHA from the image build arg
* fix(api): stop PATCH from skipping the approval workflow
* fix(api): address review feedback
* fix(ci): format upsert-user test
* fix(api): document only the auth statuses the routes return
* fix(api): drop health 400 responses the routes never return
486 lines
12 KiB
YAML
486 lines
12 KiB
YAML
Error:
|
|
type: object
|
|
required:
|
|
- error
|
|
properties:
|
|
error:
|
|
type: object
|
|
required:
|
|
- code
|
|
- message
|
|
- correlationId
|
|
properties:
|
|
code:
|
|
type: string
|
|
description: Machine-readable error code.
|
|
example: NOT_FOUND
|
|
message:
|
|
type: string
|
|
description: Human-readable error message.
|
|
example: Not found.
|
|
correlationId:
|
|
type: string
|
|
description: Request correlation identifier echoed from x-correlation-id when present.
|
|
example: 11111111-1111-4111-8111-111111111111
|
|
HealthResponse:
|
|
type: object
|
|
required:
|
|
- stage
|
|
- sha
|
|
properties:
|
|
stage:
|
|
type: string
|
|
description: Deployment stage name.
|
|
example: local
|
|
sha:
|
|
type: string
|
|
description: Git SHA inlined at image build.
|
|
example: deadbeef
|
|
ReadyResponse:
|
|
type: object
|
|
required:
|
|
- status
|
|
- database
|
|
properties:
|
|
status:
|
|
type: string
|
|
description: Process readiness marker.
|
|
example: ok
|
|
database:
|
|
type: string
|
|
description: Database ping result.
|
|
example: up
|
|
MeResponse:
|
|
type: object
|
|
required:
|
|
- id
|
|
- email
|
|
- name
|
|
- role
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Internal user primary key.
|
|
example: 11111111-1111-4111-8111-111111111111
|
|
email:
|
|
type: string
|
|
format: email
|
|
description: Caller email address.
|
|
example: admin@seahavenind.com
|
|
name:
|
|
type: string
|
|
description: Display name for the caller.
|
|
example: Dev Admin
|
|
role:
|
|
type: string
|
|
description: Authorization role for RBAC checks.
|
|
enum:
|
|
- admin
|
|
- ap_processor
|
|
- approver
|
|
- viewer
|
|
example: admin
|
|
Vendor:
|
|
type: object
|
|
required:
|
|
- id
|
|
- name
|
|
- defaultPaymentMethod
|
|
- createdAt
|
|
- updatedAt
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Vendor primary key.
|
|
example: 55555555-5555-4555-8555-555555555555
|
|
name:
|
|
type: string
|
|
description: Vendor display name.
|
|
example: Acme Facilities Supply
|
|
email:
|
|
type: [string, "null"]
|
|
description: Billing email when present.
|
|
example: billing@acmefacilities.example
|
|
defaultPaymentMethod:
|
|
type: string
|
|
enum: [check, ach]
|
|
description: Default payment method for new invoices.
|
|
example: check
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
updatedAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row update time.
|
|
GlAccount:
|
|
type: object
|
|
required: [id, code, name, createdAt, updatedAt]
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: GL account primary key.
|
|
example: 66666666-6666-4666-8666-666666666666
|
|
code:
|
|
type: string
|
|
description: Account code.
|
|
example: "6100"
|
|
name:
|
|
type: string
|
|
description: Account name.
|
|
example: Facilities Expense
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
updatedAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row update time.
|
|
Department:
|
|
type: object
|
|
required: [id, code, name, createdAt, updatedAt]
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Department primary key.
|
|
example: 77777777-7777-4777-8777-777777777777
|
|
code:
|
|
type: string
|
|
description: Department code.
|
|
example: OPS
|
|
name:
|
|
type: string
|
|
description: Department name.
|
|
example: Operations
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
updatedAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row update time.
|
|
User:
|
|
type: object
|
|
required: [id, email, name, role, createdAt, updatedAt]
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: User primary key.
|
|
example: 11111111-1111-4111-8111-111111111111
|
|
email:
|
|
type: string
|
|
format: email
|
|
description: User email address.
|
|
example: admin@seahavenind.com
|
|
name:
|
|
type: string
|
|
description: Display name.
|
|
example: Dev Admin
|
|
role:
|
|
type: string
|
|
enum: [admin, ap_processor, approver, viewer]
|
|
description: Authorization role.
|
|
example: admin
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
updatedAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row update time.
|
|
Invoice:
|
|
type: object
|
|
required:
|
|
- id
|
|
- vendorId
|
|
- invoiceNumber
|
|
- amount
|
|
- amountDue
|
|
- dueDate
|
|
- status
|
|
- paymentMethod
|
|
- memo
|
|
- createdAt
|
|
- updatedAt
|
|
- lines
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Invoice primary key.
|
|
example: 88888888-8888-4888-8888-888888888888
|
|
vendorId:
|
|
type: string
|
|
format: uuid
|
|
description: Vendor foreign key.
|
|
example: 55555555-5555-4555-8555-555555555555
|
|
invoiceNumber:
|
|
type: string
|
|
description: Vendor-issued invoice number.
|
|
example: INV-1001
|
|
amount:
|
|
type: string
|
|
description: Invoice total as numeric(14,2) text.
|
|
example: "1250.00"
|
|
amountDue:
|
|
type: string
|
|
description: Remaining amount due as numeric(14,2) text.
|
|
example: "1250.00"
|
|
dueDate:
|
|
type: string
|
|
description: Due date as YYYY-MM-DD.
|
|
example: "2026-09-01"
|
|
payDate:
|
|
type: [string, "null"]
|
|
description: Optional pay date as YYYY-MM-DD.
|
|
example: "2026-09-15"
|
|
sendPaymentOn:
|
|
type: [string, "null"]
|
|
description: Optional send date as YYYY-MM-DD.
|
|
example: "2026-09-10"
|
|
status:
|
|
type: string
|
|
enum: [pending_approval, approved, scheduled, paid, rejected, void]
|
|
description: Invoice workflow status.
|
|
example: pending_approval
|
|
paymentMethod:
|
|
type: string
|
|
enum: [check, ach]
|
|
description: Payment method for this invoice.
|
|
example: check
|
|
memo:
|
|
type: string
|
|
description: Free-form memo.
|
|
example: Seed invoice for local smoke.
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
updatedAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row update time.
|
|
lines:
|
|
type: array
|
|
description: Coding lines attached to the invoice.
|
|
items:
|
|
$ref: "#/InvoiceLine"
|
|
InvoiceLine:
|
|
type: object
|
|
required: [id, invoiceId, description, amount, createdAt]
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Line primary key.
|
|
example: 99999999-9999-4999-8999-999999999999
|
|
invoiceId:
|
|
type: string
|
|
format: uuid
|
|
description: Parent invoice id.
|
|
example: 88888888-8888-4888-8888-888888888888
|
|
description:
|
|
type: string
|
|
description: Line description.
|
|
example: Monthly maintenance
|
|
amount:
|
|
type: string
|
|
description: Line amount as numeric(14,2) text.
|
|
example: "1250.00"
|
|
glAccountId:
|
|
type: [string, "null"]
|
|
format: uuid
|
|
description: Optional GL account id.
|
|
departmentId:
|
|
type: [string, "null"]
|
|
format: uuid
|
|
description: Optional department id.
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
Document:
|
|
type: object
|
|
required: [id, objectKey, contentType, fileName, createdAt]
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Document primary key.
|
|
example: dddddddd-dddd-4ddd-8ddd-dddddddddddd
|
|
invoiceId:
|
|
type: [string, "null"]
|
|
format: uuid
|
|
description: Parent invoice id when attached.
|
|
objectKey:
|
|
type: string
|
|
description: Object key in the documents bucket.
|
|
example: seed/inv-1001.pdf
|
|
contentType:
|
|
type: string
|
|
description: Uploaded object MIME type.
|
|
example: application/pdf
|
|
fileName:
|
|
type: string
|
|
description: Original file name.
|
|
example: inv-1001.pdf
|
|
uploadedByUserId:
|
|
type: [string, "null"]
|
|
format: uuid
|
|
description: User who started the upload.
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
uploadUrl:
|
|
type: string
|
|
description: Presigned PUT URL returned on create.
|
|
uploadHeaders:
|
|
type: object
|
|
additionalProperties:
|
|
type: string
|
|
description: Headers the browser must send with the presigned PUT.
|
|
downloadUrl:
|
|
type: string
|
|
description: Presigned GET URL returned on confirm or get.
|
|
ApprovalPolicy:
|
|
type: object
|
|
required: [id, name, priority, active, createdAt, updatedAt]
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Policy primary key.
|
|
example: cccccccc-cccc-4ccc-8ccc-cccccccccccc
|
|
name:
|
|
type: string
|
|
description: Policy display name.
|
|
example: Default approver policy
|
|
priority:
|
|
type: integer
|
|
description: Lower numbers match first.
|
|
example: 10
|
|
amountThreshold:
|
|
type: [string, "null"]
|
|
description: Minimum invoice amount that matches this policy.
|
|
example: "0.00"
|
|
skipBelowAmount:
|
|
type: [string, "null"]
|
|
description: Amounts below this skip the approval step.
|
|
example: "25.00"
|
|
active:
|
|
type: boolean
|
|
description: Whether the policy is considered when matching.
|
|
example: true
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
updatedAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row update time.
|
|
ApprovalStep:
|
|
type: object
|
|
required: [id, invoiceId, stepOrder, approverRole, status, createdAt]
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Step primary key.
|
|
example: eeeeeeee-eeee-4eee-8eee-eeeeeeeeeeee
|
|
invoiceId:
|
|
type: string
|
|
format: uuid
|
|
description: Parent invoice id.
|
|
policyId:
|
|
type: [string, "null"]
|
|
format: uuid
|
|
description: Policy that created the step.
|
|
stepOrder:
|
|
type: integer
|
|
description: Order within the invoice.
|
|
example: 1
|
|
approverRole:
|
|
type: string
|
|
enum: [admin, ap_processor, approver, viewer]
|
|
description: Role allowed to act when no assignee is set.
|
|
example: approver
|
|
assigneeUserId:
|
|
type: [string, "null"]
|
|
format: uuid
|
|
description: Optional assigned user.
|
|
status:
|
|
type: string
|
|
enum: [pending, approved, rejected, skipped]
|
|
description: Step status.
|
|
example: pending
|
|
actedByUserId:
|
|
type: [string, "null"]
|
|
format: uuid
|
|
description: User who acted.
|
|
actedAt:
|
|
type: [string, "null"]
|
|
format: date-time
|
|
description: When the step was acted on.
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
InvoiceComment:
|
|
type: object
|
|
required: [id, invoiceId, body, createdAt]
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Comment primary key.
|
|
invoiceId:
|
|
type: string
|
|
format: uuid
|
|
description: Parent invoice id.
|
|
authorUserId:
|
|
type: [string, "null"]
|
|
format: uuid
|
|
description: Author user id.
|
|
body:
|
|
type: string
|
|
description: Comment text.
|
|
example: Looks good.
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|
|
ActivityLog:
|
|
type: object
|
|
required: [id, invoiceId, message, createdAt]
|
|
properties:
|
|
id:
|
|
type: string
|
|
format: uuid
|
|
description: Activity row primary key.
|
|
invoiceId:
|
|
type: string
|
|
format: uuid
|
|
description: Parent invoice id.
|
|
actorUserId:
|
|
type: [string, "null"]
|
|
format: uuid
|
|
description: Actor user id.
|
|
message:
|
|
type: string
|
|
description: Activity message.
|
|
example: Step approved.
|
|
createdAt:
|
|
type: string
|
|
format: date-time
|
|
description: Row creation time.
|