Image Gallery
The old React front-end had a dedicated image gallery feature (upload,
browse, and select images for use as client logos, brand images, and so
on), backed by an ImageGallery component and an ImageSelectionModal.
That frontend feature has not been carried over to tracker-frontend-svelte
or tracker-admin-svelte. There is currently no gallery grid, upload
button, or image-selection modal in either Svelte app — a search of
tracker-frontend-svelte/src, tracker-admin-svelte/src, and
packages/tracker-shared/src turns up no gallery/upload UI code.
What still exists
Backend
The backend image API is unchanged and still fully functional
(app/api/routes/images.py). Images are stored in the filesystem under
STATIC_DIR/images (served at the /static/images/... URL prefix) with
endpoints for:
- Listing images (paginated)
- Uploading images (validated against a fixed set of allowed MIME types: JPEG, PNG, GIF, WebP, SVG)
- Retrieving a single image's metadata
- Deleting images
Image metadata is stored in the database, including the original filename, a UUID-based storage filename, MIME type, size, dimensions, and URL path.
Data model usage
Some entities still carry an image_url field that resolves to a
/static/... URL served by the backend — for example, ProductionRun
(packages/tracker-shared/src/api/production-runs.ts) has an
image_url: string | null field. However, none of the current campaign,
brand, or client editor modals in packages/tracker-shared/src/components/
(CampaignEditorModal.svelte, clients/BrandEditorModal.svelte,
clients/ClientEditorModal.svelte) expose a way to set or change that field
today — there is no image field, upload input, or gallery button in any of
them. The value can currently only be set directly through the API.
nginx /static/ routing
Because production-run images resolve to real /static/... URLs, the
/static/ location block is deliberately kept in the Svelte apps' nginx
config even though most of the old React-era special-cased location =
blocks were removed as redundant — see
tracker-admin-svelte/docker/nginx.conf and
docs/development/svelte-staging-cutover-todo.md for the history of that
cleanup.
Adding image selection back
If a future feature needs image upload/selection in the Svelte apps, the
backend contract (app/api/routes/images.py / schemas.ImagesResponse) is
still there to build against. There is no existing Svelte component to
follow as a pattern (unlike the old React ImageSelectionModal.tsx), so a
new component would need to be built from scratch — a reasonable home would
be packages/tracker-shared/src/components/ if both apps need it, following
the pattern of the existing shared editor modals (e.g.
CampaignEditorModal.svelte) for modal structure and daisyUI styling.
Troubleshooting
If you're debugging a broken image_url on a production run/brand/client:
- Check that the image file exists on disk under
STATIC_DIR/images/ - Verify the image record exists in the database
- Confirm nginx's
/static/location is present and proxying to the API container - Check browser network requests for 404s when loading the image URL
- Remember there is no in-app UI to change these values today — they are set via direct API calls only