Willow should expose a strong API layer before it exposes convenience components.
The API is the contract that lets agents integrate Willow into other projects.
- Workspace-scoped by default.
- TypeScript-first.
- Explicit errors.
- Stable public delivery URLs.
- Version-aware assets.
- Public delivery separated from authenticated management.
- API keys hashed at rest.
- Avoid leaking Netlify implementation details as the primary user contract.
There are two broad use cases:
- App user session: a logged-in user managing workspaces and assets inside Willow.
- External upload client: another project uploads into a Willow workspace.
The exact external upload auth model is unresolved. See Open Questions.
Authenticated with Netlify Identity user session.
Initial actions:
- Get current profile/account.
- Create workspace.
- List workspaces.
- Update workspace.
- Create workspace API key.
- Revoke workspace API key.
- List workspace assets.
- Get asset detail.
- Delete asset.
- Replace asset with a new version.
Authenticated with either a user session or a workspace-scoped API credential.
For the first app UI surface, user-session upload is enough. Workspace-scoped API credentials are still part of the product contract, but the exact browser/server token pattern remains open.
Initial action:
POST /api/workspaces/{workspace_id}/assets
Request:
- Multipart file upload.
- Optional metadata:
alt_textdescriptiontagslater
Response:
asset_idversion_idkindcontent_typesize_bytesdelivery_urlimage_urlwhen applicable
Public by default for MVP, with room for access controls later.
Conceptual routes:
GET /delivery/{workspace_slug}/{asset_id}
GET /delivery/{workspace_slug}/{asset_id}/v/{version_number}
GET /image/{workspace_slug}/{asset_id}?w=800&h=600&fit=cover&q=80
Original file delivery:
- Resolve workspace and asset.
- Resolve current or requested version.
- Stream or redirect to Blob-backed content.
- Record a delivery event.
Image delivery:
- Resolve workspace and asset.
- Validate asset kind is
image. - Validate transform parameters.
- Proxy or rewrite through Netlify Image CDN.
- Record a transformation/delivery event.
API errors should use a consistent JSON shape:
{
"error": {
"code": "asset_not_found",
"message": "Asset not found.",
"request_id": "req_..."
}
}Initial error codes:
unauthorizedforbiddenworkspace_not_foundasset_not_foundunsupported_file_typefile_too_largeinvalid_image_transformupload_faileddelivery_failed
Asset API responses should expose both the asset identity and the current version.
Replacing an asset should create a new version and update current_version_id. Stable asset URLs should resolve to the current version unless a specific version is requested.