✨ Features
Lite List Endpoints in the REST API
New lightweight list endpoints for projects, members, cycles, and modules return trimmed payloads built for pickers, dropdowns, and sync jobs that only need identifiers and display fields. They avoid the cost of the full list responses when you are populating a selector or mirroring structure into an external system, and they carry the same order_by sanitization and scoping guarantees as the full endpoints.
Feature-Namespaced Translations
The internationalization package now runs on react-i18next with translations stored as per-feature JSON namespaces (workspace, project, work item, cycle, intake, and more) instead of a single monolithic TypeScript file. Translators and contributors can work on one feature area at a time across all 19 supported languages, and the public translation API is unchanged, so no consumer code needed to move.
⬆️ Enhancements
- Webhook delivery payloads now include
workspace_slug, so receivers can route events without an extra lookup. - Self-hosted telemetry now reports through OTLP metrics instead of OTLP traces, giving instance operators cleaner gauges for user, project, and page counts.
- Instance logs are now stored in PostgreSQL only, with per-log-type retention so log tables no longer grow unbounded.
- Accessibility pass across the God Mode admin app: labels on icon-only buttons, clearer link descriptions, corrected tab order, and keyboard-reachable dismiss controls.
- Nginx now reads the correct
X-Forwarded-Forheader, so rate limiting and request logs see the real client IP instead of the proxy's. - Bot user emails are derived from your configured web URL instead of a hardcoded domain.
🐞 Bug fixes
- Fixed soft-deleted states reappearing in the UI after navigation, and work items linked to deleted states surfacing through the API.
- Fixed project creation assigning the project lead incorrectly, which could leave the lead off the project member list.
- Fixed work items created or updated through the REST API sending no notifications or emails.
- Fixed the
completed_attimestamp on work items being recalculated incorrectly; it is now a read-only field. - Fixed the comment quick-actions menu rendering as an empty popover when no actions were available.
- Removed profile preference changes from the work item activity feed, where they did not belong.
- Fixed sidebar pin/unpin state leaking between users in the same workspace, or silently failing to persist.
- Fixed API error responses returning a server error instead of the intended error payload.
- Fixed the project identifier field showing no message when the value contained unsupported characters.
- Workspace and company names now require at least one letter or digit, enforced in both the UI and the API, so symbol-only names are rejected.
- Fixed the work item more-options dropdown rendering without a visible border or shadow.
- Fixed low contrast on the onboarding tour close button.
- Fixed stale user data being mutated in place after a profile update, and cover image changes returning relative URLs.
- Fixed Safari and iOS crashes caused by the missing
requestIdleCallbackAPI; a fallback scheduler now handles idle work. - Fixed the all-in-one Docker image failing to start on Docker Engine 29.5 and later due to a malformed
VOLUMEdeclaration. - Fixed web, admin, and space Docker builds failing at the PostCSS step with a missing Tailwind plugin.
🛡️ Security
This release closes a large batch of coordinated security advisories. Self-hosted instances should upgrade.
Access control and tenant isolation
- Scoped cross-workspace resource lookups on project updates, bulk estimate points, and workspace user profiles to close an IDOR for project member role updates, which previously evaluated the target member's role rather than the requester's).
- Scoped bulk work item operations — cascade deletes, cycle and module assignment, sub-issue and relation creation — to the caller's workspace and project.
- Scoped estimate point creation and deletion to the caller's workspace and project.
- Enforced workspace membership on the public REST API asset endpoint and the entity-search endpoint, which previously let any authenticated user reach another workspace's assets or enumerate its members .
- Scoped asset reads and writes to project membership across file assets, issue attachments, and workspace assets.
- Scoped workspace-level cycle and module listings to projects the caller belongs to, so private project metadata is no longer enumerable.
- Scoped page version reads to the project in the request URL.
- Fixed the read-only branch of the project member permission check ignoring the project, which exposed project rosters and publish configuration to non-members.
- Applied the guest visibility restriction to the work item list-by-ID endpoint, which let guests read work items they did not author.
- Required project admin rights to activate or deactivate a project member; a guest could previously deactivate any member, including admins.
- Validated project IDs against the caller's workspace when bulk-adding project members.
Authentication and invitations
- Blocked sign-in for deactivated accounts, which were previously reactivated silently on every login, and corrected the workspace owner permission check.
- Blocked interactive logins for bot service accounts across every provider; bots remain usable through API tokens only.
- Rejected API key authentication for deactivated accounts, which could otherwise keep using previously issued tokens indefinitely.
- Rejected unverified OAuth provider emails on GitHub, Google, GitLab, and Gitea, closing an account takeover path via attacker-controlled self-hosted providers.
- Rate-limited magic-code verification and bounded per-token attempts, which previously allowed brute-forcing the six-digit code within its TTL.
- Removed the workspace invitation token from the unauthenticated invite endpoint and required the invited user to be signed in with the matching email before accepting.
- Stopped the public project invite endpoint from disclosing the invitee's email and token, and required a valid token plus authentication to accept or reject a project invite.
- Eliminated a race condition in instance admin signup that could create two instance admins.
Injection and content safety
- Sanitized comment and intake description HTML with
nh3on both the app and API layers, closing stored XSS. - Forced script-capable uploads such as SVG to download rather than render inline, closing stored XSS via attachments.
- Normalized link hrefs in the editor before the protocol check, so whitespace-prefixed
javascript:URLs can no longer slip through . - Added allowlists for
order_by,group_by, andsub_group_byquery parameters across work item, project, view, activity, and notification endpoints — including the unauthenticated public board — closing an ordering oracle over sensitive columns and unhandled 500s. - Sanitized XLSX export cells so user-supplied values beginning with
=are no longer written as live formulas, matching the existing CSV protection. - Hardened SSRF protection for webhook delivery, work item link unfurling, and OAuth avatar fetching: redirects are no longer followed, and the IP guard now blocks multicast, unspecified, CGNAT, and IPv4-in-IPv6 addresses.
- Bound workflow inputs to environment variables in the feature deployment GitHub Action, removing a shell injection path.
Secrets and deployment
- Removed the publicly known default
SECRET_KEYandLIVE_SERVER_SECRET_KEYfrom the all-in-one and CLI deployment manifests; a random key is now generated on first boot and persisted across restarts, including on upgrade from the old default. - Made the API token rate limit read-only so users can no longer raise their own limit, and stopped persisting API keys in plaintext — tokens are now stored as SHA-256 hashes and sensitive request headers are redacted before logging.
- Rebuilt the published Docker images against patched base packages to clear outstanding image scan findings.