Commit Graph
100 Commits
Author SHA1 Message Date
Siddharth Kumar Sah 700575adc8 docs: improve collapsible variants section in README
Use a table for cleaner layout. Add image sizes and CUDA prereq note.
2026-04-06 00:28:54 +08:00
Siddharth Kumar Sah acde7af08a docs: collapse lite/cuda variants in README quick start
Keep the main docker run command front and center. Lite and CUDA
variants are in a collapsible details block so the quick start
section stays scannable.
2026-04-05 23:46:27 +08:00
Siddharth Kumar Sah 8d2f401512 fix: use torch.cuda for GPU detection instead of onnxruntime providers
onnxruntime-gpu reports CUDAExecutionProvider as "available" just
because the library was compiled with CUDA support, even on machines
with no GPU. This made gpu_available() return True incorrectly,
causing upscale.py to try torch.device("cuda") and fall back to
Lanczos instead of running Real-ESRGAN on CPU.

torch.cuda.is_available() actually probes the hardware. Use it as
the single source of truth for GPU detection.

Verified: CUDA image on Apple Silicon (no GPU) now correctly reports
gpu: false and all AI tools run on CPU without crashes.
2026-04-05 22:24:16 +08:00
Siddharth Kumar Sah a291d1fe0b fix: prevent false GPU detection when CUDA image runs without GPU
The STIRLING_GPU=true env var was baked into the :cuda Dockerfile,
which made gpu_available() return True without checking actual
hardware. On machines without a GPU, this would crash upscale.py
(torch.device("cuda") fails) and ocr.py (PaddleOCR use_gpu=True).

Fix: the env var can only disable GPU (set to false/0), never
force-enable it. Hardware detection always runs. Removed the
baked env var from the Dockerfile since it adds no value now.
2026-04-05 22:03:57 +08:00
Siddharth Kumar Sah f1ae974de9 docs: add CUDA tag to README, getting-started, deployment, benchmarks
- README: add CUDA docker run example alongside full and lite
- Getting started: add GPU acceleration tip with speedup numbers
- Deployment: add CUDA row to variants table
- Docker tags: expand benchmarks with warm + cold start tables
2026-04-05 20:35:24 +08:00
Siddharth Kumar Sah 9381564269 docs: add CUDA/GPU documentation and benchmarks
- Add :cuda tag to Docker Tags docs with setup, benchmarks, compose example
- Add GPU acceleration tip to AI engine docs
- Include benchmark table from RTX 4070 testing
2026-04-05 20:04:04 +08:00
Siddharth Kumar Sah 29a382e9e0 feat: add GPU/CUDA acceleration support (:cuda Docker tag)
Add a :cuda Docker image tag that auto-detects NVIDIA GPU at runtime
and falls back gracefully to CPU. Same pattern as Immich.

- New gpu.py shared utility for cached CUDA detection
- Background removal (rembg): pass CUDAExecutionProvider to ONNX Runtime
- Upscaling (Real-ESRGAN): use CUDA device + FP16 when GPU available
- OCR (PaddleOCR): enable use_gpu when CUDA detected
- Dispatcher reports GPU status at startup via readiness signal
- Admin health endpoint exposes GPU availability
- Dockerfile uses ARG GPU=false with conditional NVIDIA CUDA base image
- docker-compose.gpu.yml override for GPU users
- CI/CD workflows build and publish :cuda tag (amd64 only)

Three tags: :latest (CPU), :lite (no AI), :cuda (GPU with CPU fallback)
2026-04-05 19:12:45 +08:00
Siddharth Kumar SahandJulian Nadeau d0c69d6a46 fix(web): skip empty Authorization header for forward-auth proxy compatibility
Centralize duplicated getToken() + Bearer header logic into a single
formatHeaders() helper in lib/api.ts. When no token exists, the
Authorization header is omitted entirely instead of sending an empty
Bearer token, which breaks forward-auth proxies like Authelia behind
Caddy.

Changes:
- Add formatHeaders() with try-catch around localStorage access
- Replace 20+ duplicated getToken() definitions across tool components
- Migrate all call sites including file-details, settings, change-password
- Update tests to verify header omission on empty token

Based on the fix proposed by @jules2689 in #6, with improvements:
file placement (lib/api.ts vs components), localStorage error handling,
simplified truthiness check, and complete call-site coverage.

Co-Authored-By: Julian Nadeau <julian@jnadeau.ca>
2026-04-05 18:41:06 +08:00
Siddharth Kumar Sah f21579c7a3 docs: fix license (MIT -> AGPLv3), add lite refs to llms.txt and ai.md
Both llms.txt and llms-full.txt incorrectly said MIT. Also added lite
variant mention to the description and a warning callout on the AI
engine docs page noting AI tools are unavailable in the lite image.
2026-04-05 08:03:29 +08:00
Siddharth Kumar Sah be45d3ca80 docs: add lite image references across all documentation
README Quick Start now shows both :latest and :lite commands.
Getting Started adds a tip callout about the lite image.
Deployment page lists both variants with a comparison table and
updates the CI/CD description to mention both are built.
Developer guide adds the lite build command.
2026-04-05 08:01:18 +08:00
Siddharth Kumar Sah 9974ea5c09 docs: add renaming vote banner and fix license badge
Static AGPLv3 badge replaces GitHub's auto-detected one, which
couldn't parse the dual-license preamble in the LICENSE file.
2026-04-05 00:59:19 +08:00
Siddharth Kumar Sah 98553ed674 fix: use heif-convert for HEIC decoding on Linux
Linux libheif packages provide heif-convert instead of heif-dec (which
is macOS-only). The decoder now tries heif-convert first, then falls
back to heif-dec. Both accept the same argument syntax.
2026-04-04 21:55:19 +08:00
Siddharth Kumar Sah 8991cde0ab fix: install HEVC codec plugins for CI HEIC tests
Ubuntu 24.04 uses plugin-based libheif codecs. Added libheif-plugin-x265
(HEVC encoder) and libheif-plugin-libde265 (HEVC decoder) to the CI test
job. Debian bookworm (Docker) bundles these in libheif1 directly.
2026-04-04 21:50:35 +08:00
Siddharth Kumar Sah f07454d349 fix: install libheif-examples in CI for HEIC tests
The integration tests for HEIC conversion require heif-enc and heif-dec
CLI tools which are not available on ubuntu-latest by default.
2026-04-04 21:41:19 +08:00
Siddharth Kumar Sah 6717c17a26 feat: add HEIC/HEIF format support for input and output
Add bidirectional HEIC support using system libheif CLI tools (heif-enc/heif-dec)
for HEVC encoding/decoding, since Sharp's bundled libheif only supports AV1.

- HEIC input: all tools now accept iPhone HEIC photos via heif-dec pre-processing
- HEIC output: convert tool produces true HEIC (HEVC) via heif-enc
- Docker: adds libheif-examples package for heif-enc/heif-dec CLI tools
- Tests: full conversion matrix (7x7), unit tests, and Playwright e2e tests
- Docs: updated OpenAPI spec, image-engine docs, getting-started, llms-full.txt
2026-04-04 21:33:48 +08:00
Siddharth Kumar Sah 93ad7cdfc1 feat: add "Crop to Content" mode to smart crop tool
Adds a new mode that trims uniform-color borders around the subject,
like GIMP's "Crop to Content." Includes configurable tolerance threshold
and optional pad-to-square with target size for e-commerce workflows.

The original attention-based crop is preserved as "Focus Crop" mode.

Closes #7
2026-04-04 19:49:49 +08:00
Siddharth Kumar Sah 30908ed058 fix: default theme to light instead of following system preference
New users on dark-mode systems were seeing dark theme on first visit.
The default is now explicitly light, matching the API's DEFAULT_THEME.
Users can still switch to dark or system in settings.
2026-04-04 19:42:05 +08:00
Siddharth Kumar Sah 9d621734c3 fix: resolve multiple API and e2e test bugs
- Health endpoint returns "healthy" instead of "ok" for consistency
- MAX_USERS now configurable via env var (default 5)
- People API returns team names instead of UUIDs in register/list
- PUT user update accepts team names (name-first lookup, fallback to ID)
- Login rate limit follows global rate limit when RATE_LIMIT_PER_MIN > 1000
- Strip-metadata preserves original format encoding instead of always PNG
- Fix e2e tests: rotate/crop/border button selectors match actual UI
- Fix e2e tests: create Engineering/Design teams in people test setup
- Fix e2e tests: people UI uses select for team field, not text input
- Update visual regression baseline for tablet home page
2026-04-04 17:44:51 +08:00
Siddharth Kumar Sah 9f0354388f fix: replace navigator.clipboard with copyToClipboard utility 2026-04-04 16:33:10 +08:00
Siddharth Kumar Sah b650dcd791 fix: replace crypto.randomUUID with generateId in pipeline/automation 2026-04-04 16:31:35 +08:00
Siddharth Kumar Sah 659081c568 fix: replace crypto.randomUUID with generateId in AI tool settings 2026-04-04 16:30:44 +08:00
Siddharth Kumar Sah 7a5a753a2d fix: replace crypto.randomUUID with generateId in use-tool-processor 2026-04-04 16:29:48 +08:00
Siddharth Kumar Sah 6b03a8b8bd fix: restore navigator.clipboard and execCommand mocks in tests 2026-04-04 16:28:43 +08:00
Siddharth Kumar Sah 19ce303123 feat: add copyToClipboard() utility with execCommand fallback 2026-04-04 16:25:25 +08:00
Siddharth Kumar Sah f61ab9f85c feat: add generateId() utility for non-secure context compatibility 2026-04-04 16:21:43 +08:00
Siddharth Kumar Sah 2fc42ebd14 docs: add implementation plan for HTTP compatibility fix
7 tasks covering generateId() utility, copyToClipboard() utility,
replacement of all 10 call sites, and final verification.
2026-04-04 16:19:23 +08:00
Siddharth Kumar Sah 2422baec30 docs: add execCommand fallback to clipboard utility in design spec
Without the fallback, every Copy button is dead on HTTP. The
execCommand approach is deprecated but works in all current browsers
and does not require a secure context.
2026-04-04 16:17:11 +08:00
Siddharth Kumar Sah 04c2461390 docs: add design spec for HTTP/non-secure context compatibility
Addresses issues #4 and #5 - crypto.randomUUID() and
navigator.clipboard.writeText() fail over plain HTTP on
non-localhost addresses, breaking all tool operations.
2026-04-04 16:14:41 +08:00
Siddharth Kumar Sah 3642b7d3b2 fix: log volume permission errors instead of swallowing them
Previously chown errors were silently discarded. Now logs a warning so
users can diagnose permission issues with Docker volume mounts.
2026-04-04 14:06:48 +08:00
Siddharth Kumar Sah dae27f4d55 fix: add XHR timeout to prevent UI spinning forever
60s timeout for standard tools, 5 min for AI tools. Shows a user-facing
error message instead of spinning indefinitely if the server hangs.
2026-04-04 14:06:41 +08:00
Siddharth Kumar Sah 5cd2b864bd fix: disable worker pool to prevent Docker processing hang
Worker thread initialization imports the tool registry which reads SQLite.
Under Docker volume filesystems, this can deadlock silently on SQLITE_BUSY,
causing APPLY to spin at 0% forever. Sharp operations complete in milliseconds
and don't need worker offloading. Added 30s AbortSignal timeout as defense
in depth for future re-enablement.
2026-04-04 14:05:11 +08:00
Siddharth Kumar Sah 39afb2a403 fix: handle volume permission issues for bind-mounted /data directory
Adds a gosu-based entrypoint that starts as root, fixes ownership of
/data and /tmp/workspace for the stirling user, then drops privileges.
This fixes "SQLITE database not found" errors when users bind-mount
host directories.
2026-04-04 00:16:41 +08:00
Siddharth Kumar Sah 47e53dc6cd feat: move theme toggle and GitHub button to top-right navbar
Remove socialLinks config and three-dots menu. Add appearance toggle
and combined GitHub + Star button directly in the navbar via layout
slot. The button shows the Octocat icon, "Star" label, and live
stargazer count.
2026-04-03 23:20:23 +08:00
Siddharth Kumar Sah 78cbdfdd6f chore: add docs screenshot 2026-04-03 23:17:06 +08:00
Siddharth Kumar Sah 47adfde5cb feat: add GitHub stars button to docs navbar and fix footer license
Add a star button with live count from the GitHub API in the top-right
of the docs site. Fix footer from "MIT License" to "AGPLv3 License".
2026-04-03 23:14:37 +08:00
Siddharth Kumar Sah 05fc844410 chore: use first-person voice in license and CLA text 2026-04-03 23:11:19 +08:00
Siddharth Kumar Sah 70b0ceed1c chore: switch to AGPLv3 dual-license
Replace MIT with AGPLv3 + commercial dual-license. Add copyright header
and dual-license notice to LICENSE, add CLA to CONTRIBUTING.md, update
README license section, and update all package.json license fields.
2026-04-03 23:07:58 +08:00
Siddharth Kumar Sah c2709d60f0 chore: remove sponsorship badges until Ko-fi and GitHub Sponsors are set up 2026-03-31 20:15:57 +08:00
Siddharth Kumar Sah 4fa8dd0780 fix: allow SVG files in the convert tool
SVG files were rejected by the convert endpoint because
validateImageBuffer only recognized raster magic bytes. This adds
text-based SVG detection, sanitization in the tool factory, and
proper Sharp density handling so SVG-to-raster conversion works
through the standard convert route.
2026-03-30 11:37:09 +08:00
Siddharth Kumar Sah b1bfcbef9c chore: remove internal superpowers docs from tracking
These files are already gitignored but were tracked from before
the ignore rule was added. Files remain local.
2026-03-30 08:48:06 +08:00
Siddharth Kumar Sah 50a52b43c1 chore: rebrand repo from siddharthksah to stirling-image org
Update all references across docs, workflows, UI components, and config
to point to the new GitHub org (stirling-image/stirling-image) and Docker
Hub account (stirlingimage/stirling-image) ahead of repo transfer.
2026-03-30 08:17:54 +08:00
Siddharth Kumar Sah 7f17cb98ce feat: add privacy policy page and fix CSP blocking API docs
Add a privacy policy page accessible at /privacy (public, no auth required).
Relax Content-Security-Policy for /api/docs route to allow Scalar's inline
script initialization, fixing blank docs page in production.
2026-03-29 23:57:08 +08:00
Siddharth Kumar Sah 1cbdfa1590 feat: add worker threads, persistent Python sidecar, graceful shutdown, and architectural improvements
- Graceful shutdown: SIGTERM/SIGINT handlers drain HTTP, stop workers, close DB
- Thumbnail caching: disk-cached thumbnails with immutable Cache-Control headers
- Worker thread pool: Piscina offloads Sharp processing off the main event loop
- Persistent Python dispatcher: pre-imports ML libraries, eliminates cold-start latency
- Tool page registry: declarative tool-to-component mapping replaces 750-line switch
- File store cleanup: remove dead derived fields, stable files array reference
- Job persistence: progress written to SQLite jobs table, stale jobs recovered on startup
2026-03-29 17:23:41 +08:00
Siddharth Kumar Sah 88729e255d update bg removal png image for demo 2026-03-28 19:25:39 +08:00
Siddharth Kumar Sah 4577d5c30e fix: simplify public health to static response, add 403 test
Remove DB probe from public health endpoint - it only needs to confirm
the process is alive. Add test for non-admin user getting 403 on admin
health endpoint.
2026-03-28 19:08:17 +08:00
Siddharth Kumar Sah 818e5877a7 fix: move health diagnostics behind admin auth
Public GET /api/v1/health now returns only status and version.
Full diagnostics (uptime, storage, database, queue) moved to
GET /api/v1/admin/health which requires admin authentication.
2026-03-28 19:08:17 +08:00
Siddharth Kumar Sah 813fa6b7e8 fix: use two-pass validation in settings PUT to prevent partial writes
Validation now runs on all entries before any database writes.
Previously, clean entries could be written before a later malicious
entry triggered a 400 response.
2026-03-28 19:08:17 +08:00
Siddharth Kumar Sah 8a62093130 fix: reject HTML tags in settings API to prevent stored XSS
PUT /api/v1/settings now returns 400 if any key or value contains HTML
tags. Settings are configuration values - there is no legitimate use
case for HTML in them.
2026-03-28 19:08:17 +08:00
Siddharth Kumar Sah fb84f5ce8d fix: switch README Docker references from GHCR to Docker Hub
GHCR image requires authentication for pulls. Docker Hub image is
publicly accessible and works for anonymous users.
2026-03-28 19:08:17 +08:00
Siddharth Kumar Sah 2e29501ae6 fix: show checkerboard behind transparent images in before/after slider
The processed image in the BeforeAfterSlider was layered on top of the
original with a semi-transparent background. When the processed result
had transparency (e.g. after remove-background), the original image
showed through, making it look like the background was not removed.

Added an opaque checkerboard background behind the processed image so
transparent areas are clearly visible instead of showing the original.
2026-03-28 18:34:22 +08:00
Siddharth Kumar Sah aa1f87fc91 fix: resolve pipeline step race condition and infinite re-render loop
Two issues caused intermittent step addition failures in the automation
pipeline:

1. RemoveBgControls had onChange in its useEffect deps. Since onChange is
   a new function reference on every parent render, this created an
   infinite re-render loop (effect -> setState -> render -> effect).
   Fixed by using the onChangeRef pattern matching other settings
   components.

2. All step mutation callbacks read from stepsRef.current and passed
   values to setSteps. Concurrent callbacks (e.g. addStep + a settings
   effect) would overwrite each other. Fixed by switching to functional
   state updates (setSteps(prev => ...)) and removing stepsRef.

Also rewrites automate e2e tests to use manual step addition instead of
referencing templates that no longer exist in the UI.
2026-03-28 18:34:05 +08:00
Siddharth Kumar Sah 748ac607bc fix: sync stepsRef during render, not useEffect
Child component effects (Controls onChange) fire before the parent's
useEffect that synced stepsRef. This caused updateStepSettings to read
stepsRef.current as [] and wipe out newly added steps.

Fix: assign stepsRef.current = steps directly during render so the
ref is always current before any child effects execute.
2026-03-28 17:02:24 +08:00
Siddharth Kumar Sah 8b20fef2d8 fix: prevent stale closure in pipeline step callbacks
All step mutation callbacks (addStep, removeStep, moveStep,
updateStepSettings) captured `steps` in their useCallback closures.
When React batched state updates, rapid interactions could use a stale
steps array, causing clicks to silently fail.

Fix: use a stepsRef that always holds the latest value. Callbacks read
from stepsRef.current instead of the captured closure variable, and no
longer need `steps` in their dependency arrays.
2026-03-28 16:42:59 +08:00
Siddharth Kumar Sah 7b1b019b77 fix: clear search when adding a step from the tool picker
When a tool was selected via search, the search text persisted after
the picker closed. Reopening the picker showed a filtered list instead
of all tools, making it look like clicking tools without searching
didn't work.
2026-03-28 16:32:28 +08:00
Siddharth Kumar Sah 33cd575506 chore: standardize tool count to 30+ across all docs and UI 2026-03-28 16:32:28 +08:00
Siddharth Kumar Sah 9acbedf4b7 fix: prevent pipeline step settings from resetting on collapse
The settings panel used conditional rendering ({isExpanded && ...})
which unmounted the Controls component on collapse, losing all state.
Switch to CSS hidden class so the component stays mounted and settings
persist when the panel is collapsed and re-expanded.
2026-03-28 16:17:39 +08:00
Siddharth Kumar Sah 1c05bc76e5 refactor: replace TOOL_FIELDS with shared Controls components (DRY)
Extract a *Controls subcomponent from all 16 pipeline-compatible tool
settings components. Each Controls component holds the UI state and
settings controls, accepts an onChange callback, and uses useRef to
prevent infinite re-render loops. The standalone *Settings components
become thin wrappers that add useToolProcessor, useFileStore, and
action buttons.

pipeline-step-settings.tsx is rewritten from ~675 lines to ~55 lines:
the entire TOOL_FIELDS declarative map and generic renderer are deleted
and replaced with direct imports of the Controls components. Pipeline
steps now render the exact same UI as standalone tool pages.

Special cases:
- CropControls: numeric inputs for pipeline (standalone uses canvas)
- RotateControls: resetSignal prop for post-processing reset
- ColorControls: accepts toolId for tab selection
- StripMetadataControls: checkboxes only (no file inspection)
- RemoveBgControls: already extracted, unchanged
2026-03-28 16:04:42 +08:00
Siddharth Kumar Sah 5a50aecd0b refactor: extract RemoveBgControls for DRY reuse in pipeline steps
Extract the settings controls (subject type, quality, background color)
from RemoveBgSettings into a shared RemoveBgControls component that
accepts settings + onChange props. Both the standalone tool page and the
pipeline step configurator now render the same component, so the UI is
identical and changes only need to be made in one place.
2026-03-28 15:40:39 +08:00
Siddharth Kumar Sah 017a71562a fix: add remove-background settings to pipeline step configurator
The pipeline step settings had an empty array for remove-background,
showing "No configurable settings" even though the tool supports
model selection and background color. Add AI model selector (u2net,
birefnet-general-lite, birefnet-general, birefnet-portrait, bria-rmbg)
and background color picker matching the standalone tool's options.
2026-03-28 15:32:28 +08:00
Siddharth Kumar Sah c48bfba879 feat: make AI tools pipeline-compatible and add search to tool picker
Register remove-background, upscale, and blur-faces in the pipeline
tool registry via registerToolProcessFn(). These tools keep their
custom HTTP routes (with progress callbacks) for direct use, but now
also provide a simple process function for pipeline/batch execution.

Add a search bar to the pipeline tool picker so users can quickly
find tools by name or description. Uses the existing SearchBar
component and the same filtering pattern as the main tool panel.

Update tests to reflect that these 3 AI tools are now pipeline-
compatible (moved from excluded to included assertions).
2026-03-28 15:09:23 +08:00
Siddharth Kumar Sah 4a504281a3 fix: surface hidden errors and add batch rejection tests
Fix empty catch blocks in settings dialog (logo upload/delete) and
automate page (pipeline save) that silently swallowed errors. Users
now see error messages when these operations fail.

Add 5 integration tests verifying batch endpoint returns 404 for
custom-route tools (remove-background, upscale, ocr, blur-faces,
erase-object), matching the pipeline rejection tests.
2026-03-28 14:45:14 +08:00
Siddharth Kumar Sah fa01388742 test: add pipeline tool compatibility tests
Add 8 tests that would have caught the pipeline bug where custom-route
tools (remove-background, upscale, ocr, etc.) were shown in the
pipeline picker but failed silently when executed.

New tests:
- GET /api/v1/pipeline/tools returns factory-registered tool IDs
- Verify resize, crop, convert, compress, rotate are included
- Verify remove-background, upscale, ocr, blur-faces, erase-object,
  info, collage, compare are excluded
- Pipeline execution returns 400 for each custom-route tool
2026-03-28 14:42:27 +08:00
Siddharth Kumar Sah 658954ea19 fix: remove Google Drive coming soon placeholder from files nav 2026-03-28 14:40:23 +08:00
Siddharth Kumar Sah 0410bf3461 fix: pipeline only shows compatible tools and displays errors
The pipeline tool picker was showing all tools, but only tools
registered via createToolRoute() support pipeline execution. Tools
with custom routes (remove-background, upscale, ocr, etc.) would
silently fail with "Tool not found" and the empty catch block hid
the error from users.

Add GET /api/v1/pipeline/tools endpoint that returns the IDs of
pipeline-compatible tools. The frontend fetches this list and filters
the tool picker accordingly. Also surface pipeline execution errors
in the UI instead of swallowing them.
2026-03-28 14:38:48 +08:00
Siddharth Kumar Sah 565b4805c7 fix: trigger browser password save prompt on password change
Safari, Chrome, and Firefox only offer to save passwords when they see
a real form submission with page navigation, not fetch() + redirect.

After the change-password API call succeeds, dynamically create a form
with the username and new password (autocomplete=username + new-password),
POST it to "/" causing a real navigation. The browser detects the form
submission with credential fields and prompts to save.

Also make the username field visible (read-only) on the change-password
page since Safari ignores hidden inputs for password detection, and add
autocomplete attributes to the login page fields.
2026-03-28 14:24:13 +08:00
Siddharth Kumar Sah 7c76c2a2a0 feat: add password generator and browser save prompt on change-password page
Add a "Generate strong password" button that creates a random 16-char
password meeting all requirements (uppercase, lowercase, digit).
Generated passwords are shown in plain text so users can copy them.
Add autocomplete attributes (current-password, new-password, username)
so browsers prompt to save the new credentials after submission.
2026-03-28 14:12:46 +08:00
Siddharth Kumar Sah 01cd1d9f71 feat: add forced password change page on first login
The backend sets mustChangePassword=true for all new accounts and
blocks API calls until the password is changed. The frontend was not
handling this flag - it logged the user in and redirected to the
dashboard where every API call silently failed with 403.

Add a /change-password page that is shown when mustChangePassword is
true. The login page now redirects there instead of home, and the
AuthGuard intercepts any direct navigation to force the change first.
2026-03-28 14:02:13 +08:00
Siddharth Kumar Sah b08e006512 fix(tests): remove temp DB cleanup that races with other test files
The integration test cleanup was deleting the shared temp directory
(rmSync on dirname(DB_PATH)), which causes SQLITE_IOERR_FSTAT in
other test files that still reference the same database. The temp
directory uses a random UUID under /tmp and is cleaned up by the OS.
2026-03-28 12:49:23 +08:00
Siddharth Kumar Sah 28c44bef5f updated the dashboard image 2026-03-28 12:29:39 +08:00
Siddharth Kumar Sah f17c114246 docs: improve README with clearer positioning and scannable feature list 2026-03-28 12:26:31 +08:00
Siddharth Kumar Sah 9f68960eda docs: rewrite README, add CONTRIBUTING.md, developer and translation guides
Rewrite README to remove AI writing patterns (em dashes, promotional
language, vague claims). Make Quick Start section explicit about default
credentials and forced password change. Add Contributing section linking
to CONTRIBUTING.md, developer guide, and translation guide.

Create CONTRIBUTING.md with issue guidelines, PR workflow, commit
conventions, and development setup. Add developer guide (dev setup,
project structure, how to add a tool) and translation guide (how the
i18n system works, step-by-step for adding a language) to VitePress
docs. Register both new pages in the docs sidebar.
2026-03-28 12:14:24 +08:00
Siddharth Kumar Sah ce51065243 fix: handle migration race condition in concurrent test workers
Drizzle's migrate() throws when multiple vitest workers race to apply
migrations on the same temp database. The DrizzleError wraps a
SqliteError ("table already exists") in its cause chain. Add a
same-process guard and a catch that checks both the outer message and
cause for "already exists" so the second worker continues safely.
2026-03-28 11:45:54 +08:00
Siddharth Kumar Sah 6cfa3b0c38 feat: multi-arch Docker support, security hardening, and test improvements
Remove hardcoded --platform=linux/amd64 from Dockerfile so buildx produces
native arm64 images for Apple Silicon and Raspberry Pi. Add audit logging
for auth events, harden file storage with extension whitelists and
double-extension attack prevention, reject null-byte buffers in validation,
add data-testid attributes to all tool settings components, update
deployment docs with architecture notes and correct CI workflow references,
and fix unit test mock to match throwWithMessage error extraction.
2026-03-28 11:19:09 +08:00
Siddharth Kumar Sah d3f6bac62b fix(docs): remove hero logo from home page 2026-03-27 20:54:46 +08:00
Siddharth Kumar Sah 98478e2719 feat(docs): add gem logo to GitHub Pages nav bar and home hero 2026-03-27 20:52:06 +08:00
Siddharth Kumar Sah 8ae1d8cec3 docs: slim down REST API page to quick-start guide
The full API reference now lives at /api/docs (Scalar). This page
becomes a getting-started guide covering auth, tool pattern, tool IDs,
batch, pipelines, and errors — pointing to the interactive docs for
per-endpoint details.
2026-03-27 17:36:58 +08:00
Siddharth Kumar Sah 0e938c9b7e docs: add llms.txt info box to REST API page and fix Swagger reference 2026-03-27 17:32:11 +08:00
Siddharth Kumar Sah a4d4d36828 fix(docs): clean up footer llms.txt links 2026-03-27 17:10:58 +08:00
Siddharth Kumar Sah c59e4a0668 feat(docs): add llms.txt links to GitHub Pages footer
Add llms.txt and llms-full.txt links in the footer with
"AI-friendly docs" label. Also add link rel="llms-txt" head tag
for automatic discovery by AI tools.
2026-03-27 16:41:44 +08:00
Siddharth Kumar Sah 620b8ad038 fix(api): resolve team name lookup and show server error messages
- Backend: look up teams by name first (frontend sends name, not ID)
- Frontend: parse response body on API errors instead of showing
  generic "API error: 400" — now shows the actual server message
  (e.g. "Password must be at least 8 characters...")
2026-03-27 16:41:44 +08:00
Siddharth Kumar Sah 5c4b2a59d3 fix(docs): ignore localhost dead links in VitePress build
The /api/docs tip box links to localhost which fails the dead link
check in CI.
2026-03-27 13:53:34 +08:00
Siddharth Kumar Sah e3a8558134 fix(ui): clean up settings, automate page, fullscreen logo, and README
- README: simplify to match Stirling-PDF style, add dashboard screenshot
- Settings: remove unsupported languages from dropdown, remove unused
  experimental tools toggle
- Automate: remove hardcoded template pipelines from sidebar
- Fullscreen: add GemLogo icon to header
2026-03-27 13:50:04 +08:00
Siddharth Kumar Sah e6dc7b0a18 feat(docs): add llms.txt and llms-full.txt to GitHub Pages
Serve LLM-friendly documentation at the docs site root.
llms.txt is the index, llms-full.txt has all docs in one file.
2026-03-27 13:50:04 +08:00
Siddharth Kumar Sah cff1930920 feat(api): add llms.txt and llms-full.txt endpoints
Serve LLM-friendly documentation at /llms.txt (index) and
/llms-full.txt (full API docs as markdown). Generated from the
OpenAPI spec at startup.
2026-03-27 13:50:04 +08:00
Siddharth Kumar Sah 655398e184 test(api): add integration tests for API docs endpoint
Also update GitHub Pages REST API doc to link to /api/docs.
2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah 9ed1090651 feat(api): add all remaining endpoints to OpenAPI spec
Add batch, pipeline, file, auth, API key, settings, teams, branding, and
system endpoints — bringing the total from 38 to 67 documented paths.
2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah 2bf86894d0 feat(api): add all tool endpoints to OpenAPI spec 2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah 05854fd61f fix(api): use content instead of spec.content for Scalar v1.49 API 2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah 9488201806 feat(api): add OpenAPI 3.1 spec skeleton with common schemas 2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah 849878e72f feat(api): register docs route in server and test helper 2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah a46d500012 fix(api): allow Scalar docs through auth and CSP 2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah abb2916233 feat(api): add Scalar docs route and install dependency 2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah dcd926c57e feat(branding): add OG social preview image 2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah fadf0a8a22 refactor(branding): extract GemLogo to shared component and add to About section 2026-03-27 13:50:03 +08:00
Siddharth Kumar Sah 26cc18342f feat(branding): add PWA manifest and PNG logo assets 2026-03-27 13:50:02 +08:00
Siddharth Kumar Sah 42ec0f2490 feat(docs): add gem favicon to VitePress site 2026-03-27 13:50:02 +08:00
Siddharth Kumar Sah d47548a1d7 fix(a11y): add aria-hidden to decorative GemLogo SVG 2026-03-27 13:50:02 +08:00
Siddharth Kumar Sah 39dfb93679 feat(branding): show gem icon in app header as default logo 2026-03-27 13:50:02 +08:00
Siddharth Kumar Sah 036492725e feat(branding): add favicon and meta tags to index.html 2026-03-27 13:50:02 +08:00
Siddharth Kumar Sah 0214ac11b1 feat(branding): add faceted gem SVG logo assets 2026-03-27 13:50:02 +08:00