⚠️ Breaking changes
- fix(mcp): declare containsAny operator for MULTI_SELECT filter schema (#26744) (#26748) by @PINYOPATTANAWASANPORN
- chore(security): pin adm-zip to 0.6.1 for every consumer (#27117) by @mabdullahabaid
- feat(sharing): reshape record sharing API and share panel (#27121) by @FelixMalfait
- feat(usage-limit): replace the limit meter with a usage unit (#27124) by @etiennejouan
- chore(security): upgrade nodemailer to v10 (#27164) by @mabdullahabaid
- chore(security): upgrade @electron/packager to v20 to drop extract-zip (#27185) by @mabdullahabaid
- refactor(ai): drop unused agent history repository registrations and errorDetails field (#27197) by @FelixMalfait
- chore: lift the AI SDK and drop the @ai-sdk/provider resolution (#27242) by @mabdullahabaid
- Remove the install apps onboarding step and rely on pre-installed apps (#27374) by @etiennejouan
- Track application upgrade as a queued job with progress (#27526) by @martmull
- sendInboxMessage takes workspaceMemberIds; one thread key is one conversation (#27615) by @FelixMalfait
✨ New features
- feat(enterprise): withhold repeat trials by server id, flag repeat cards for review (#25620) by @ijreilly
- feat: add new mixin guard (#26663) by @BOHEUS
- feat: allow aggregating rating fields (#26728) by @BOHEUS
- feat: admin-issued two-factor authentication recovery codes (#26933) by @abdulrahmancodes
- feat(teams): claim the Microsoft tenant for the workspace on connect (#27003) by @abdulrahmancodes
- feat(ai-chat): A/B test a data-first workspace setup prompt (#27050) by @etiennejouan
- feat(ai-chat): log one structured line per failed turn (#27102) by @etiennejouan
- feat(ai): let runAgent continue a conversation by thread key (#27135) by @FelixMalfait
- feat(usage): meter API complexity as the max record fields a query can return (#27155) by @etiennejouan
- feat(mcp): log the JSON-RPC method and tool name and trace tool generation (#27160) by @charlesBochet
- feat(ai): let agents and workflows propose tool calls for approval (#27169) by @FelixMalfait
- feat(permissions): add a workspace flag to turn off record share visibility gating (#27177) by @charlesBochet
- feat(workflow): human input instructions for agent steps, routed to the creator's inbox (#27190) by @FelixMalfait
- feat(api): select REST fields and cap the default field set (#27195) by @charlesBochet
- feat(ai): ask one question per call and step through every pending request (#27206) by @FelixMalfait
- feat(ai): unread badge on the inbox, with inbox state sent as record events (#27221) by @FelixMalfait
- feat(ai-chat): # to reference records, @ to bring teammates into a chat (#27234) by @FelixMalfait
- feat(workflow): waits as a first-class step outcome, Wait for Event node, agent waits (#27247) by @FelixMalfait
- feat(workflow): optional instructions on a form step, with variables (#27251) by @FelixMalfait
- feat(ai-chat): one @ menu for teammates and records, grouped by type (#27258) by @FelixMalfait
- feat(ai-chat): attach files pasted into the composer (#27273) by @etiennejouan
- feat(workflow): agent steps talk through the inbox like Send to Inbox (#27287) by @FelixMalfait
- feat(cli): introduce the Twenty command line (#27295) by @Weiko
- feat(teams): record inbound Teams messages as assistant requests (#27348) by @abdulrahmancodes
- feat(applications): show install and uninstall progress in the action buttons (#27357) by @martmull
- feat(cli): ship a yarn.lock with the app template (#27523) by @Weiko
- feat(slack): restrict the assistant to linked members, drop the default role (#27533) by @abdulrahmancodes
- feat(cli): add explicit object UI creation flags (#27602) by @Weiko
- feat(cli): offer object UI companions interactively (#27603) by @Weiko
- feat(teams): add the Teams assistant agent (#27654) by @abdulrahmancodes
- feat(teams): match a Teams sender to a workspace member by email (#27659) by @abdulrahmancodes
💅 Improvements & UX
- Forward typed events with React compatibility to front component workers (#26356) by @bosiraphael
- Stamp the requesting application on created call recordings (#26685) by @martmull
- AI: add effort levels to GPT-6 Luna and GPT-6 Sol (#26816) by @vladbisceanu
- [1/3] Let apps declare user-scoped application variables (#26868) by @ehconitin
- [2/3] Let each member set their own value of a user application variable (#26869) by @ehconitin
- Speed up CI ~1.8x (front 2.5x, server 1.4x) (#26876) by @neo773
- Add Sync Teams Transcript action that imports a transcript into a Call Recording (#26914) by @ehconitin
- Call recorder: replace the nightly pending-request cron with per-request follow-ups (#26917) by @ehconitin
- [3/3] Cache encrypted user application variable values (#26941) by @ehconitin
- Prevent concurrent workspace cache refreshes from restoring stale data (#26982) by @ehconitin
- Chat inbox: read cursor, unread line, done and snooze per member (#27046) by @FelixMalfait
- Migrate field input pickers and row menus (#27061) by @bosiraphael
- Migrate navigation menus and icon pickers (#27064) by @bosiraphael
- Migrate address and email autocompletes (#27065) by @bosiraphael
- Migrate record and tab dropdown menus (#27070) by @bosiraphael
- Snapshot the AuthPrincipalGuard and application target of every endpoint (#27082) by @prastoin
- Unify resizing with ResizeHandle (#27083) by @bosiraphael
- Bound AI agent steps of application workflow runs by the run roles (#27115) by @thomtrp
- Migrate phone country picker to Twenty UI (#27125) by @bosiraphael
- Migrate currency picker to Twenty UI (#27127) by @bosiraphael
- Migrate country selection in Twenty UI (#27128) by @bosiraphael
- Keep agent steps in one group and surface reasoning summaries (#27138) by @FelixMalfait
- Add share_record tool to the AI chat (#27144) by @FelixMalfait
- Update snapshot agentThread entity new auth coverage (#27145) by @prastoin
- Take the endpoint permission snapshot from the integration app (#27147) by @prastoin
- Keep the first keystroke typed into a dropdown search (#27148) by @bosiraphael
- Let buttons inside field inputs handle Enter (#27150) by @bosiraphael
- Share record selection state between table and board (#27166) by @FelixMalfait
- Select ranges from an anchor record in table and board (#27168) by @FelixMalfait
- Revert "perf(server): keep workspace cache versions live for 10 minutes before packing" (#27170) by @charlesBochet
- Select several chats in the inbox and act on them at once (#27171) by @FelixMalfait
- Remove AI chat inbox filter dropdown (#27172) by @FelixMalfait
- Select records in list views with cmd+click and shift+click (#27174) by @FelixMalfait
- Drag to select in the inbox (#27175) by @FelixMalfait
- Drag to reorder records in list views (#27187) by @FelixMalfait
- Show the information banner once in the AI chat inbox (#27188) by @FelixMalfait
- Right-click menu on list rows and inbox chats (#27189) by @FelixMalfait
- Clean up record selection, drag and drop, and list code (#27191) by @FelixMalfait
- Show empty list groups again once they have records (#27198) by @FelixMalfait
- Stop fading the board card drag source (#27203) by @FelixMalfait
- Replace hidden chat messages with system messages (#27207) by @FelixMalfait
- Load a member's chat inbox state with its threads (#27219) by @FelixMalfait
- Render chips and markdown in AI reasoning and approval summaries (#27231) by @FelixMalfait
- Serve AI history from workspace storage only and drop the core tables (#27235) by @FelixMalfait
- Show the last message and a Needs input status in the chat inbox (#27236) by @FelixMalfait
- Refuse administration operations to installed application tokens (#27241) by @prastoin
- Remove model-directed AI chat navigation (#27246) by @FelixMalfait
- Add isSystem to agents and workflows (#27252) by @FelixMalfait
- Add /agents list and agent page, and remove the agent settings pages (#27254) by @FelixMalfait
- Allow value in list field in validation rules (#27267) by @thomtrp
- Fall back to default icons for empty field icons in the validation rule editor (#27268) by @thomtrp
- Compare date fields with now by calendar day in validation rules (#27269) by @thomtrp
- Evaluate static default values when checking validation rules on a creation draft (#27270) by @thomtrp
- Upgrade Preact to 11 for React 19 refs (#27271) by @bosiraphael
- Support Avatar image loading in front component renderer (#27274) by @bosiraphael
- Fix input selection and Autocomplete (#27275) by @bosiraphael
- Restrict application-only endpoints to application callers (#27279) by @prastoin
- Report every violated validation rule message on a record write (#27282) by @thomtrp
- Validation rule form: preview with field section and status (#27283) by @thomtrp
- Fix duplicate rows after creating records in grouped tables (#27291) by @Weiko
- Allow object permissions while creating a role (#27292) by @Weiko
- Stop upgrade status gauges from stampeding the database (#27293) by @charlesBochet
- Use Gmail alias display name when sending from an alias (#27296) by @neo773
- Keep a validation rule's error field when the field is deactivated (#27297) by @thomtrp
- Invoke media event handlers through their own listeners (#27298) by @bosiraphael
- email alias manager preserve aliases even if they do not support syncing (#27299) by @neo773
- End workflow jobs quietly when their run was deleted (#27300) by @thomtrp
- Reuse ORM relation attachment helpers in validation rule evaluation (#27301) by @thomtrp
- Keep validation rules in sync with metadata events (#27302) by @thomtrp
- Fix 2.14 SyncCallRecordingRequestStatus on workspaces upgrading from 2.11 (#27303) by @prastoin
- Delete the runs of deleted core workflows and versions (#27304) by @thomtrp
- Allow removing workflows from an application manifest (#27309) by @thomtrp
- Build dependencies before running Knip (#27312) by @bosiraphael
- Ignore twenty-front-component-renderer workspace in knip (#27316) by @charlesBochet
- Return auth errors instead of 500 on auth-required route triggers (#27318) by @prastoin
- Require a label for upgrade commands in next version directories (#27319) by @FelixMalfait
- Remove agent evaluations and the agent Logs tab (#27320) by @FelixMalfait
- Skip logic function jobs whose application was uninstalled (#27321) by @martmull
- Add triggers to agents (1/3) (#27322) by @FelixMalfait
- Run agents from their triggers (2/3) (#27323) by @FelixMalfait
- Add a Triggers tab to the agent page (3/3) (#27324) by @FelixMalfait
- Report unhandled 500s to Sentry (#27325) by @prastoin
- Fix 2.38 and 2.43 system relation provisioning on objects without a table (#27326) by @prastoin
- Measure real queue wait and report delayed jobs apart from waiting ones (#27329) by @martmull
- Record status, timing, model, usage and creator on agent turns (#27336) by @FelixMalfait
- Record runAgent calls made without a thread (#27337) by @FelixMalfait
- Remove dead AI code and unused module imports (#27339) by @FelixMalfait
- Bill tool-call repairs in workflows, check queued attachments, report closed questions (#27340) by @FelixMalfait
- Organize Twenty UI components by family (#27354) by @bosiraphael
- Delete a core workflow's definition with it (#27359) by @thomtrp
- Confirm before deleting core workflows (#27360) by @thomtrp
- Stop reporting suspended-workspace refusals to Sentry (#27361) by @charlesBochet
- Hold a suspended workspace on its billing pages (#27362) by @charlesBochet
- Keep JSX handlers when a clone replaces a remote element ref (#27366) by @bosiraphael
- Add purchased credit grants and spend them after free credits (#27367) by @etiennejouan
- Align settings switches and complete feature flag labels (#27370) by @Bonapara
- Ground the scaffolded AGENTS.md in what the build enforces and fix dev:add output (#27371) by @ijreilly
- Hide thinking steps on agent messages sent before any user message (#27379) by @FelixMalfait
- Split front storybook tests into one job per scope (#27380) by @prastoin
- Complete ColorSample and Loader APIs (#27381) by @bosiraphael
- Move workflow step waits to a generic pendingWakeUp engine primitive (#27382) by @FelixMalfait
- Save which fields the record creation form shows (#27384) by @thomtrp
- Accept isActive when updating a page layout widget (#27389) by @thomtrp
- List every record form field with its visibility (#27390) by @thomtrp
- Add core index column icons and show visibility as tags (#27391) by @Bonapara
- Support bounded front component portals (#27392) by @bosiraphael
- Use node slots for icon presentation (#27393) by @bosiraphael
- Align Banner and InlineBanner feedback APIs (#27396) by @bosiraphael
- Let agents resume themselves; workflow AI steps wait for a callback (#27397) by @FelixMalfait
- Let agent triggers and runAgent calls wait on events and durations (#27403) by @FelixMalfait
- Expose the selected records filter to front components (#27404) by @charlesBochet
- Stop agent code from depending on workflow code (#27407) by @FelixMalfait
- Consolidate the 2.46 chat inbox upgrade commands (#27415) by @FelixMalfait
- Keep the AI engine free of workflow code and remove duplicated agent run code (#27416) by @FelixMalfait
- Use one atomic token bucket for every rate limit (#27418) by @FelixMalfait
- Read credits used this period through one ClickHouse reader (#27419) by @FelixMalfait
- Resolve how an object is shared in one place (#27420) by @FelixMalfait
- Move the calendar onto the shared record selection and drag provider (#27421) by @FelixMalfait
- Bring the inbox multi-select closer to the design (#27426) by @FelixMalfait
- Move code shared by modules out of pages (#27427) by @FelixMalfait
- Remove dead front code and duplicate tests (#27428) by @FelixMalfait
- Use existing shared helpers instead of local copies in front (#27429) by @FelixMalfait
- Inbox: chat subscriptions and server-side mentions (#27430) by @FelixMalfait
- Add a record page layout to the inbox and fit it to phones (#27431) by @FelixMalfait
- Untangle the front ui module from app and domain code (#27432) by @FelixMalfait
- Fix inverted front module dependencies (#27433) by @FelixMalfait
- Remove unused NestJS module imports in twenty-server (#27434) by @FelixMalfait
- Align front file names and folders with conventions (#27435) by @FelixMalfait
- Remove unused repository providers from server modules (#27436) by @FelixMalfait
- Stop side panel URL changes from re-rendering the record index (#27438) by @charlesBochet
- Provide each server service from a single module (#27441) by @FelixMalfait
- Inbox: assign chats to a member (#27442) by @FelixMalfait
- Remove module exports no importer uses (#27444) by @FelixMalfait
- Register business modules in ModulesModule instead of CoreEngineModule (#27445) by @FelixMalfait
- Remove module imports left unused by the previous cleanups (#27446) by @FelixMalfait
- Register business query hooks in ModulesModule (#27447) by @FelixMalfait
- Add support page to the website (#27459) by @abdulrahmancodes
- Hide private workflows' trigger items by core version id (#27474) by @thomtrp
- Show hidden fields on the record creation form (#27475) by @thomtrp
- Reveal hidden fields targeted by a validation error (#27476) by @thomtrp
- Look workflow versions up through their core workflow (#27477) by @thomtrp
- Move skeleton placeholders into twenty-ui (#27481) by @bosiraphael
- Allow grouping charts by Created by and report invalid chart configurations as user errors (#27482) by @charlesBochet
- Move the workflow status and automated trigger type enums to core (#27483) by @thomtrp
- Let navigation links point to a path inside the app (#27484) by @thomtrp
- Make Callout dismissal caller-owned (#27485) by @bosiraphael
- Add setup guide banner to the email channel page (#27487) by @neo773
- Align Tooltip shorthand and parts (#27488) by @bosiraphael
- Keep hidden creation form fields hidden and list only supported fields in the form settings (#27493) by @thomtrp
- Show workflow selection commands on the core Workflows index (#27494) by @Bonapara
- Reveal hidden fields targeted by a validation rule the server enforces (#27495) by @thomtrp
- Add loading positions to Button (#27496) by @bosiraphael
- Write the front component JSX runtime in TypeScript (#27497) by @bosiraphael
- Make typography composition explicit (#27504) by @bosiraphael
- Expose Collapsible parts (#27507) by @bosiraphael
- Block uninstalling a server route app from its owner workspace while installed elsewhere (#27510) by @martmull
- Monitor server routes left unreachable by their owner workspace (#27513) by @martmull
- Find a waiting tool call by its id instead of scanning recent messages (#27527) by @FelixMalfait
- Drop the canProposeToolCalls run capability (#27528) by @FelixMalfait
- Inline the single-use answer tool call hook and translate two chat errors (#27530) by @FelixMalfait
- Share one check for whether a workflow step still waits (#27531) by @FelixMalfait
- Close the ask_questions calls still waiting on an answer (#27532) by @FelixMalfait
- Format the workflow step wake-up handler (#27536) by @FelixMalfait
- Derive an agent run's turn author with its execution context (#27537) by @FelixMalfait
- Keep AI chat working for workspaces the 2.46 commands have not reached (#27538) by @FelixMalfait
- Only suspend paused agent steps that still wait, and release those of deleted runs (#27539) by @FelixMalfait
- Keep 2.46 instance commands safe for a rolling deploy and large tables (#27540) by @FelixMalfait
- Hand the agent executor the run's execution context (#27541) by @FelixMalfait
- Give the core workflow pages their own labels, icon and status options (#27543) by @thomtrp
- Require only the WORKFLOWS permission on the core workflow pages (#27545) by @thomtrp
- Validation rule form: design fixes and picker key ownership (#27546) by @thomtrp
- Record a run waiting on wait_for_* as waiting, not done (#27548) by @FelixMalfait
- Add the record creation form settings page (#27549) by @thomtrp
- Open the form settings from an Edit button on the record creation form (#27550) by @thomtrp
- Gate the AI chat inbox behind a feature flag (#27552) by @FelixMalfait
- Drop the ANSWERED agent run caller outcome (#27554) by @FelixMalfait
- Freeze the run spec the 2.46 suspend-paused-agent-steps command writes (#27555) by @FelixMalfait
- Validate the Delay step duration like Wait for Event (#27556) by @FelixMalfait
- Remove the unused addAgentChatThreadParticipants mutation (#27557) by @FelixMalfait
- Make the agent chat states plain states (#27558) by @FelixMalfait
- Close a thread's pending question through one function (#27559) by @FelixMalfait
- Run agent continuations without an ambient system context (#27560) by @FelixMalfait
- Pull the pure parts out of useAgentChatSubscription (#27561) by @FelixMalfait
- Show application workflows in the workflows list (#27562) by @thomtrp
- Remove dead Unsubscribe rewrite from the 2-46 assignee command (#27563) by @FelixMalfait
- Gate a background run's human-input tools in one place (#27564) by @FelixMalfait
- Derive chat loading and session start instead of syncing them in effects (#27565) by @FelixMalfait
- One workflow service for a waiting step (#27568) by @FelixMalfait
- Open the first inbox chat with a redirect instead of an effect (#27569) by @FelixMalfait
- Compute the inbox counts on the server over all of a member's chats (#27570) by @FelixMalfait
- Stay on an inbox chat that leaves the filtered list by coming back to the inbox (#27571) by @FelixMalfait
- Replace the seven AI chat inbox mutations with one batched mutation (#27576) by @FelixMalfait
- Represent a paused agent run as a pending wake-up (#27579) by @FelixMalfait
- Leave rich text rules to the server until it computes the markdown (#27582) by @thomtrp
- Complete Field and Slider anatomy (#27583) by @bosiraphael
- Align Section and CommandBlock composition (#27584) by @bosiraphael
- Enable the core workflow pages on new workspaces (#27585) by @thomtrp
- Subscribe to Teams transcripts in Microsoft Graph when a connection is added (#27586) by @ehconitin
- Expose Checkbox and Switch parts (#27587) by @bosiraphael
- Align input and textarea integration (#27589) by @bosiraphael
- Expose complete Popover parts (#27590) by @bosiraphael
- Bound HTTP Request step duration and payload size (#27593) by @prastoin
- Import Teams transcripts when Microsoft Graph notifies that they are ready (#27594) by @ehconitin
- Compile Is not on number and currency filters to neq (#27601) by @charlesBochet
- Fix stale metadata in SSE events (#27604) by @bosiraphael
- Complete AlertDialog parts (#27605) by @bosiraphael
- Expose complete Dialog parts (#27606) by @bosiraphael
- Batch seat prorations and credit upgrades for invoice-paying subscriptions (#27607) by @ijreilly
- Bound outbound HTTP requests by default (#27608) by @prastoin
- Complete Button and IconButton contracts (#27609) by @bosiraphael
- Add optional Redis cache prefix for clustered Redis (#27610) by @Weiko
- Show "Worked for X" instead of step count in AI chat thinking summary (#27611) by @FelixMalfait
- Stabilize navigation tooltip story (#27612) by @bosiraphael
- Make agent run caller refs opaque to the engine (#27613) by @FelixMalfait
- AI chat: a new chat has its thread id from the start (#27617) by @FelixMalfait
- Stop the Create command from loading while the record creation form is open (#27618) by @thomtrp
- AI chat: apply participant event rows instead of refetching (#27619) by @FelixMalfait
- Keep spaces typed in navigation folder names (#27620) by @FelixMalfait
- Show saved role permissions on the member Permissions tab (#27623) by @FelixMalfait
- Fix oversized icon in InlineBanner (#27624) by @FelixMalfait
- Fix error toast when renaming a view from the Options menu (#27625) by @FelixMalfait
- Lighter shortcut hint in buttons and new snooze/done icons in the AI inbox (#27626) by @FelixMalfait
- Allow a zero usage limit (#27627) by @ijreilly
- Restore agent.evaluationInputs where the original 2.46 drop already ran (#27628) by @FelixMalfait
- Let app page layout manifests set isFirstTabPinned (#27629) by @martmull
- Show validation rules the server refused a record with in the creation form (#27630) by @thomtrp
- Complete Card composition (#27632) by @bosiraphael
- Use UTC when a Create Calendar Event step has no time zone (#27634) by @FelixMalfait
- Preserve native Breadcrumb links (#27636) by @bosiraphael
- Fix changing a workflow node into an Iterator (#27639) by @FelixMalfait
- Expose Avatar parts and explicit interaction (#27640) by @bosiraphael
- Stabilize Dropdown trailing action story (#27641) by @bosiraphael
- Store the page layout target in the side panel navigation item (#27645) by @FelixMalfait
- Derive AvatarGroup overflow (#27646) by @bosiraphael
- Document S3 self-hosting setup and forward S3 credentials in Compose (#27647) by @martmull
- Simplify Chip content and interaction (#27648) by @bosiraphael
- Drop the unused workflow object read in useCoreObjectsCommands (#27650) by @thomtrp
- Document that AI file attachments need a public SERVER_URL (#27656) by @etiennejouan
- Explain missing call recording summary when transcript is empty or failed (#27658) by @ehconitin
- Last contact: spend fewer calls of the shared rate limit (#27662) by @martmull
- Fix Fathom imports that silently lose data (#27663) by @ehconitin
- Retry Twenty and Fathom rate limits in the Fathom app (#27667) by @ehconitin
- Simplify Tag and Status composition (#27681) by @bosiraphael
- Keep ListItem presentational (#27683) by @bosiraphael
- Clarify SettingsRow control integration (#27686) by @bosiraphael
- Only suggest the Send to Inbox step in the Form warning when that step is enabled (#27687) by @FelixMalfait
- Stop duplicating Gmail sent emails when sync fetches them again (#27688) by @neo773
- Map job title in the prefilled Quick Lead workflow (#27692) by @FelixMalfait
- Keep usage-limit reads compatible during rollout (#27694) by @FelixMalfait
- Let application workflows add a command menu item (#27698) by @thomtrp
- Keep a wake-up until what it resumes is handed off (#27704) by @FelixMalfait
- Register the wait on an answer before the call can be answered (#27705) by @FelixMalfait
- Clarify ImageInput file selection (#27706) by @bosiraphael
- Replace Accounts with App preferences behind a feature flag (#27708) by @ehconitin
- Add app preferences pages for Gmail, Google Calendar, Outlook and IMAP (#27709) by @ehconitin
- Call recorder: spread the upcoming calendar events sweep across workspaces (#27716) by @ehconitin
- Convert workflow rich text to BlockNote in the workflow record actions (#27721) by @charlesBochet
- Move the AI chat stall watchdog into the subscription it watches (#27722) by @FelixMalfait
🐛 Bug fixes
- fix(auth): make login tokens single use (#26614) by @addyCooks
- fix(front): open field links with noopener to prevent reverse tabnabbing (#26643) by @addyCooks
- fix(shared): round currency filter amounts to whole micros (#26690) by @breken-ai
- fix(shared): check currencyCode for currency code emptiness filters (#26691) by @breken-ai
- fix(cache-lock): renew the lock lease while withLock runs and fence every release (#26709) by @addyCooks
- fix(front): suppress Safari 'Cancelled' abort errors as snackbar notifications (#26740) by @okxint
- fix(auth): validate login password before processing workspace invitation (#26657) (#26742) by @PINYOPATTANAWASANPORN
- fix(front): move abbreviated numbers to the next suffix when rounding reaches 1000 (#26880) by @sarmah-rup
- fix(front): preserve null currency amountMicros in CSV export (#26929) by @pranav440
- fix(rich-text): keep selection after image autosave (#26969) by @waelantar
- fix: make tokenBucketThrottleOrThrow atomic for every caller (#27012) by @abdulrahmancodes
- fix(tools): report tool crashes to Sentry once, from dispatch (#27038) by @etiennejouan
- fix(front): preserve multi-record selection in side-panel components (#27041) by @waelantar
- fix(ai): navigate_app takes explicit record and view ids (#27108) by @FelixMalfait
- fix(frontend): honor wildcard and missing Accept headers (#27119) by @FelixMalfait
- fix(server): preserve OAuth-only caller reach in application targeting (#27120) by @Weiko
- fix(workflow): stop reporting queued triggers for inactive versions to Sentry (#27137) by @thomtrp
- fix(front): stop GraphQLPlayground story failing on Monaco worker load errors (#27139) by @thomtrp
- fix(workflow): align core visibility cell and add back arrow to versions panel (#27143) by @thomtrp
- fix(calendar): stop re-saving unchanged calendar events and participants on sync (#27151) by @charlesBochet
- fix(ai): human input bugs found reviewing the approval feature (#27194) by @FelixMalfait
- fix(ai-chat): write each assistant checkpoint in one transaction (#27213) by @FelixMalfait
- fix: refresh role caches after workspace member removal (#27226) by @glitchedmob
- fix(api): isEmptyArray filter ignores boolean value and misses NULL-stored arrays (#27232) by @okxint
- fix(domain): serve frontend when its host is under public domain (#27248) by @YadurajManu
- fix(workflow): a form step waits on its run, not in a conversation (#27250) by @FelixMalfait
- fix(twenty-sdk): only remove dist/sdk before bundling declarations (#27261) by @PINYOPATTANAWASANPORN
- fix(usage-limit): only a row on the default's period replaces it (#27272) by @etiennejouan
- fix(mcp): mark database read tools read-only in direct mode (#27310) by @UditSinghChauhan
- fix(usage): throw when the recurring charge lookup fails instead of charging every fee again (#27315) by @etiennejouan
- fix(mcp): stop requiring defaulted fields in create tool schemas (#27345) by @UditSinghChauhan
- fix(email): render links inline in the email thread message body (#27350) by @ijreilly
- fix(server): unblock the server typecheck that times out on every PR (#27351) by @FelixMalfait
- fix(usage-limit): keep the limits form off scopes only an operator can set (#27373) by @etiennejouan
- fix(api): make neq match NULL rows when compared against a real value (#27399) by @Atharva0222
- fix(cli): color doctor status labels (#27411) by @Weiko
- fix(cli): default unnamed login connections to default (#27412) by @Weiko
- fix(cli): omit deletedAt from default data columns (#27413) by @Weiko
- fix(cli): guide app changes through plan and apply (#27414) by @Weiko
- fix(cli): make built binary executable (#27422) by @Weiko
- fix(cli): improve command output readability (#27423) by @Weiko
- fix(cli): simplify connection hints and planning messages (#27425) by @Weiko
- fix(auth): trust the identity provider's email for SSO sign-ups and show the real SAML/OIDC URLs (#27486) by @ijreilly
- fix(cli): install the pinned CLI in generated app CI (#27518) by @Weiko
- fix(cli): explain the Node requirement instead of crashing on unsupported Node versions (#27520) by @Weiko
- fix(cli): create a fallback yarn.lock during app init (#27651) by @Weiko
- fix(cli): avoid deprecated widget positions in app init (#27660) by @Weiko
⚡ Performance
- perf(permissions): resolve settings permission flags from the workspace cache (#27109) by @FelixMalfait
- perf(roles): batch role relation resolvers and add a getRole query (#27118) by @FelixMalfait
- perf(cache): map user workspaces to members in the member cache (#27131) by @FelixMalfait
- perf(server): build universal identifier lookups once per cache rebuild (#27134) by @charlesBochet
- perf(rich-text): parse markdown with marked instead of BlockNote's jsdom pipeline (#27142) by @charlesBochet
- perf(server): keep workspace cache versions live for 10 minutes before packing (#27149) by @charlesBochet
- perf(server): memoize credentialed CORS origins on their config inputs (#27154) by @charlesBochet
- perf(mcp): generate database tool input schemas as plain JSON Schema (#27158) by @charlesBochet
- perf(api): stop expanding timeline activities in depth relations (#27162) by @charlesBochet
- perf(api): drop NULLS FIRST from the id pagination tiebreaker (#27176) by @charlesBochet
- perf(ai-chat): send each stream chunk's RPUSH and EXPIRE together (#27211) by @FelixMalfait
- perf(ai-chat): spot changed chat messages by reference instead of deep comparison (#27212) by @FelixMalfait
- perf(ai-history): check workspace history readiness once per process (#27215) by @FelixMalfait
- perf(ai-chat): share one access check across the steps and tool calls of a short window (#27216) by @FelixMalfait
- perf(server): bump metadata version only when object or field metadata changes (#27265) by @charlesBochet
🔧 Developer & API
- Accept enum string values in twenty-sdk inputs (#27193) by @prastoin
- AI catalog steward: refresh stale self-host smart default (gpt-5.6-sol@high → gpt-6-astra@low) (#27240) by @twenty-pr-author
- last-contact: drop the calendar cron and cut API calls under the shared rate limit (#27313) by @martmull
- Clean up CodeEditorHeader API (#27376) by @bosiraphael
- Normalize Separator API (#27383) by @bosiraphael
- Run workflow, API and trigger agent turns through one engine runner (#27385) by @FelixMalfait
- Normalize DirectionProvider API (#27387) by @bosiraphael
- Normalize VisuallyHidden API (#27388) by @bosiraphael
- Send workflow chat messages through an engine inbox API (#27405) by @FelixMalfait
- Regenerate the metadata GraphQL types (#27542) by @FelixMalfait
- Regenerate the SDK metadata client (#27544) by @FelixMalfait
- Set up the inbox state of threads created through the record API (#27553) by @FelixMalfait
- Tag the application API rate-limit counter with the workspace id (#27643) by @martmull
- Revert "Tag the application API rate-limit counter with the workspace id" (#27652) by @martmull
- Log the app and workspace when an application hits the API rate limit (#27655) by @martmull
🏗️ Internal changes (37)
- docs(self-host): suggest a URL-safe generator for the Postgres password (#26759) by @omlahore
- refactor(orm): remove query builder mutations in favor of repository writes (#27104) by @FelixMalfait
- refactor(permissions): one way to read object, field and flag permissions (#27114) by @FelixMalfait
- test(workflow): wait for statuses recomputed by the status job (#27122) by @FelixMalfait
- refactor(orm): fold the lean write path into performMutation (#27129) by @FelixMalfait
- refactor(shared): expose universal identifier validation (#27140) by @Weiko
- revert(slack): remove per-channel rules for the assistant (#26016) (#27156) by @abdulrahmancodes
- test(mcp): snapshot database tool input schemas from tools/list (#27161) by @charlesBochet
- chore(security): bump undici to fixed versions everywhere (#27165) by @mabdullahabaid
- chore(security): bump @fastify/busboy to 3.2.2 (#27173) by @mabdullahabaid
- chore(security): bump engine.io to 6.6.11 (#27178) by @mabdullahabaid
- chore(security): bump @grpc/grpc-js to 1.14.5 (#27179) by @mabdullahabaid
- chore(security): bump moment to 2.31.0 (#27181) by @mabdullahabaid
- chore(security): bump markdown-it to 14.3.2 (#27182) by @mabdullahabaid
- chore(security): bump dompurify to 3.4.16 (#27183) by @mabdullahabaid
- chore(security): pin js-yaml 5.x to 5.4.2 for @verdaccio/config (#27184) by @mabdullahabaid
- refactor(ai): simplify and unify AI chat code on server and front (#27192) by @FelixMalfait
- chore(security): bump next to 16.3.8 (#27201) by @mabdullahabaid
- refactor(cache): derive role target and resolver name caches from flat entity maps (#27204) by @charlesBochet
- chore(security): lift module-federation to 2.9.2 and drop two dts-plugin pins (#27209) by @mabdullahabaid
- chore: rewrite //resolutions to document only current entries (#27217) by @mabdullahabaid
- chore(security): lift mintlify to 4.2.956 and drop the puppeteer pin (#27220) by @mabdullahabaid
- chore(teams): move to twenty-ui 2.45 and align the Twenty SDKs (#27243) by @mabdullahabaid
- test(workflow): fix tests broken by moving form steps off conversations (#27253) by @FelixMalfait
- refactor(server): remove the no-op ORMEntityMetadatas workspace cache (#27266) by @charlesBochet
- chore(usage-limit): remove the webhook rate limit and execution quota feature flags (#27278) by @etiennejouan
- refactor(usage-limit): charge usage rows through one call that debits then records (#27286) by @etiennejouan
- chore(logic-function): remove the IS_LOGIC_FUNCTION_PREBUILT_MODE_ENABLED feature flag (#27307) by @martmull
- docs(apps): add a good practices page for app development at scale (#27347) by @martmull
- test(cli): verify workspace and packaged installations in CI (#27424) by @Weiko
- chore(cli): check the twenty package before publishing and bump it to 0.4.0 (#27489) by @Weiko
- docs(cli): describe installing the twenty package from npm (#27492) by @Weiko
- docs(sdk): point to the twenty CLI package from the SDK README (#27512) by @Weiko
- ci(cli): run the CLI's lint, typecheck and unit tests (#27519) by @Weiko
- chore(security): bump proxy-addr to 2.0.8 (#27522) by @mabdullahabaid
- chore(security): bump shell-quote to 1.12.0 (#27524) by @mabdullahabaid
- docs(apps): move the good practices page to Getting Started (#27685) by @martmull
🎉 New contributors
- @PINYOPATTANAWASANPORN made their first contribution in #26742
- @glitchedmob made their first contribution in #27226
- @okxint made their first contribution in #27232
- @YadurajManu made their first contribution in #27248
- @omlahore made their first contribution in #26759
- @sarmah-rup made their first contribution in #26880
- @pranav440 made their first contribution in #26929
Full changelog (431 PRs)
- feat(enterprise): withhold repeat trials by server id, flag repeat cards for review (#25620) by @ijreilly
- Forward typed events with React compatibility to front component workers (#26356) by @bosiraphael
- fix(auth): make login tokens single use (#26614) by @addyCooks
- fix(front): open field links with noopener to prevent reverse tabnabbing (#26643) by @addyCooks
- feat: add new mixin guard (#26663) by @BOHEUS
- Stamp the requesting application on created call recordings (#26685) by @martmull
- fix(shared): round currency filter amounts to whole micros (#26690) by @breken-ai
- fix(shared): check currencyCode for currency code emptiness filters (#26691) by @breken-ai
- fix(cache-lock): renew the lock lease while withLock runs and fence every release (#26709) by @addyCooks
- feat: allow aggregating rating fields (#26728) by @BOHEUS
- fix(front): suppress Safari 'Cancelled' abort errors as snackbar notifications (#26740) by @okxint
- fix(auth): validate login password before processing workspace invitation (#26657) (#26742) by @PINYOPATTANAWASANPORN
- fix(mcp): declare containsAny operator for MULTI_SELECT filter schema (#26744) (#26748) by @PINYOPATTANAWASANPORN
- docs(self-host): suggest a URL-safe generator for the Postgres password (#26759) by @omlahore
- AI: add effort levels to GPT-6 Luna and GPT-6 Sol (#26816) by @vladbisceanu
- [1/3] Let apps declare user-scoped application variables (#26868) by @ehconitin
- [2/3] Let each member set their own value of a user application variable (#26869) by @ehconitin
- Speed up CI ~1.8x (front 2.5x, server 1.4x) (#26876) by @neo773
- fix(front): move abbreviated numbers to the next suffix when rounding reaches 1000 (#26880) by @sarmah-rup
- Add Sync Teams Transcript action that imports a transcript into a Call Recording (#26914) by @ehconitin
- Call recorder: replace the nightly pending-request cron with per-request follow-ups (#26917) by @ehconitin
- fix(front): preserve null currency amountMicros in CSV export (#26929) by @pranav440
- feat: admin-issued two-factor authentication recovery codes (#26933) by @abdulrahmancodes
- [3/3] Cache encrypted user application variable values (#26941) by @ehconitin
- fix(rich-text): keep selection after image autosave (#26969) by @waelantar
- Prevent concurrent workspace cache refreshes from restoring stale data (#26982) by @ehconitin
- feat(teams): claim the Microsoft tenant for the workspace on connect (#27003) by @abdulrahmancodes
- fix: make tokenBucketThrottleOrThrow atomic for every caller (#27012) by @abdulrahmancodes
- fix(tools): report tool crashes to Sentry once, from dispatch (#27038) by @etiennejouan
- fix(front): preserve multi-record selection in side-panel components (#27041) by @waelantar
- Chat inbox: read cursor, unread line, done and snooze per member (#27046) by @FelixMalfait
- feat(ai-chat): A/B test a data-first workspace setup prompt (#27050) by @etiennejouan
- Migrate field input pickers and row menus (#27061) by @bosiraphael
- Migrate navigation menus and icon pickers (#27064) by @bosiraphael
- Migrate address and email autocompletes (#27065) by @bosiraphael
- Migrate record and tab dropdown menus (#27070) by @bosiraphael
- Snapshot the AuthPrincipalGuard and application target of every endpoint (#27082) by @prastoin
- Unify resizing with ResizeHandle (#27083) by @bosiraphael
- feat(ai-chat): log one structured line per failed turn (#27102) by @etiennejouan
- refactor(orm): remove query builder mutations in favor of repository writes (#27104) by @FelixMalfait
- fix(ai): navigate_app takes explicit record and view ids (#27108) by @FelixMalfait
- perf(permissions): resolve settings permission flags from the workspace cache (#27109) by @FelixMalfait
- refactor(permissions): one way to read object, field and flag permissions (#27114) by @FelixMalfait
- Bound AI agent steps of application workflow runs by the run roles (#27115) by @thomtrp
- chore(security): pin adm-zip to 0.6.1 for every consumer (#27117) by @mabdullahabaid
- perf(roles): batch role relation resolvers and add a getRole query (#27118) by @FelixMalfait
- fix(frontend): honor wildcard and missing Accept headers (#27119) by @FelixMalfait
- fix(server): preserve OAuth-only caller reach in application targeting (#27120) by @Weiko
- feat(sharing): reshape record sharing API and share panel (#27121) by @FelixMalfait
- test(workflow): wait for statuses recomputed by the status job (#27122) by @FelixMalfait
- feat(usage-limit): replace the limit meter with a usage unit (#27124) by @etiennejouan
- Migrate phone country picker to Twenty UI (#27125) by @bosiraphael
- chore: bump version to 2.46.0 (#27126) by @twenty-pr
- Migrate currency picker to Twenty UI (#27127) by @bosiraphael
- Migrate country selection in Twenty UI (#27128) by @bosiraphael
- refactor(orm): fold the lean write path into performMutation (#27129) by @FelixMalfait
- perf(cache): map user workspaces to members in the member cache (#27131) by @FelixMalfait
- perf(server): build universal identifier lookups once per cache rebuild (#27134) by @charlesBochet
- feat(ai): let runAgent continue a conversation by thread key (#27135) by @FelixMalfait
- fix(workflow): stop reporting queued triggers for inactive versions to Sentry (#27137) by @thomtrp
- Keep agent steps in one group and surface reasoning summaries (#27138) by @FelixMalfait
- fix(front): stop GraphQLPlayground story failing on Monaco worker load errors (#27139) by @thomtrp
- refactor(shared): expose universal identifier validation (#27140) by @Weiko
- perf(rich-text): parse markdown with marked instead of BlockNote's jsdom pipeline (#27142) by @charlesBochet
- fix(workflow): align core visibility cell and add back arrow to versions panel (#27143) by @thomtrp
- Add share_record tool to the AI chat (#27144) by @FelixMalfait
- Update snapshot agentThread entity new auth coverage (#27145) by @prastoin
- Take the endpoint permission snapshot from the integration app (#27147) by @prastoin
- Keep the first keystroke typed into a dropdown search (#27148) by @bosiraphael
- perf(server): keep workspace cache versions live for 10 minutes before packing (#27149) by @charlesBochet
- Let buttons inside field inputs handle Enter (#27150) by @bosiraphael
- fix(calendar): stop re-saving unchanged calendar events and participants on sync (#27151) by @charlesBochet
- perf(server): memoize credentialed CORS origins on their config inputs (#27154) by @charlesBochet
- feat(usage): meter API complexity as the max record fields a query can return (#27155) by @etiennejouan
- revert(slack): remove per-channel rules for the assistant (#26016) (#27156) by @abdulrahmancodes
- perf(mcp): generate database tool input schemas as plain JSON Schema (#27158) by @charlesBochet
- feat(mcp): log the JSON-RPC method and tool name and trace tool generation (#27160) by @charlesBochet
- test(mcp): snapshot database tool input schemas from tools/list (#27161) by @charlesBochet
- perf(api): stop expanding timeline activities in depth relations (#27162) by @charlesBochet
- chore(security): upgrade nodemailer to v10 (#27164) by @mabdullahabaid
- chore(security): bump undici to fixed versions everywhere (#27165) by @mabdullahabaid
- Share record selection state between table and board (#27166) by @FelixMalfait
- chore: sync AI model catalog (#27167) by @github-actions
- Select ranges from an anchor record in table and board (#27168) by @FelixMalfait
- feat(ai): let agents and workflows propose tool calls for approval (#27169) by @FelixMalfait
- Revert "perf(server): keep workspace cache versions live for 10 minutes before packing" (#27170) by @charlesBochet
- Select several chats in the inbox and act on them at once (#27171) by @FelixMalfait
- Remove AI chat inbox filter dropdown (#27172) by @FelixMalfait
- chore(security): bump @fastify/busboy to 3.2.2 (#27173) by @mabdullahabaid
- Select records in list views with cmd+click and shift+click (#27174) by @FelixMalfait
- Drag to select in the inbox (#27175) by @FelixMalfait
- perf(api): drop NULLS FIRST from the id pagination tiebreaker (#27176) by @charlesBochet
- feat(permissions): add a workspace flag to turn off record share visibility gating (#27177) by @charlesBochet
- chore(security): bump engine.io to 6.6.11 (#27178) by @mabdullahabaid
- chore(security): bump @grpc/grpc-js to 1.14.5 (#27179) by @mabdullahabaid
- chore(security): bump moment to 2.31.0 (#27181) by @mabdullahabaid
- chore(security): bump markdown-it to 14.3.2 (#27182) by @mabdullahabaid
- chore(security): bump dompurify to 3.4.16 (#27183) by @mabdullahabaid
- chore(security): pin js-yaml 5.x to 5.4.2 for @verdaccio/config (#27184) by @mabdullahabaid
- chore(security): upgrade @electron/packager to v20 to drop extract-zip (#27185) by @mabdullahabaid
- Drag to reorder records in list views (#27187) by @FelixMalfait
- Show the information banner once in the AI chat inbox (#27188) by @FelixMalfait
- Right-click menu on list rows and inbox chats (#27189) by @FelixMalfait
- feat(workflow): human input instructions for agent steps, routed to the creator's inbox (#27190) by @FelixMalfait
- Clean up record selection, drag and drop, and list code (#27191) by @FelixMalfait
- refactor(ai): simplify and unify AI chat code on server and front (#27192) by @FelixMalfait
- Accept enum string values in twenty-sdk inputs (#27193) by @prastoin
- fix(ai): human input bugs found reviewing the approval feature (#27194) by @FelixMalfait
- feat(api): select REST fields and cap the default field set (#27195) by @charlesBochet
- refactor(ai): drop unused agent history repository registrations and errorDetails field (#27197) by @FelixMalfait
- Show empty list groups again once they have records (#27198) by @FelixMalfait
- chore(security): bump next to 16.3.8 (#27201) by @mabdullahabaid
- Stop fading the board card drag source (#27203) by @FelixMalfait
- refactor(cache): derive role target and resolver name caches from flat entity maps (#27204) by @charlesBochet
- feat(ai): ask one question per call and step through every pending request (#27206) by @FelixMalfait
- Replace hidden chat messages with system messages (#27207) by @FelixMalfait
- chore(security): lift module-federation to 2.9.2 and drop two dts-plugin pins (#27209) by @mabdullahabaid
- perf(ai-chat): send each stream chunk's RPUSH and EXPIRE together (#27211) by @FelixMalfait
- perf(ai-chat): spot changed chat messages by reference instead of deep comparison (#27212) by @FelixMalfait
- fix(ai-chat): write each assistant checkpoint in one transaction (#27213) by @FelixMalfait
- perf(ai-history): check workspace history readiness once per process (#27215) by @FelixMalfait
- perf(ai-chat): share one access check across the steps and tool calls of a short window (#27216) by @FelixMalfait
- chore: rewrite //resolutions to document only current entries (#27217) by @mabdullahabaid
- Load a member's chat inbox state with its threads (#27219) by @FelixMalfait
- chore(security): lift mintlify to 4.2.956 and drop the puppeteer pin (#27220) by @mabdullahabaid
- feat(ai): unread badge on the inbox, with inbox state sent as record events (#27221) by @FelixMalfait
- fix: refresh role caches after workspace member removal (#27226) by @glitchedmob
- Render chips and markdown in AI reasoning and approval summaries (#27231) by @FelixMalfait
- fix(api): isEmptyArray filter ignores boolean value and misses NULL-stored arrays (#27232) by @okxint
- feat(ai-chat): # to reference records, @ to bring teammates into a chat (#27234) by @FelixMalfait
- Serve AI history from workspace storage only and drop the core tables (#27235) by @FelixMalfait
- Show the last message and a Needs input status in the chat inbox (#27236) by @FelixMalfait
- chore: sync AI model catalog (#27237) by @github-actions
- AI catalog steward: refresh stale self-host smart default (gpt-5.6-sol@high → gpt-6-astra@low) (#27240) by @twenty-pr-author
- Refuse administration operations to installed application tokens (#27241) by @prastoin
- chore: lift the AI SDK and drop the @ai-sdk/provider resolution (#27242) by @mabdullahabaid
- chore(teams): move to twenty-ui 2.45 and align the Twenty SDKs (#27243) by @mabdullahabaid
- Remove model-directed AI chat navigation (#27246) by @FelixMalfait
- feat(workflow): waits as a first-class step outcome, Wait for Event node, agent waits (#27247) by @FelixMalfait
- fix(domain): serve frontend when its host is under public domain (#27248) by @YadurajManu
- fix(workflow): a form step waits on its run, not in a conversation (#27250) by @FelixMalfait
- feat(workflow): optional instructions on a form step, with variables (#27251) by @FelixMalfait
- Add isSystem to agents and workflows (#27252) by @FelixMalfait
- test(workflow): fix tests broken by moving form steps off conversations (#27253) by @FelixMalfait
- Add /agents list and agent page, and remove the agent settings pages (#27254) by @FelixMalfait
- feat(ai-chat): one @ menu for teammates and records, grouped by type (#27258) by @FelixMalfait
- fix(twenty-sdk): only remove dist/sdk before bundling declarations (#27261) by @PINYOPATTANAWASANPORN
- chore: sync AI model catalog (#27262) by @github-actions
- perf(server): bump metadata version only when object or field metadata changes (#27265) by @charlesBochet
- refactor(server): remove the no-op ORMEntityMetadatas workspace cache (#27266) by @charlesBochet
- Allow value in list field in validation rules (#27267) by @thomtrp
- Fall back to default icons for empty field icons in the validation rule editor (#27268) by @thomtrp
- Compare date fields with now by calendar day in validation rules (#27269) by @thomtrp
- Evaluate static default values when checking validation rules on a creation draft (#27270) by @thomtrp
- Upgrade Preact to 11 for React 19 refs (#27271) by @bosiraphael
- fix(usage-limit): only a row on the default's period replaces it (#27272) by @etiennejouan
- feat(ai-chat): attach files pasted into the composer (#27273) by @etiennejouan
- Support Avatar image loading in front component renderer (#27274) by @bosiraphael
- Fix input selection and Autocomplete (#27275) by @bosiraphael
- chore(usage-limit): remove the webhook rate limit and execution quota feature flags (#27278) by @etiennejouan
- Restrict application-only endpoints to application callers (#27279) by @prastoin
- Report every violated validation rule message on a record write (#27282) by @thomtrp
- Validation rule form: preview with field section and status (#27283) by @thomtrp
- refactor(usage-limit): charge usage rows through one call that debits then records (#27286) by @etiennejouan
- feat(workflow): agent steps talk through the inbox like Send to Inbox (#27287) by @FelixMalfait
- Fix duplicate rows after creating records in grouped tables (#27291) by @Weiko
- Allow object permissions while creating a role (#27292) by @Weiko
- Stop upgrade status gauges from stampeding the database (#27293) by @charlesBochet
- feat(cli): introduce the Twenty command line (#27295) by @Weiko
- Use Gmail alias display name when sending from an alias (#27296) by @neo773
- Keep a validation rule's error field when the field is deactivated (#27297) by @thomtrp
- Invoke media event handlers through their own listeners (#27298) by @bosiraphael
- email alias manager preserve aliases even if they do not support syncing (#27299) by @neo773
- End workflow jobs quietly when their run was deleted (#27300) by @thomtrp
- Reuse ORM relation attachment helpers in validation rule evaluation (#27301) by @thomtrp
- Keep validation rules in sync with metadata events (#27302) by @thomtrp
- Fix 2.14 SyncCallRecordingRequestStatus on workspaces upgrading from 2.11 (#27303) by @prastoin
- Delete the runs of deleted core workflows and versions (#27304) by @thomtrp
- chore(logic-function): remove the IS_LOGIC_FUNCTION_PREBUILT_MODE_ENABLED feature flag (#27307) by @martmull
- Allow removing workflows from an application manifest (#27309) by @thomtrp
- fix(mcp): mark database read tools read-only in direct mode (#27310) by @UditSinghChauhan
- Build dependencies before running Knip (#27312) by @bosiraphael
- last-contact: drop the calendar cron and cut API calls under the shared rate limit (#27313) by @martmull
- fix(usage): throw when the recurring charge lookup fails instead of charging every fee again (#27315) by @etiennejouan
- Ignore twenty-front-component-renderer workspace in knip (#27316) by @charlesBochet
- Return auth errors instead of 500 on auth-required route triggers (#27318) by @prastoin
- Require a label for upgrade commands in next version directories (#27319) by @FelixMalfait
- Remove agent evaluations and the agent Logs tab (#27320) by @FelixMalfait
- Skip logic function jobs whose application was uninstalled (#27321) by @martmull
- Add triggers to agents (1/3) (#27322) by @FelixMalfait
- Run agents from their triggers (2/3) (#27323) by @FelixMalfait
- Add a Triggers tab to the agent page (3/3) (#27324) by @FelixMalfait
- Report unhandled 500s to Sentry (#27325) by @prastoin
- Fix 2.38 and 2.43 system relation provisioning on objects without a table (#27326) by @prastoin
- Measure real queue wait and report delayed jobs apart from waiting ones (#27329) by @martmull
- Record status, timing, model, usage and creator on agent turns (#27336) by @FelixMalfait
- Record runAgent calls made without a thread (#27337) by @FelixMalfait
- Remove dead AI code and unused module imports (#27339) by @FelixMalfait
- Bill tool-call repairs in workflows, check queued attachments, report closed questions (#27340) by @FelixMalfait
- chore: sync AI model catalog (#27343) by @github-actions
- fix(mcp): stop requiring defaulted fields in create tool schemas (#27345) by @UditSinghChauhan
- docs(apps): add a good practices page for app development at scale (#27347) by @martmull
- feat(teams): record inbound Teams messages as assistant requests (#27348) by @abdulrahmancodes
- fix(email): render links inline in the email thread message body (#27350) by @ijreilly
- fix(server): unblock the server typecheck that times out on every PR (#27351) by @FelixMalfait
- Organize Twenty UI components by family (#27354) by @bosiraphael
- feat(applications): show install and uninstall progress in the action buttons (#27357) by @martmull
- Delete a core workflow's definition with it (#27359) by @thomtrp
- Confirm before deleting core workflows (#27360) by @thomtrp
- Stop reporting suspended-workspace refusals to Sentry (#27361) by @charlesBochet
- Hold a suspended workspace on its billing pages (#27362) by @charlesBochet
- Keep JSX handlers when a clone replaces a remote element ref (#27366) by @bosiraphael
- Add purchased credit grants and spend them after free credits (#27367) by @etiennejouan
- Align settings switches and complete feature flag labels (#27370) by @Bonapara
- Ground the scaffolded AGENTS.md in what the build enforces and fix dev:add output (#27371) by @ijreilly
- fix(usage-limit): keep the limits form off scopes only an operator can set (#27373) by @etiennejouan
- Remove the install apps onboarding step and rely on pre-installed apps (#27374) by @etiennejouan
- Clean up CodeEditorHeader API (#27376) by @bosiraphael
- Hide thinking steps on agent messages sent before any user message (#27379) by @FelixMalfait
- Split front storybook tests into one job per scope (#27380) by @prastoin
- Complete ColorSample and Loader APIs (#27381) by @bosiraphael
- Move workflow step waits to a generic pendingWakeUp engine primitive (#27382) by @FelixMalfait
- Normalize Separator API (#27383) by @bosiraphael
- Save which fields the record creation form shows (#27384) by @thomtrp
- Run workflow, API and trigger agent turns through one engine runner (#27385) by @FelixMalfait
- Normalize DirectionProvider API (#27387) by @bosiraphael
- Normalize VisuallyHidden API (#27388) by @bosiraphael
- Accept isActive when updating a page layout widget (#27389) by @thomtrp
- List every record form field with its visibility (#27390) by @thomtrp
- Add core index column icons and show visibility as tags (#27391) by @Bonapara
- Support bounded front component portals (#27392) by @bosiraphael
- Use node slots for icon presentation (#27393) by @bosiraphael
- Align Banner and InlineBanner feedback APIs (#27396) by @bosiraphael
- Let agents resume themselves; workflow AI steps wait for a callback (#27397) by @FelixMalfait
- fix(api): make neq match NULL rows when compared against a real value (#27399) by @Atharva0222
- Let agent triggers and runAgent calls wait on events and durations (#27403) by @FelixMalfait
- Expose the selected records filter to front components (#27404) by @charlesBochet
- Send workflow chat messages through an engine inbox API (#27405) by @FelixMalfait
- Stop agent code from depending on workflow code (#27407) by @FelixMalfait
- fix(cli): color doctor status labels (#27411) by @Weiko
- fix(cli): default unnamed login connections to default (#27412) by @Weiko
- fix(cli): omit deletedAt from default data columns (#27413) by @Weiko
- fix(cli): guide app changes through plan and apply (#27414) by @Weiko
- Consolidate the 2.46 chat inbox upgrade commands (#27415) by @FelixMalfait
- Keep the AI engine free of workflow code and remove duplicated agent run code (#27416) by @FelixMalfait
- Use one atomic token bucket for every rate limit (#27418) by @FelixMalfait
- Read credits used this period through one ClickHouse reader (#27419) by @FelixMalfait
- Resolve how an object is shared in one place (#27420) by @FelixMalfait
- Move the calendar onto the shared record selection and drag provider (#27421) by @FelixMalfait
- fix(cli): make built binary executable (#27422) by @Weiko
- fix(cli): improve command output readability (#27423) by @Weiko
- test(cli): verify workspace and packaged installations in CI (#27424) by @Weiko
- fix(cli): simplify connection hints and planning messages (#27425) by @Weiko
- Bring the inbox multi-select closer to the design (#27426) by @FelixMalfait
- Move code shared by modules out of pages (#27427) by @FelixMalfait
- Remove dead front code and duplicate tests (#27428) by @FelixMalfait
- Use existing shared helpers instead of local copies in front (#27429) by @FelixMalfait
- Inbox: chat subscriptions and server-side mentions (#27430) by @FelixMalfait
- Add a record page layout to the inbox and fit it to phones (#27431) by @FelixMalfait
- Untangle the front ui module from app and domain code (#27432) by @FelixMalfait
- Fix inverted front module dependencies (#27433) by @FelixMalfait
- Remove unused NestJS module imports in twenty-server (#27434) by @FelixMalfait
- Align front file names and folders with conventions (#27435) by @FelixMalfait
- Remove unused repository providers from server modules (#27436) by @FelixMalfait
- Stop side panel URL changes from re-rendering the record index (#27438) by @charlesBochet
- Provide each server service from a single module (#27441) by @FelixMalfait
- Inbox: assign chats to a member (#27442) by @FelixMalfait
- Remove module exports no importer uses (#27444) by @FelixMalfait
- Register business modules in ModulesModule instead of CoreEngineModule (#27445) by @FelixMalfait
- Remove module imports left unused by the previous cleanups (#27446) by @FelixMalfait
- Register business query hooks in ModulesModule (#27447) by @FelixMalfait
- Add support page to the website (#27459) by @abdulrahmancodes
- chore: sync AI model catalog (#27473) by @github-actions
- Hide private workflows' trigger items by core version id (#27474) by @thomtrp
- Show hidden fields on the record creation form (#27475) by @thomtrp
- Reveal hidden fields targeted by a validation error (#27476) by @thomtrp
- Look workflow versions up through their core workflow (#27477) by @thomtrp
- Move skeleton placeholders into twenty-ui (#27481) by @bosiraphael
- Allow grouping charts by Created by and report invalid chart configurations as user errors (#27482) by @charlesBochet
- Move the workflow status and automated trigger type enums to core (#27483) by @thomtrp
- Let navigation links point to a path inside the app (#27484) by @thomtrp
- Make Callout dismissal caller-owned (#27485) by @bosiraphael
- fix(auth): trust the identity provider's email for SSO sign-ups and show the real SAML/OIDC URLs (#27486) by @ijreilly
- Add setup guide banner to the email channel page (#27487) by @neo773
- Align Tooltip shorthand and parts (#27488) by @bosiraphael
- chore(cli): check the twenty package before publishing and bump it to 0.4.0 (#27489) by @Weiko
- docs(cli): describe installing the twenty package from npm (#27492) by @Weiko
- Keep hidden creation form fields hidden and list only supported fields in the form settings (#27493) by @thomtrp
- Show workflow selection commands on the core Workflows index (#27494) by @Bonapara
- Reveal hidden fields targeted by a validation rule the server enforces (#27495) by @thomtrp
- Add loading positions to Button (#27496) by @bosiraphael
- Write the front component JSX runtime in TypeScript (#27497) by @bosiraphael
- Make typography composition explicit (#27504) by @bosiraphael
- i18n - website translations (#27506) by @github-actions
- Expose Collapsible parts (#27507) by @bosiraphael
- Block uninstalling a server route app from its owner workspace while installed elsewhere (#27510) by @martmull
- docs(sdk): point to the twenty CLI package from the SDK README (#27512) by @Weiko
- Monitor server routes left unreachable by their owner workspace (#27513) by @martmull
- i18n - website translations (#27514) by @github-actions
- fix(cli): install the pinned CLI in generated app CI (#27518) by @Weiko
- ci(cli): run the CLI's lint, typecheck and unit tests (#27519) by @Weiko
- fix(cli): explain the Node requirement instead of crashing on unsupported Node versions (#27520) by @Weiko
- chore(security): bump proxy-addr to 2.0.8 (#27522) by @mabdullahabaid
- feat(cli): ship a yarn.lock with the app template (#27523) by @Weiko
- chore(security): bump shell-quote to 1.12.0 (#27524) by @mabdullahabaid
- Track application upgrade as a queued job with progress (#27526) by @martmull
- Find a waiting tool call by its id instead of scanning recent messages (#27527) by @FelixMalfait
- Drop the canProposeToolCalls run capability (#27528) by @FelixMalfait
- Inline the single-use answer tool call hook and translate two chat errors (#27530) by @FelixMalfait
- Share one check for whether a workflow step still waits (#27531) by @FelixMalfait
- Close the ask_questions calls still waiting on an answer (#27532) by @FelixMalfait
- feat(slack): restrict the assistant to linked members, drop the default role (#27533) by @abdulrahmancodes
- Format the workflow step wake-up handler (#27536) by @FelixMalfait
- Derive an agent run's turn author with its execution context (#27537) by @FelixMalfait
- Keep AI chat working for workspaces the 2.46 commands have not reached (#27538) by @FelixMalfait
- Only suspend paused agent steps that still wait, and release those of deleted runs (#27539) by @FelixMalfait
- Keep 2.46 instance commands safe for a rolling deploy and large tables (#27540) by @FelixMalfait
- Hand the agent executor the run's execution context (#27541) by @FelixMalfait
- Regenerate the metadata GraphQL types (#27542) by @FelixMalfait
- Give the core workflow pages their own labels, icon and status options (#27543) by @thomtrp
- Regenerate the SDK metadata client (#27544) by @FelixMalfait
- Require only the WORKFLOWS permission on the core workflow pages (#27545) by @thomtrp
- Validation rule form: design fixes and picker key ownership (#27546) by @thomtrp
- Record a run waiting on wait_for_* as waiting, not done (#27548) by @FelixMalfait
- Add the record creation form settings page (#27549) by @thomtrp
- Open the form settings from an Edit button on the record creation form (#27550) by @thomtrp
- Gate the AI chat inbox behind a feature flag (#27552) by @FelixMalfait
- Set up the inbox state of threads created through the record API (#27553) by @FelixMalfait
- Drop the ANSWERED agent run caller outcome (#27554) by @FelixMalfait
- Freeze the run spec the 2.46 suspend-paused-agent-steps command writes (#27555) by @FelixMalfait
- Validate the Delay step duration like Wait for Event (#27556) by @FelixMalfait
- Remove the unused addAgentChatThreadParticipants mutation (#27557) by @FelixMalfait
- Make the agent chat states plain states (#27558) by @FelixMalfait
- Close a thread's pending question through one function (#27559) by @FelixMalfait
- Run agent continuations without an ambient system context (#27560) by @FelixMalfait
- Pull the pure parts out of useAgentChatSubscription (#27561) by @FelixMalfait
- Show application workflows in the workflows list (#27562) by @thomtrp
- Remove dead Unsubscribe rewrite from the 2-46 assignee command (#27563) by @FelixMalfait
- Gate a background run's human-input tools in one place (#27564) by @FelixMalfait
- Derive chat loading and session start instead of syncing them in effects (#27565) by @FelixMalfait
- One workflow service for a waiting step (#27568) by @FelixMalfait
- Open the first inbox chat with a redirect instead of an effect (#27569) by @FelixMalfait
- Compute the inbox counts on the server over all of a member's chats (#27570) by @FelixMalfait
- Stay on an inbox chat that leaves the filtered list by coming back to the inbox (#27571) by @FelixMalfait
- Replace the seven AI chat inbox mutations with one batched mutation (#27576) by @FelixMalfait
- chore: sync AI model catalog (#27577) by @github-actions
- Represent a paused agent run as a pending wake-up (#27579) by @FelixMalfait
- Leave rich text rules to the server until it computes the markdown (#27582) by @thomtrp
- Complete Field and Slider anatomy (#27583) by @bosiraphael
- Align Section and CommandBlock composition (#27584) by @bosiraphael
- Enable the core workflow pages on new workspaces (#27585) by @thomtrp
- Subscribe to Teams transcripts in Microsoft Graph when a connection is added (#27586) by @ehconitin
- Expose Checkbox and Switch parts (#27587) by @bosiraphael
- Align input and textarea integration (#27589) by @bosiraphael
- Expose complete Popover parts (#27590) by @bosiraphael
- Bound HTTP Request step duration and payload size (#27593) by @prastoin
- Import Teams transcripts when Microsoft Graph notifies that they are ready (#27594) by @ehconitin
- Compile Is not on number and currency filters to neq (#27601) by @charlesBochet
- feat(cli): add explicit object UI creation flags (#27602) by @Weiko
- feat(cli): offer object UI companions interactively (#27603) by @Weiko
- Fix stale metadata in SSE events (#27604) by @bosiraphael
- Complete AlertDialog parts (#27605) by @bosiraphael
- Expose complete Dialog parts (#27606) by @bosiraphael
- Batch seat prorations and credit upgrades for invoice-paying subscriptions (#27607) by @ijreilly
- Bound outbound HTTP requests by default (#27608) by @prastoin
- Complete Button and IconButton contracts (#27609) by @bosiraphael
- Add optional Redis cache prefix for clustered Redis (#27610) by @Weiko
- Show "Worked for X" instead of step count in AI chat thinking summary (#27611) by @FelixMalfait
- Stabilize navigation tooltip story (#27612) by @bosiraphael
- Make agent run caller refs opaque to the engine (#27613) by @FelixMalfait
- sendInboxMessage takes workspaceMemberIds; one thread key is one conversation (#27615) by @FelixMalfait
- AI chat: a new chat has its thread id from the start (#27617) by @FelixMalfait
- Stop the Create command from loading while the record creation form is open (#27618) by @thomtrp
- AI chat: apply participant event rows instead of refetching (#27619) by @FelixMalfait
- Keep spaces typed in navigation folder names (#27620) by @FelixMalfait
- Show saved role permissions on the member Permissions tab (#27623) by @FelixMalfait
- Fix oversized icon in InlineBanner (#27624) by @FelixMalfait
- Fix error toast when renaming a view from the Options menu (#27625) by @FelixMalfait
- Lighter shortcut hint in buttons and new snooze/done icons in the AI inbox (#27626) by @FelixMalfait
- Allow a zero usage limit (#27627) by @ijreilly
- Restore agent.evaluationInputs where the original 2.46 drop already ran (#27628) by @FelixMalfait
- Let app page layout manifests set isFirstTabPinned (#27629) by @martmull
- Show validation rules the server refused a record with in the creation form (#27630) by @thomtrp
- Complete Card composition (#27632) by @bosiraphael
- Use UTC when a Create Calendar Event step has no time zone (#27634) by @FelixMalfait
- Preserve native Breadcrumb links (#27636) by @bosiraphael
- Fix changing a workflow node into an Iterator (#27639) by @FelixMalfait
- Expose Avatar parts and explicit interaction (#27640) by @bosiraphael
- Stabilize Dropdown trailing action story (#27641) by @bosiraphael
- Tag the application API rate-limit counter with the workspace id (#27643) by @martmull
- Store the page layout target in the side panel navigation item (#27645) by @FelixMalfait
- Derive AvatarGroup overflow (#27646) by @bosiraphael
- Document S3 self-hosting setup and forward S3 credentials in Compose (#27647) by @martmull
- Simplify Chip content and interaction (#27648) by @bosiraphael
- Drop the unused workflow object read in useCoreObjectsCommands (#27650) by @thomtrp
- fix(cli): create a fallback yarn.lock during app init (#27651) by @Weiko
- Revert "Tag the application API rate-limit counter with the workspace id" (#27652) by @martmull
- feat(teams): add the Teams assistant agent (#27654) by @abdulrahmancodes
- Log the app and workspace when an application hits the API rate limit (#27655) by @martmull
- Document that AI file attachments need a public SERVER_URL (#27656) by @etiennejouan
- Explain missing call recording summary when transcript is empty or failed (#27658) by @ehconitin
- feat(teams): match a Teams sender to a workspace member by email (#27659) by @abdulrahmancodes
- fix(cli): avoid deprecated widget positions in app init (#27660) by @Weiko
- Last contact: spend fewer calls of the shared rate limit (#27662) by @martmull
- Fix Fathom imports that silently lose data (#27663) by @ehconitin
- i18n - translations (#27665) by @github-actions
- Retry Twenty and Fathom rate limits in the Fathom app (#27667) by @ehconitin
- i18n - translations (#27669) by @github-actions
- chore: sync AI model catalog (#27675) by @github-actions
- Simplify Tag and Status composition (#27681) by @bosiraphael
- Keep ListItem presentational (#27683) by @bosiraphael
- docs(apps): move the good practices page to Getting Started (#27685) by @martmull
- Clarify SettingsRow control integration (#27686) by @bosiraphael
- Only suggest the Send to Inbox step in the Form warning when that step is enabled (#27687) by @FelixMalfait
- Stop duplicating Gmail sent emails when sync fetches them again (#27688) by @neo773
- Map job title in the prefilled Quick Lead workflow (#27692) by @FelixMalfait
- Keep usage-limit reads compatible during rollout (#27694) by @FelixMalfait
- Let application workflows add a command menu item (#27698) by @thomtrp
- Keep a wake-up until what it resumes is handed off (#27704) by @FelixMalfait
- Register the wait on an answer before the call can be answered (#27705) by @FelixMalfait
- Clarify ImageInput file selection (#27706) by @bosiraphael
- Replace Accounts with App preferences behind a feature flag (#27708) by @ehconitin
- Add app preferences pages for Gmail, Google Calendar, Outlook and IMAP (#27709) by @ehconitin
- i18n - translations (#27711) by @github-actions
- Call recorder: spread the upcoming calendar events sweep across workspaces (#27716) by @ehconitin
- i18n - translations (#27717) by @github-actions
- i18n - translations (#27719) by @github-actions
- Convert workflow rich text to BlockNote in the workflow record actions (#27721) by @charlesBochet
- Move the AI chat stall watchdog into the subscription it watches (#27722) by @FelixMalfait
- i18n - translations (#27728) by @github-actions
- i18n - translations (#27730) by @github-actions
Full Changelog: twenty/v2.45.0...twenty/v2.46.0