v1.1.1
- Add Braid site attribution link to footer - by @andrew-boyd (0eddc)
- Parse ISO dates with a year before 1000 - by @Osamaali313 in https://github.com/formkit/tempo/issues/85 (371de)
- format: Use Intl.Locale to merge hourCycle into locale with existing Unicode extensions - by @crossi-dev in https://github.com/formkit/tempo/issues/68 and https://github.com/formkit/tempo/issues/84 (22050)
- yearDays: Return whole days regardless of time zone - by @pcbeingused333 in https://github.com/formkit/tempo/issues/87 (b6d8a)
v3.3.16
3.3.16 is a security release. It fixes a race in the collaboration socket that could expose and write to pads the user was not allowed to open, and picks up the ueberDB MSSQL fix. Upgrade as soon as you can.
- Collaboration — every socket message now stays bound to the pad it was authorized for (GHSA-c36r-65p6-q3m9, #8458). The earlier fix for GHSA-6mcx-x5h6-rpw2 only pinned the target pad for USER_CHANGES. Chat, history (CHANGESET_REQ), saved revisions, pad options and pad deletion still read the pad from the socket's session when they ran. A second CLIENT_READY on the same socket rewrote that session before its own access check. A message authorized for one pad could then run against another, which leaked the other pad's text, history and chat and let chat messages and saved revisions be written into it, including on pads the user could only view. CLIENT_READY now changes the session only after access is granted, and each message carries the pad and access mode it was authorized with. Reported by @leograntquinn-crypto.
- Database — ueberdb2 6.1.19 (#8444). Fixes SQL injection in the MSSQL driver's bulk writes (GHSA-xmqq-59rx-x7pf). Only installs using
"dbType": "mssql"are affected.
- The default-content author test no longer depends on the local
defaultPadTextsetting (#8445). - The Docker workflow now records the release version (#8456).
- Dependency updates, including undici 8.12.4, mssql 12.7.14, entities 9.0.0, surrealdb 2.2.2 and resolve 1.22.14.
v3.3.16
3.3.16 is a security release. It fixes a race in the collaboration socket that could expose and write to pads the user was not allowed to open, and picks up the ueberDB MSSQL fix. Upgrade as soon as you can.
- Collaboration — every socket message now stays bound to the pad it was authorized for (GHSA-c36r-65p6-q3m9, #8458). The earlier fix for GHSA-6mcx-x5h6-rpw2 only pinned the target pad for USER_CHANGES. Chat, history (CHANGESET_REQ), saved revisions, pad options and pad deletion still read the pad from the socket's session when they ran. A second CLIENT_READY on the same socket rewrote that session before its own access check. A message authorized for one pad could then run against another, which leaked the other pad's text, history and chat and let chat messages and saved revisions be written into it, including on pads the user could only view. CLIENT_READY now changes the session only after access is granted, and each message carries the pad and access mode it was authorized with. Reported by @leograntquinn-crypto.
- Database — ueberdb2 6.1.19 (#8444). Fixes SQL injection in the MSSQL driver's bulk writes (GHSA-xmqq-59rx-x7pf). Only installs using
"dbType": "mssql"are affected.
- The default-content author test no longer depends on the local
defaultPadTextsetting (#8445). - The Docker workflow now records the release version (#8456).
- Dependency updates, including undici 8.12.4, mssql 12.7.14, entities 9.0.0, surrealdb 2.2.2 and resolve 1.22.14.
🗂️ Release v1.4.0
Univer 1.4.0 adds Office attachment workflows, shape merging in Slides, richer pivot filtering, and GETPIVOTDATA. This release also separates product-specific comment integrations and introduces several package and API migrations.
Preserve embedded OLE files when working with Office documents, with actions to preview, download, rename, and delete attachments. Supported Office files can also be converted into independent online documents when the application provides the required collaboration, attachment, and exchange services.
Office export keeps the original embedded file by default. Applications can request the current confirmed version of a converted online document instead:
import { ExchangeFormat } from '@univerjs-pro/exchange-client';
const file = await univerAPI.exportSheetByUnitIdAsync(
unitId,
ExchangeFormat.XLSX,
undefined,
{ oleAttachmentSource: 'online' }
);
The server must support this export option. Cross-type Office previews require the corresponding existing product UI module; conversion and preview use the existing drawing and exchange plugins.
Combine supported selections with Union, Combine, Fragment, Intersect, and Subtract. The operations create new shape geometry and support undo/redo and collaboration. The first selected object determines the primary formatting and the subtraction direction.
Pivot tables and pivot charts can combine different filter categories on the same field after enabling Allow multiple filters per field. The option is off by default.
Fixed date filters also support whole-day comparison, so timestamps from the same day can match without requiring identical time values.
await pivotTable.setOptions({ allowMultipleFilters: true });
await pivotTable.setDateFilter(fieldId, {
operator: univerAPI.Enum.ST_PivotFilterOperatorEnum.dateEqual,
expected: dateSerial,
useWholeDay: true,
});
Disabling multiple filters while combined filters are active clears the report's filters and the corresponding shared slicer/timeline selections. The UI asks for confirmation.
Use GETPIVOTDATA to retrieve aggregated values from a visible PivotTable report:
=GETPIVOTDATA("Sales",$A$3,"Region","East")
The initial implementation reads the visible report from a single-cell anchor, searching up to 200 rows below and 50 columns to its right.
Docs now respects paragraph settings that allow Latin words to break across lines. A new control in paragraph settings makes this behavior editable and supports inherited and mixed paragraph states.
Image and chart comment Facade integrations have moved out of the generic shape-thread-comment Facade into four new packages:
| Package | Integration |
|---|---|
@univerjs-pro/sheets-drawing-thread-comment |
Images in Sheets |
@univerjs-pro/sheets-chart-thread-comment |
Charts in Sheets |
@univerjs-pro/docs-drawing-thread-comment |
Images in Docs |
@univerjs-pro/docs-chart-thread-comment |
Charts in Docs |
These packages provide the existing createCommentAsync, getComments, and listCommentsAsync methods for their respective objects. Generic FShape comments remain in @univerjs-pro/shape-thread-comment.
- Formulas: Improve array-spill invalidation, shared-formula dependencies, and recalculation after worksheet-reference changes. Writing cell values through
setValue/setValuesnow persists removal of the replaced formula. - Sheets: Preserve imported XLSX table differential formats and inherited font sizes while editing; improve merged-cell rendering, autofill after scrolling, and sheet renaming.
- UI and mobile: Compact the two-row Ribbon before moving groups into More, improve keyboard navigation, and enforce permissions consistently in mobile controls and dialogs.
- Collaboration: Reconnect after Chrome page freeze/resume, include filter/table models during snapshot formula replay, and authorize comment-only changesets with the Unit Comment permission.
- Rendering and performance: Defer SmartArt reference-data initialization, correct spacing for charts with empty titles, preserve LaTeX formula backgrounds, and improve dark-mode editing panels.
Keep all @univerjs/* and @univerjs-pro/* dependencies used by your application on the same version.
Applications using image or chart comment methods must add the corresponding package and its Facade import. For example, in an existing Sheets application:
import { UniverSheetsDrawingThreadCommentPlugin } from '@univerjs-pro/sheets-drawing-thread-comment';
import '@univerjs-pro/sheets-drawing-thread-comment/facade';
univer.registerPlugin(UniverSheetsDrawingThreadCommentPlugin);
Apply the same pattern to the other integrations in the table above. Retain the generic shape-comment integration when using FShape comments.
The @univerjs-pro/ink/facade entry has been removed. Board ink methods now belong to FBoard:
-import '@univerjs-pro/ink/facade';
+import '@univerjs-pro/boards/facade';
Import Board ink enums and IBoardInkFacadeInsertOptions from @univerjs-pro/boards/facade as well.
Use dedicated /worker entry points for worker-side plugins. For example:
-import { UniverRPCWorkerThreadPlugin } from '@univerjs/rpc';
-import { UniverSheetsPivotChartWorkerPlugin } from '@univerjs-pro/sheets-pivot-chart';
+import { UniverRPCWorkerThreadPlugin } from '@univerjs/rpc/worker';
+import { UniverSheetsPivotChartWorkerPlugin } from '@univerjs-pro/sheets-pivot-chart/worker';
The retained root exports for worker-only APIs are deprecated in 1.4.0, with removal planned for 1.5.0 as described below. Docs workers can now register UniverDocsWorkerPlugin from @univerjs/docs/worker instead of calling startDocsLayoutWorker directly. Worker presets have been updated to use the dedicated entries.
Redundant version/schemaVersion fields have been removed from affected resource payloads, including document formulas, external references, Slides tables, and Slides fonts. Update custom serializers, validators, and imports of the removed schema-version constants.
For example, a document-formula resource is now:
-const resource = { schemaVersion: 1, formulas: {} };
+const resource = { formulas: {} };
- Applying worksheet/range protection or setting worksheet permission points clears the affected workbook's undo/redo history. Review workflows that apply protection after editing.
- Deployments using the new OLE, shape-merge, or pivot-filter workflows need corresponding server-side support. Use an OLE-capable drawing model and compatible native exchange runtime at the import/export boundary.
- The new table differential-format import requires matching Sheets, Sheets Numfmt, and native exchange components. Historical snapshots are not rewritten automatically; re-import the original XLSX when possible to adopt the new format handling.
- Update self-hosted collaboration runtimes to receive the snapshot-replay and comment-permission fixes.
Removal of the deprecated Worker root exports is planned for 1.5.0, tracked in #8079 and its companion update. These exports are still available in 1.4.0, so custom Worker entry scripts can migrate before the next release.
Import the following APIs from their package's /worker entry instead of its root:
| Package | API moving to /worker |
|---|---|
@univerjs/rpc |
UniverRPCWorkerThreadPlugin |
@univerjs/rpc-node |
UniverRPCNodeWorkerPlugin |
@univerjs/sheets-formula |
UniverRemoteSheetsFormulaPlugin |
@univerjs/sheets-filter-ui |
UniverSheetsFilterUIWorkerPlugin |
@univerjs/engine-render |
DocumentLayoutSession |
@univerjs-pro/bases |
UniverRemoteBasesPlugin |
@univerjs-pro/bases-dashboard |
UniverRemoteBaseDashboardPlugin |
@univerjs-pro/sheets-pivot-chart |
UniverSheetsPivotChartWorkerPlugin |
The two manual startup helpers also need migration:
- Replace
startDocsLayoutWorkerfrom@univerjs/docswithUniverDocsWorkerPluginfrom@univerjs/docs/worker. - Replace
startPdfPageThumbnailWorkerfrom@univerjs-pro/pdfs-uiwithUniverPdfsUIWorkerPluginfrom@univerjs-pro/pdfs-ui/worker.
For a Docs Worker entry:
import { Univer } from '@univerjs/core';
import { UniverDocsWorkerPlugin } from '@univerjs/docs/worker';
const univer = new Univer();
univer.registerPlugin(UniverDocsWorkerPlugin);
For a PDF thumbnail Worker entry:
import { UniverPdfsUIWorkerPlugin } from '@univerjs-pro/pdfs-ui/worker';
import { Univer } from '@univerjs/core';
const univer = new Univer();
univer.registerPlugin(UniverPdfsUIWorkerPlugin);
Apply these changes inside the Worker entry files. The built-in Worker presets in 1.4.0 already use the dedicated entry points.
Full changelog: v1.3.1…v1.4.0
mobx-react-plugin@1.0.2
b433c95720ced6f987d2379913933d49517cb48f#4770 Thanks @kubk! - Faster transforms: files that cannot contain components, hooks or flows are skipped without being parsed, and the Vite plugin only generates code when something changed. Code generation options for the Vite plugin now go inbabel.generatorOpts.
v4.13.17
- fix(cookie): match the
__Secure-and__Host-prefixes case-insensitively in https://github.com/honojs/hono/pull/5608 - fix(utils/url): do not match a query key across separators in https://github.com/honojs/hono/pull/5607
- fix(etag,pretty-json): cancel the discarded response body in https://github.com/honojs/hono/pull/5606
- fix(client): detect the JSON media type with whitespace before a parameter in https://github.com/honojs/hono/pull/5609
- fix(timing): honor a precision of 0 in
setMetricin https://github.com/honojs/hono/pull/5363 - fix(utils/mime,ssg): match media types case-insensitively in https://github.com/honojs/hono/pull/5449
- fix(timing): escape double quotes and backslashes in Server-Timing descriptions in https://github.com/honojs/hono/pull/5478
- fix(etag): preserve commas within quoted entity tags in https://github.com/honojs/hono/pull/5353
- fix(accepts): preserve exact media type quality over subtype wildcards in https://github.com/honojs/hono/pull/5427
- fix(cookie): match the
__Secure-and__Host-prefixes case-insensitively inCookieConstraintin https://github.com/honojs/hono/pull/5611 - fix(jsx): add the CSP nonce to all scripts generated by
ErrorBoundaryin https://github.com/honojs/hono/pull/5430 - fix(ssg): do not reuse created directories across
toSSGruns in https://github.com/honojs/hono/pull/5381 - fix(aws-lambda): sanitize non-ASCII header values in API Gateway v2 events in https://github.com/honojs/hono/pull/5483
- fix(jsx): escape element and object attribute values in https://github.com/honojs/hono/pull/5512
- fix(jsx): do not render ref objects as attributes in https://github.com/honojs/hono/pull/5615
- fix(factory): keep independent return types for nine handlers in https://github.com/honojs/hono/pull/5618
Full Changelog: https://github.com/honojs/hono/compare/v4.13.16...v4.13.17
Astryx v0.7.11
Astryx 0.7.11 — all @astryxdesign/* packages ship at this version.
OLD_VERSION=0.7.10 # replace with the Core version your project uses today
npm install @astryxdesign/core@0.7.11 @astryxdesign/cli@0.7.11 # plus every other @astryxdesign/* package you use, at 0.7.11
npx @astryxdesign/cli upgrade --from "$OLD_VERSION" --apply --path .
- Under a finger (a coarse primary pointer, on any touch device), Popover grows out of its trigger, wide before tall, with its edge held on the trigger, and shrinks back into the trigger when it closes. The growth plays the theme's
--duration-medium-min(in the Storybook theme, the step nearest iOS's 206 ms growth) with its entrance easing, and the shrink plays its exit duration and easing, on the compositor. A close during the growth, or an open during the shrink, turns back from where the popover is. With reduced motion it cross-fades in and out, opacity only, in 200 ms or less. A fine primary pointer (a mouse) keeps its entrance. A tap that lands while it grows is ignored, and a pan started then scrolls nothing. The shrink plays on the layer runtime's exit copy, of which Popover is the first user. The growth starts in the next animation frame, before that frame paints, so the opening tap does no extra layout. (#8187) DropdownMenuSubMenuacceptsdelayandhideDelay, in milliseconds, the same optionsTooltip,HoverCardandTopNavMenuhave.delayis how long a hovering pointer waits before the flyout opens (default 150), andhideDelayis how long the flyout stays after the pointer leaves (default 200). The defaults match today's timing, so nothing changes unless you pass them. Keyboard focus and touch never wait. (#10298)Timestamptakes atimezoneIDprop naming the IANA zone its absolute formats render in, such as'UTC'or'America/Los_Angeles'. An explicit zone renders identically on the server and the client, so a server-rendered absolute time no longer depends on the server's zone and hydrates without a mismatch. Omit it (or pass'local') to keep the viewer's own zone, relative formats' visible text ignores it (configuredtooltipEntriesrows still follow it), and an unknown identifier warns once in development and falls back to the viewer's zone. (#9789)
- Animated layout glides now use the theme's
--duration-mediuminstead of--duration-medium-min: 300 ms instead of 225 ms in the Neutral theme, and 410 ms instead of 310 ms with no theme. Their move curve, Reduce Motion behavior, and support forlinear()andsteps()easing stay unchanged. (#10261) - Under Reduce Motion, a cross-fade's move and its call's settle wait while a sampler pauses its fade, so the element never moves, and an exit's element never goes, while the paused fade still shows. (#10378)
Avatarinitials and the default person icon paint in primary text on the neutral tint, a pair at 4.5:1 or more in light and dark mode; secondary text fell below 4.5:1 in dark mode. Initials read darker in light mode and lighter in dark mode. (#10205)- Banner:
role="alert"now sits on the title and description only, not on the whole banner, so an urgent alert holds only its message (component:BannerFR8; WCAG 2.2 4.1.3 Status Messages). The dismiss and expand controls, their tooltips, a caller's action, and the supporting content are outside the alert. ARIA attributes passed withrole="alert", such asaria-label, move with it. Other roles still land on the banner frame. Userole="alert"only for an urgent message, and announce every other message withuseAnnounce. No visual change: the banner renders the same pixels as before. (#6779) - BottomSheet: a touch release takes the iOS sheet's measured values, and a release moving back toward where the drag began cancels. A release faster than about 1,000 px/s is a flick: it goes at least to the next detent in its direction, so a short fast flick at the lowest detent closes the sheet instead of springing back. From a higher detent, a flick that would carry past the next detent goes on, so a hard flick closes the sheet and a softer one stops at the next detent. A slow or medium touch throw now travels less than before, and a slow touch drag closes the sheet only past halfway to closed. A mouse or pen drag is unchanged. (#10234)
- A labelled
Buttonhas its accessible name again in VoiceOver on macOS 14 (Safari 17 and WKWebView). The label sat inside adisplay: contentswrapper, which that WebKit drops names through, so it read an unnamed "button". The wrapper is now a flex box that takes the Button's own layout, and the Button looks the same. (#10256) - Under a finger, a
ButtonorIconButtonis easier to hit. Its touch target grows toward 44 px through an invisible band, as far as its neighbors leave room, and its box doesn't change. A disabled button, or a busy one that can't be interrupted, gets no band, and a button in aButtonGroupuses the group's band. Input clear buttons now use the same band in place of their fixed 24 px overlay, and in Safari a tap on that band clears the field. Nothing changes under a mouse. Swizzling a ListItem, CheckboxInput, RadioListItem, InfoTip or SegmentedControl no longer leaves an import of the touch band's styles that can't resolve. (#10216) CalendarandDateRangeInputno longer cause a hydration mismatch when the server and the browser are on different dates, for example a UTC server and a visitor already in tomorrow. Today is read only after hydration: a server-rendered Calendar shows no today marker until then, and a Calendar with nofocusDateor value keeps its month grid's space empty until the browser's month is known. A DateRangeInput shows the year in its range text until then. (#10226)- Shift and one mouse wheel notch now scroll a
Carouselrow by the notch, once. Before, Firefox also scrolled the row on its own, so each notch moved it twice: React's wheel listener is passive, so Carousel could not stop the browser's scroll. A wheel with a horizontal delta, such as a trackpad swipe, and a row with nothing to scroll keep the browser's own scroll. (#10246) - A theme's
borderRadiusandpaddingon thechat-composertarget now also set the composer's--_chat-composer-radiusand--_chat-composer-padding, so the composer body, its status strip, and the concentric send and attach button radius follow the theme. Withdensity="compact", the body keeps its compact padding, and its radius still follows. Before, the derived-variable registry filed these two mappings underchat, a key no element renders, sodefineTheme({components: {'chat-composer': {base: {borderRadius: '16px', padding: '8px'}}}})emitted onlyborder-radiusandpaddingon the composer root, and everything that reads the two variables kept the default geometry. (#10249) CodeBlock's copy button now says when copying fails. A rejected clipboard write used to look like nothing happened. Now the button shows a cross in place of the copy icon for 2 seconds, as a copy shows its check mark (a theme that maps thecode-block-copyicon slot keeps its own rest glyph during the failure), and is named, tooltipped and announced as "Failed to copy value to clipboard." (a new localized key,@astryx.codeBlock.copyFailed). A newonCopyError(error)prop receives the rejection once per failed copy; the error itself is never shown. (#10272)- The Core modules that read
process.env.NODE_ENVfor development warnings now declare it themselves, so those files type-check in a project that does not install@types/node, such as a swizzledBreadcrumbs,StepperorTabList. Bundlers still replace the value at build time, so production builds drop the warnings as before. No API changes. (#10252) - A block-edge reveal or conceal, as in Collapsible, TreeList and Table's row expansion with an
animatedLayouthandle, now slides the revealed element's children on the same frames as the content beside it, under a still clip on the element's box. An element that paints its own box, such as Table'spanelVariant="muted"panel, keeps the moving clip. On iOS Safari a moving clip ran on its own clock and parted from that content for a few frames; now the two stay together. The glide's timing and curve are unchanged. Collapsible's region now wraps its children in one inner element; selectors likeregion > *or:first-childon the region's children need updating. (#10296) Kbd: a key badge grows with a larger text size instead of holding its fixed height, so a bigger glyph stays inside its badge. At the default text size nothing changes. The docs now listref, say how a screen reader names the shortcut, and say that Kbd only shows keys and does not listen for them. (#10267)- In a List with
hasDividers, a hovered or pressed row keeps both of its dividers visible through its tint, with a mouse and under a finger. The divider above the row used to merge into the tint, and under a finger both dividers did. The dividers keep--color-border; nothing hides. (#10280) - Overlay, AppShell and MobileNav work in a DOM with no
matchMedia, such as an app's jsdom test. Before, Overlay threw on its first render, AppShell as it mounted (with React 19.2 or later), and MobileNav as it closed. WherematchMediaexists, nothing changes. (#10327) - Carousel paging: on a busy page, a finger held on a settling row now stops it, as on an idle page. Before, when the page received the touch and its lift together, a short hold read as a tap and the row ran on to its target. (#10330)
- Carousel paging: a row that resizes while it settles back onto the page it left now hands back to native scrolling, instead of staying held by the paging. (#10419)
presentation="adaptive"no longer crashes in environments withoutmatchMedia(jsdom tests). (#10275)- A Selector's list, opened over its trigger near the bottom of the screen while a software keyboard is up, now slides up and ends above the keyboard with its options in view. Before, it shrank to a sliver or opened under the keyboard. Without a keyboard it opens where it did. (#10169)
- A searchable
Selector's closed trigger now names the selected option after its label, so a screen reader announces the selection (for example "Team, Banana, button, collapsed"). (#10170) - BottomSheet: in iOS Safari, focus moving from a Tall sheet's field to a plain button inside a web component now rides the content down from the blur, as focus moving to any other control that brings up no keyboard does. A frame, or a custom element that can hold a field the page cannot see, still keeps the content in place. (#10388)
StatusDot'ssuccess,warninganderrordots paint their status icon role (--color-icon-<status>) instead of the strong status fill, so the dot keeps 3:1 or more against the page and card surfaces; the warning dot used to read near 1.8:1 on a muted card. Success and error dots change colour too: they take their status icon colour, which is darker in light mode in the default theme. Aniconinside a status dot now paints in the surface colour. (#10204)- On a touch screen with a mouse, after a finger opens a menu, a dialog, a drawer, a mobile nav or a popover, a click with a mouse that has not moved since reaches what is under it while the layer enters. Before, that click landed on the entrance's input hold and did nothing. A finger's or a pen's tap during the entrance is still ignored. A mouse that has sent no pointer event since the page loaded still meets the hold. (#10303)
- BottomSheet: in iOS Safari, which publishes no keyboard slide, when the on-screen keyboard closes, a Tall sheet's content rides down with it on UIKit's keyboard spring, instead of jumping back to its earlier scroll once the keyboard is gone. A field that takes focus again before the keyboard is down rides back up, and focus moving to a select, whose picker takes the keyboard's place, starts no ride. In Chrome on Android, a busy page that reads the keyboard's hide late no longer moves the content back up before it settles. (#9776)
- A toast shown over a
Dialogno longer blinks out for a frame or more when the Dialog closes outside a click, for example when it closes once an awaited save finishes. The toast stays on screen while the Dialog closes. A close from a click, the Escape key or the backdrop already kept it. (#10251) - DateInput: under a finger, a bottom-sheet wheel's turn onto a tapped row, a key's row or a value set from outside now plays the shared settle spring from rest, instead of a fixed 300 ms ease-in-ease-out. The wheel's main interaction is a gesture, so all its motion springs; a flick's coast and a slow release's snap stay as they are. (#9924)
- Closing a Popover, menu or other anchored layer no longer lays out the page an extra time. The layer runtime reads a closing layer's animations only when the layer's closed state declares a discrete
displaytransition or a keyframe animation. It reads that style while the layer is still closed. Such a layer, as TopNavMegaMenu's panel is, still keeps its trigger's anchor name until its fade ends. An animation a script starts is not tracked. (#10368)
- FormLayout says to wrap it in a native
<form>, and that<form>has no Astryx replacement. (#10349) LayerProvider: editors and generated docs now show its description and example; they were attached to an internal constant. The docs no longer say that a nested provider is ignored: a nested provider keeps the outer toast configuration and mounts no second toast viewport, and one that declaresinsetapplies its declared edges to the anchored layers in its subtree. (#10283)- Layout's
heightprop says thatfillneeds a container with a set height, such as AppShell's content area. (#10348)
- Internal: a source comment in
Carouselnow says that the wheel listener reads no style or layout unless a flick holds the row. Apps see no change. (#10281) - Internal: the input hold's constant for the mouse's opening is named for the half side it holds, and its comment goes. Apps see no change. (#10317)
- Internal: Core's keyboard module reads the press slop that press feedback uses for its tap route, instead of its own copy of the same 10 px, and three source comments that restated names are gone. Apps see no change. (#10389)
- Internal: Core's keyboard module keeps a field above the on-screen keyboard where its nearest scroller can bring it up: a field in scrolling content is scrolled into view by its nearest scroller, the document included, a field in a container fixed at the viewport's bottom moves that container up by the part of it the keyboard still covers, unless the container sets its own
translate, the app is moving it itself, or it is taller than the room above the keyboard, where its scroller reveals the field instead, or with none it moves only as far as the field needs, and focus moves and first taps into those fields arrive without the browser's reveal. A field in a fixed container the app positions itself (a dialog or a sheet that fills the viewport, a bar floating above the bottom edge, or a bar with its owntranslate) is revealed by a scroller around it there, and with none keeps the browser's own reveal. Core's fields adopt it next; apps import nothing new. (#9776) - Internal: the layer runtime gains one exit copy for touch presentations that animate a popover out: a static, inert copy of the closing popover, shown only in the top layer where the popover was drawn, for the close to play on. Core's other inert copies now join no form, carry no anchor name and keep their color scheme, as their documentation says. (#8186)
- Internal:
Dialog,DrawerandBottomSheethand the toast viewport back to the page through a callback ref when they close or unmount, in place of a layout cleanup. A toast still stays on screen while the modal closes. Apps see no change. (#10351) - Internal: source comments in Popover's touch presentation and the transient copy now match what the code does: a touch that starts before the input hold can close the popover, and
measurereads before the frame writes. Apps see no change. (#10300)
astryx buildranks Core blocks of component families its picker was not fitted with somewhat better: the block picker's doc-side word weights are refitted from paraphrases of each block's own source. (#10355)
astryx buildnames its two alternative page templates in the same order it chooses the start from, so the three templates it shows for a whole page are its best three. The start, the number of alternatives, the blocks and the JSON shape are unchanged. (#10357)astryx build --type docand--type themenow point toastryx search <query> --type docor--type theme: a build kit has no docs or themes, so build says so once on stderr and names the search that finds them. Stdout, JSON output and exit codes are unchanged. (#10401)astryx doctorno longer warns that no theme is wired in an app that imports its themes itself. Without a generated theme module or a package.jsonastryx.theme, thethemescheck now passes when the source of the app imports a theme's built module or stylesheet (the importstheme addwrites) or passes a theme toTheme, followed through module-scope variables,defineTheme({extends}), re-exports and installed packages to its package, and names the file. Only a theme whose package is installed, or a local theme, counts. A theme passed toThemethat doctor cannot trace (a prop, a function result, a variable declared inside a component) is reported as not confirmed (info), not as missing. (#10353)- The CLI's semver range check reads
^0as any 0.x.y and^0.0as any 0.0.y, and reads a hyphen range (1.0.0 - 2.0.0) as inclusive bounds, with a partial upper bound (1.0.0 - 2) covering its whole series as npm does. Before,^0and^0.0were locked to a single patch version and a hyphen range could never match, soastryx doctorand the peer-version checks reported a false mismatch for projects that declare those ranges. (#10184) - The reminder to run
astryx initin a project that has not run it no longer prints before every command. It now prints after a command that succeeds, at most once a day per project, recorded in the per-user state as the daily hints are. It does not print with--json, after a command that fails, or whenCIis set.astryx doctorstill reports the missing setup in its agent-docs check every time. No JSON shape or exit code changes. (#10343) - In a folder inside an Astryx project whose own
package.jsondeclares no Astryx package, such as a tool folder that installs its own@astryxdesign/core, the setup reminder'sinitcommand now names the project's release, as run from the project's folder: the project's own CLI when it installs one, otherwise the package runner pinned to the project's Core, such asnpx @astryxdesign/cli@0.7.3 init. It used to pin the release of the CLI that answered the run, whatever the project records. No JSON shape or exit code changes. (#10343) astryx experimental render: a page outside a project now renders. Outside a project (no Core or CLI the folder reads, and no package.json that declares one), the page takes the@astryxdesign/*packages its folder lacks, and the integrations a host approves, from the copy the CLI itself runs with, instead of failing with ERR_RENDER_MISSING_DEPENDENCY. React and StyleX come from that copy too, so the page loads one copy of each, even in a React app that installs its own. When that copy's Core cannot be downloaded, a page that needs it fails with ERR_VERSIONS_UNAVAILABLE, as other commands that read Core do. Inside a project, the page uses only the project's own packages. (#10362)- A link to a topic that an integration replaces under the same name opens the replacement. In an app whose integration replaced
themeorgetting-started,doctorreported Core's links to them as naming no doc. (#10342) swizzleno longer copies a component's browser test harnesses (*.spec.ts,*.spec.tsx, such as Item'sItemMarkerColumns.a11y.chromium.spec.ts) when the installed Core source holds them:@astryxdesign/core0.7.5 and earlier, or Core's repository source. They import Playwright and an unpublished test package, so a project that swizzled such a component failed to type-check or build. Core 0.7.6 and later ship no harnesses, so swizzling from them is unchanged. (#10230)astryx theme buildno longer depends on the order it loads the core component docs. A parent doc that lists a sub-component by name only, such asAvatar.doc.mjslistingAvatarStatusDot, erased the values the sub-component's own doc declares when it loaded after that doc; whenAvatar.doc.mjsloaded last,avatar-status-dotvariant:successcounted as a custom value. The build now merges every doc's entry for a component. (#10288)astryx integration verifyno longer reportstheme_module_stalefor a theme whose built module differs only in the command its comment says built it, such as a theme built withyarn astryxand verified wherepnpm exec astryxruns. Any other difference still fails. (#10344)
- A compact or full hook list, and the suggestions for an unknown hook name, list each of Core's folders once. Before, they listed a folder again for each hook they looked up. (#10324)
- A search, build or component read lists each folder once. A process that runs several reads, such as a docs site's search or an agent harness, reuses a folder's listing once the folder has stayed unchanged for two seconds. A later read lists the folder again after an entry is added, removed or renamed. (#10274)
- Within one operation, component discovery reads each component doc once, and the component matcher looks for each component's doc once, not once for each name they resolve. Resolving 30 names that only the matcher finds, such as names in another case, makes 14,794 file-system calls instead of 305,108. Results are unchanged. (#10277)
- The Authoring guides (Quick Start, Field reference, Building Blocks, Ship, Help, and Make your integration work globally) now carry the keyword "authoring", so
astryx search authoringlists them right after the Authoring overview instead of after API function pages. (#10354) astryx build --helplists every value--typeaccepts (component, hook, doc, template, theme), matching the invalid-type error and what build actually runs, and says thatdocandthemegive an empty kit, since the kit has no doc or theme group. A test keeps the help text, the choices, the API doc and the error message on build and search naming the same set, and checks what each value returns. (#10361)- Getting Started has an Upgrade section: upgrade every Astryx package your app lists in one command, to the same release, then run
astryx upgrade. If your package manager holds new releases back, exempt the whole@astryxdesign/*scope, not only some of its packages. (#10241) - The custom theme guide names the files of a local theme, including the same-stem descriptor
theme addreads. (#10347) - The CLI's bundled colour token docs say the status icon colours (
--color-icon-<status>) paint status marks on the page or a card, such as a StatusDot. (#10204) - New block, "Table — Selection in the Leading Mark": row selection with no checkbox column. Each row shows its avatar, and the checkbox takes the avatar's slot while a mouse is over it, on keyboard focus, and on every row once anything is selected. On touch screens the checkbox always shows. It uses the existing
useTableSelectionStateand renders the checkboxes in the name column, so no new Table API is involved. (#10395)
- Internal: the export reader can report type-only exports and map a module's whole public surface in one pass. No change to any command's output. (#10365)
- In
RichTextEditor, Backspace at the very start of a code block turns it into a paragraph holding its lines, with the caret at its start. It used to merge the code into the block above, so a heading above took the code in, and the Markdown read back as a longer heading and a stray paragraph. A code block with nothing above it, which already became a paragraph, now keeps its lines when its Markdown is read back. (#8581) - RichText: an image in Markdown, inline (
) or by reference (![alt][ref]), comes back exactly as written after you edit the text around it; a shortcut reference image (![alt]) followed directly by a link is written in its collapsed form (![alt][]), so the link stays a link. Before, an edit in an image's paragraph could escape its brackets (!\[\](…)), so other Markdown readers saw text instead of an image. RichText has no image node: an image shows as its Markdown source, one token that Backspace deletes whole and autolinking leaves alone. A caret placed inside it moves to its edge, so typing adds text beside the image instead of replacing it. Copying it, or splitting or joining its paragraph, keeps the source. (#10356)
Thanks to everyone who contributed to this release:
@cixzhang @emilyhorsman @ernestt @josephfarina @nbozidarevic @thecodebasedot @utsavo-afk @vjeux
Full Changelog: https://github.com/meta/astryx/compare/v0.7.10...v0.7.11
v16.5.0-canary.43
- fix(app-render): stop prerendered Link headers from accumulating on revalidation: #100960
- Align eslint-config-next TypeScript peer with typescript-eslint: #101247
- Reduce header allocations in NodeNextResponse: #101225
- [image-optimizer] Move next/image-optimizer-transform under the next/experimental namespace: #101252
- [image-optimizer] Don't use NextConfigComplete for the imageOptimizerTransform public API: #101184
- Improve Request Insights context menus and trace interactions: #97796
- Build and analyze in one pass: #99962
- docs: clarify SVG handling in the Image Optimization API: #101301
- Turbopack: use hash collections for turbo-tasks values whose order is unobserved: #100939
- Turbopack: don't split page entries into a facade: #101152
- Turbopack: replace Next.js entry kinds with an opaque entry tag: #101291
- docs: map BFF proxy example routes to fixed backend endpoints: #101286
- docs: explain ESLint setup with TypeScript 7: #101246
- Durable use cache conditional reads: #101283
- docs: read the URL in history API event handlers instead of calling hooks: #101224
- review: escalate Next.js concepts in Turbopack code: #101278
- test: enable HMR dependency acceptance coverage for webpack: #101196
- test: Replace
itTurbopackwith test gates: #101195
Huge thanks to @styfle, @lukesandberg, @linyiru, @icyJoseph, @kassens, @mischnic, @eps1lon, @bgw, @DavidIlie, and @wbinnssmith for helping!
Release 2026-11-06 23:04
Release 2026-11-06 23:04
- vue-query: return a reactive
statefromuseQuerysostatus=== 'success'narrowsdatawithout unwrapping refs (#12541) (f4199ab51) by @DamianOsipiuk
- vue-query: keep query-core's
enabled(query)callback (#12542) (025773a83) by @DamianOsipiuk
- @tanstack/angular-query-experimental@5.107.1
- @tanstack/eslint-plugin-query@5.107.1
- @tanstack/lit-query@0.2.38
- @tanstack/preact-query@5.107.1
- @tanstack/preact-query-devtools@5.107.1
- @tanstack/preact-query-persist-client@5.107.1
- @tanstack/query-async-storage-persister@5.107.1
- @tanstack/query-broadcast-client-experimental@5.107.1
- @tanstack/query-core@5.107.1
- @tanstack/query-devtools@5.107.1
- @tanstack/query-persist-client-core@5.107.1
- @tanstack/query-sync-storage-persister@5.107.1
- @tanstack/react-query@5.107.1
- @tanstack/react-query-devtools@5.107.1
- @tanstack/react-query-next-experimental@5.107.1
- @tanstack/react-query-persist-client@5.107.1
- @tanstack/solid-query@5.107.1
- @tanstack/solid-query-devtools@5.107.1
- @tanstack/solid-query-persist-client@5.107.1
- @tanstack/svelte-query@6.4.1
- @tanstack/svelte-query-devtools@6.4.1
- @tanstack/svelte-query-persist-client@6.4.1
- @tanstack/vue-query@5.107.1
- @tanstack/vue-query-devtools@6.4.1