Skip to content

perf: Shrink bundles by dropping @tanstack/store and the key-name tables - #211

Merged
KevinVandy merged 8 commits into
mainfrom
fix/devtools-peer-deps
Oct 30, 2026
Merged

KevinVandy merged 8 commits into
mainfrom
fix/devtools-peer-deps

Conversation

@KevinVandy

@KevinVandy KevinVandy commented Oct 30, 2026 •

Copy link
Copy Markdown
Member

Cuts bundle size in core and every adapter. A React app with useHotkey and HotkeysProvider goes from 12.0 kB to 7.8 kB (brotli). Typed hotkeys behave as before; the behavior changes only affect input the types don't allow.

Size vs. the latest release

@tanstack/hotkeys 0.19.0 and @tanstack/react-hotkeys 0.18.0 vs. this PR. Each import is bundled with esbuild, minified, in production mode, and compressed with brotli; React is external.

Import Release This PR Change
@tanstack/hotkeys everything 13.5 kB 11.9 kB −12%
getHotkeyManager 8.5 kB 6.4 kB −24%
HotkeyRecorder 6.7 kB 4.6 kB −32%
getKeyStateTracker 2.9 kB 0.9 kB −67%
formatForDisplay 2.5 kB 1.9 kB −24%
Manager + app hotkeys 9.7 kB 7.6 kB −22%
@tanstack/react-hotkeys everything 16.2 kB 13.6 kB −16%
React useHotkey 10.5 kB 7.4 kB −29%
React useHotkey + HotkeysProvider 12.0 kB 7.8 kB −34%
…+ defineAppHotkeys 12.0 kB 9.0 kB −25%
React useHotkeyRecorder 8.1 kB 4.9 kB −40%
React useKeyHold + useHeldKeys 4.1 kB 1.1 kB −72%
React useHotkeyRegistrations 9.8 kB 6.7 kB −32%

Core size-limit budgets are unchanged, leaving room for upcoming fixes. New entries cover React useHotkey with and without the provider, and a provider without app hotkeys.

Changes

  • No more @tanstack/store at runtime. Core uses a small built-in store with the same state, get, setState, and subscribe API, typed by picking from TanStack Store's types. @tanstack/store is a devDependency, and its types are inlined into dist/vendor. Adapters subscribe with small helpers instead of the @tanstack/*-store packages, and React uses its built-in useSyncExternalStore. The stores still work with TanStack Store's framework adapters.
  • App hotkey support loads on demand. Providers create the app hotkeys store through a factory that defineAppHotkeys registers, so apps without app hotkeys don't bundle it.
  • Key names are case-sensitive, and the key-name tables are gone. normalizeKeyName uppercases letters and maps ' ' to Space; other names stay as written, and key aliases such as Esc are no longer resolved. Validation uses a short pattern instead of a list of keys, and the recorder checks for whitespace keys instead of running full validation. The exported key sets keep their values but are dropped by bundles that don't import them.
  • formatForDisplay accepts typed input only. It takes hotkeys, which include single keys, plus modifiers on their own such as 'Shift', instead of any string. Keys from a KeyboardEvent, such as held keys, are passed as { key }; the held-key examples and devtools do this.
  • triggerRegistration moves to devtools. It was only used by the devtools Trigger button. It's now part of the devtools package, built on the manager's public API.
  • Warnings only in development. Console warnings and errors are skipped when process.env.NODE_ENV is 'production'. In development, registering a hotkey with a key name like escape warns that it may never fire.
  • Hardening. Saved custom hotkeys, app hotkey ids, and display labels look up own properties only, so names such as toString or __proto__ from saved data are ignored instead of read from Object.prototype.
  • Devtools host peers. Each devtools adapter lists its TanStack Devtools host as an optional peer at the current release.
  • Docs and agent skills. The formatting and held-key guides for every framework explain the { key } form, and the core skill notes that key names are case-sensitive.

Every package gets a minor bump.

Behavior changes

  • Spellings the hotkey types don't allow, such as escape, Esc, f1, Plus, and pgdn, stay as written and no longer match. Letters still match in any case, and modifier aliases such as Ctrl, Cmd, and Option still work. Hotkeys saved by the recorder are canonical and keep working.
  • validateHotkey and checkHotkey warn about keys not written like a known key ('escape'), instead of keys missing from a list.
  • formatForDisplay no longer accepts arbitrary strings; pass held keys as { key }.
  • HotkeyManager.triggerRegistration is removed from core.
  • The recorder rejects whitespace keys, such as the non-breaking space from Option+Space on macOS, with "Whitespace keys cannot be recorded".
  • The stores are no longer Store instances, so instanceof Store and actions don't apply.

Testing

  • pnpm test:ci passes, including example type checks and builds, as do Ember's browser suite and the Playwright e2e suite (150 tests in Chromium, Firefox, and WebKit).
  • typed-behavior.test.ts fingerprints parsing, normalization, validation, display, held-key display, event matching, recorded chords, and recorder and manager runs with dispatched events, for every typed chord, raw chord, and sequence, and for realistic events across all modifiers and every character up to U+2FFF. The fingerprints were captured before the refactor and still match.
  • The store tests run against both the new store and TanStack Store, so their notification behavior can't drift apart.
  • New tests cover devtools live updates and triggering, compatibility with @tanstack/react-store's useSelector, the app hotkeys factory, production logging, single-key display, whitespace recording, the registration warning, and prototype-named input.

…in development

- Core and every adapter subscribe with a small built-in store instead of
  @tanstack/store and the framework store adapters. Stores keep the same
  state, get, setState, and subscribe API, typed with TanStack Store's own
  types, and still work with TanStack Store's framework adapters.
- Providers load app hotkey support only when the app uses defineAppHotkeys.
- Console warnings and errors are logged only outside production builds.
- Devtools adapters list their TanStack Devtools host as an optional peer at
  the current release.
@changeset-bot

changeset-bot Bot commented Oct 30, 2026 •

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: d3195a5

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 18 packages
Name Type
@tanstack/hotkeys Minor
@tanstack/react-hotkeys Minor
@tanstack/preact-hotkeys Minor
@tanstack/solid-hotkeys Minor
@tanstack/vue-hotkeys Minor
@tanstack/svelte-hotkeys Minor
@tanstack/angular-hotkeys Minor
@tanstack/lit-hotkeys Minor
@tanstack/alpine-hotkeys Minor
@tanstack/octane-hotkeys Minor
@tanstack/ember-hotkeys Minor
@tanstack/hotkeys-devtools Minor
@tanstack/react-hotkeys-devtools Minor
@tanstack/preact-hotkeys-devtools Minor
@tanstack/solid-hotkeys-devtools Minor
@tanstack/vue-hotkeys-devtools Minor
@tanstack/svelte-hotkeys-devtools Minor
@tanstack/angular-hotkeys-devtools Minor

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@coderabbitai

coderabbitai Bot commented Oct 30, 2026 •

Copy link
Copy Markdown

Important

Review skipped

Too many files!

This PR contains 256 files, which is 106 over the limit of 150.

To get a review, reduce the PR to 150 files or fewer by splitting it into smaller PRs or changing its base branch.

Upgrade to a paid plan to raise the limit.

This review couldn't start because sufficient usage credits or metered capacity aren't available. Add credits or update usage-based reviews in the billing tab, then retry.

Run configuration
Commits

Reviewing files that changed from the base of the PR and between 8602ebe and d3195a5.

Files ignored due to path filters: 138
  • docs/framework/angular/reference/functions/injectDefaultHotkeysOptions.md is excluded by !docs/**/reference/**
  • docs/framework/angular/reference/functions/injectHotkeysContext.md is excluded by !docs/**/reference/**
  • docs/framework/angular/reference/functions/provideHotkeys.md is excluded by !docs/**/reference/**
  • docs/framework/angular/reference/interfaces/HotkeysContextValue.md is excluded by !docs/**/reference/**
  • docs/framework/angular/reference/interfaces/HotkeysProviderOptions.md is excluded by !docs/**/reference/**
  • docs/framework/angular/reference/interfaces/ProvideHotkeysOptions.md is excluded by !docs/**/reference/**
  • docs/framework/angular/reference/type-aliases/MaybeGetter.md is excluded by !docs/**/reference/**
  • docs/framework/angular/reference/variables/HOTKEYS_INJECTION_TOKEN.md is excluded by !docs/**/reference/**
  • docs/framework/octane/reference/functions/HotkeysProvider.md is excluded by !docs/**/reference/**
  • docs/framework/octane/reference/functions/useDefaultHotkeysOptions.md is excluded by !docs/**/reference/**
  • docs/framework/octane/reference/functions/useHotkeysContext.md is excluded by !docs/**/reference/**
  • docs/framework/octane/reference/interfaces/DefaultHotkeysOptions.md is excluded by !docs/**/reference/**
  • docs/framework/octane/reference/interfaces/HotkeysProviderProps.md is excluded by !docs/**/reference/**
  • docs/framework/octane/reference/type-aliases/HotkeysProviderOptions.md is excluded by !docs/**/reference/**
  • docs/framework/preact/reference/functions/HotkeysProvider.md is excluded by !docs/**/reference/**
  • docs/framework/preact/reference/functions/useDefaultHotkeysOptions.md is excluded by !docs/**/reference/**
  • docs/framework/preact/reference/functions/useHeldKeys.md is excluded by !docs/**/reference/**
  • docs/framework/preact/reference/functions/useHotkeysContext.md is excluded by !docs/**/reference/**
  • docs/framework/preact/reference/functions/useKeyHold.md is excluded by !docs/**/reference/**
  • docs/framework/preact/reference/interfaces/HotkeysProviderOptions.md is excluded by !docs/**/reference/**
  • docs/framework/preact/reference/interfaces/HotkeysProviderProps.md is excluded by !docs/**/reference/**
  • docs/framework/react/reference/functions/HotkeysProvider.md is excluded by !docs/**/reference/**
  • docs/framework/react/reference/functions/useDefaultHotkeysOptions.md is excluded by !docs/**/reference/**
  • docs/framework/react/reference/functions/useHeldKeys.md is excluded by !docs/**/reference/**
  • docs/framework/react/reference/functions/useHotkeysContext.md is excluded by !docs/**/reference/**
  • docs/framework/react/reference/functions/useKeyHold.md is excluded by !docs/**/reference/**
  • docs/framework/react/reference/interfaces/HotkeysProviderOptions.md is excluded by !docs/**/reference/**
  • docs/framework/react/reference/interfaces/HotkeysProviderProps.md is excluded by !docs/**/reference/**
  • docs/framework/solid/reference/functions/createHeldKeyCodes.md is excluded by !docs/**/reference/**
  • docs/framework/solid/reference/functions/createHeldKeys.md is excluded by !docs/**/reference/**
  • docs/framework/solid/reference/functions/createKeyHold.md is excluded by !docs/**/reference/**
  • docs/framework/solid/reference/functions/useDefaultHotkeysOptions.md is excluded by !docs/**/reference/**
  • docs/framework/solid/reference/functions/useHotkeysContext.md is excluded by !docs/**/reference/**
  • docs/framework/solid/reference/interfaces/HotkeysProviderOptions.md is excluded by !docs/**/reference/**
  • docs/framework/solid/reference/interfaces/HotkeysProviderProps.md is excluded by !docs/**/reference/**
  • docs/framework/solid/reference/variables/HotkeysProvider.md is excluded by !docs/**/reference/**
  • docs/framework/svelte/reference/functions/getDefaultHotkeysOptions.md is excluded by !docs/**/reference/**
  • docs/framework/svelte/reference/functions/getHotkeysContext.md is excluded by !docs/**/reference/**
  • docs/framework/svelte/reference/functions/setHotkeysContext.md is excluded by !docs/**/reference/**
  • docs/framework/svelte/reference/interfaces/HotkeysContextOptions.md is excluded by !docs/**/reference/**
  • docs/framework/svelte/reference/interfaces/HotkeysProviderOptions.md is excluded by !docs/**/reference/**
  • docs/framework/svelte/reference/interfaces/HotkeysProviderProps.md is excluded by !docs/**/reference/**
  • docs/framework/svelte/reference/variables/DEFAULT_OPTIONS.md is excluded by !docs/**/reference/**
  • docs/framework/vue/reference/functions/provideHotkeysContext.md is excluded by !docs/**/reference/**
  • docs/framework/vue/reference/functions/useDefaultHotkeysOptions.md is excluded by !docs/**/reference/**
  • docs/framework/vue/reference/functions/useHeldKeys.md is excluded by !docs/**/reference/**
  • docs/framework/vue/reference/functions/useHotkeysContext.md is excluded by !docs/**/reference/**
  • docs/framework/vue/reference/interfaces/HotkeysProviderOptions.md is excluded by !docs/**/reference/**
  • docs/framework/vue/reference/interfaces/ProvideHotkeysContextOptions.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/functions/activateHotkeysProviderScope.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/functions/createAppHotkeysStore.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/functions/createHotkeyBindings.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/functions/createStore.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/functions/getHotkeysProviderScopeKey.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/functions/mergeHotkeysProviderDefaults.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/functions/prepareHotkeyDefinitions.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/functions/subscribePublishedAppHotkeys.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/index.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/interfaces/HotkeysProviderScopeProps.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/interfaces/PrepareHotkeyDefinitionsOptions.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/AdapterAppHotkeyOptions.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/AdapterChordOptions.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/AdapterCommonOptions.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/AdapterHotkeyDefinition.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/AdapterHotkeyOptions.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/AdapterOptionsFor.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/AdapterSequenceOptions.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/HotkeyBindingsCommonOptions.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/HotkeyDefinition.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/Store.md is excluded by !docs/**/reference/**
  • docs/reference/adapter/type-aliases/WithTarget.md is excluded by !docs/**/reference/**
  • docs/reference/classes/AppHotkeysStore.md is excluded by !docs/**/reference/**
  • docs/reference/classes/HotkeyManager.md is excluded by !docs/**/reference/**
  • docs/reference/classes/HotkeyRecorder.md is excluded by !docs/**/reference/**
  • docs/reference/classes/KeyStateTracker.md is excluded by !docs/**/reference/**
  • docs/reference/functions/assertValidHotkey.md is excluded by !docs/**/reference/**
  • docs/reference/functions/checkHotkey.md is excluded by !docs/**/reference/**
  • docs/reference/functions/defineAppHotkeys.md is excluded by !docs/**/reference/**
  • docs/reference/functions/formatForDisplay.md is excluded by !docs/**/reference/**
  • docs/reference/functions/getAppHotkeyRegistrationOptions.md is excluded by !docs/**/reference/**
  • docs/reference/functions/getHotkeyManager.md is excluded by !docs/**/reference/**
  • docs/reference/functions/getKeyStateTracker.md is excluded by !docs/**/reference/**
  • docs/reference/functions/isAppHotkey.md is excluded by !docs/**/reference/**
  • docs/reference/functions/isCustomHotkey.md is excluded by !docs/**/reference/**
  • docs/reference/functions/isSingleLetterKey.md is excluded by !docs/**/reference/**
  • docs/reference/functions/normalizeKeyName.md is excluded by !docs/**/reference/**
  • docs/reference/functions/provideAppHotkeys.md is excluded by !docs/**/reference/**
  • docs/reference/functions/publishAppHotkeysStore.md is excluded by !docs/**/reference/**
  • docs/reference/functions/resolveAppHotkey.md is excluded by !docs/**/reference/**
  • docs/reference/functions/toHotkeyRegistrationView.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/ActivateHotkeyScopeOptions.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/AppHotkey.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/AppHotkeyInput.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/AppHotkeyListItem.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/AppHotkeysState.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/AppHotkeysStoreOptions.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/FormatDisplayOptions.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/HotkeyChordOptions.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/HotkeyChordRegistration.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/HotkeyChordRegistrationView.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/HotkeyOptions.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/HotkeyRegistrationHandle.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/HotkeyScopesState.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/HotkeySequenceOptions.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/HotkeySequenceRegistration.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/HotkeySequenceRegistrationView.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/KeyStateTrackerState.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/Register.md is excluded by !docs/**/reference/**
  • docs/reference/interfaces/ValidationResult.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/AppHotkeyChordOptions.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/AppHotkeyDefaultKind.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/AppHotkeyId.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/AppHotkeyOptions.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/AppHotkeySequenceOptions.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/AppHotkeyStatus.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/AppHotkeys.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/CustomHotkeys.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/DefinedAppHotkeys.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/DisplayHotkey.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/DisplayHotkeyChord.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/HotkeyOptionsFor.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/HotkeyRegistration.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/HotkeyRegistrationStatus.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/HotkeyRegistrationView.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/RegisteredAppHotkeys.md is excluded by !docs/**/reference/**
  • docs/reference/type-aliases/Target.md is excluded by !docs/**/reference/**
  • docs/reference/variables/ALL_KEYS.md is excluded by !docs/**/reference/**
  • docs/reference/variables/EDITING_KEYS.md is excluded by !docs/**/reference/**
  • docs/reference/variables/FUNCTION_KEYS.md is excluded by !docs/**/reference/**
  • docs/reference/variables/LETTER_KEYS.md is excluded by !docs/**/reference/**
  • docs/reference/variables/MODIFIER_ALIASES.md is excluded by !docs/**/reference/**
  • docs/reference/variables/MODIFIER_KEYS.md is excluded by !docs/**/reference/**
  • docs/reference/variables/MODIFIER_ORDER.md is excluded by !docs/**/reference/**
  • docs/reference/variables/NAVIGATION_KEYS.md is excluded by !docs/**/reference/**
  • docs/reference/variables/NUMBER_KEYS.md is excluded by !docs/**/reference/**
  • docs/reference/variables/PUNCTUATION_CODE_MAP.md is excluded by !docs/**/reference/**
  • docs/reference/variables/PUNCTUATION_KEYS.md is excluded by !docs/**/reference/**
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml, !**/pnpm-lock.yaml
Files selected for processing: 256
  • .changeset/case-sensitive-key-names.md
  • .changeset/dev-only-warnings.md
  • .changeset/devtools-host-peers.md
  • .changeset/drop-tanstack-store.md
  • .changeset/lazy-app-hotkeys-store.md
  • .intent/review-state.json
  • docs/devtools.md
  • docs/framework/alpine/guides/app-hotkeys.md
  • docs/framework/alpine/guides/formatting-display.md
  • docs/framework/alpine/guides/held-key-state-helpers.md
  • docs/framework/alpine/guides/hotkey-manager.md
  • docs/framework/alpine/guides/hotkeys.md
  • docs/framework/angular/guides/app-hotkeys.md
  • docs/framework/angular/guides/formatting-display.md
  • docs/framework/angular/guides/held-key-state-helpers.md
  • docs/framework/angular/guides/hotkey-manager.md
  • docs/framework/angular/guides/hotkeys.md
  • docs/framework/ember/guides/app-hotkeys.md
  • docs/framework/ember/guides/formatting-display.md
  • docs/framework/ember/guides/held-key-state-helpers.md
  • docs/framework/ember/guides/hotkey-manager.md
  • docs/framework/ember/guides/hotkeys.md
  • docs/framework/lit/guides/app-hotkeys.md
  • docs/framework/lit/guides/formatting-display.md
  • docs/framework/lit/guides/held-key-state-helpers.md
  • docs/framework/lit/guides/hotkey-manager.md
  • docs/framework/lit/guides/hotkeys.md
  • docs/framework/octane/guides/app-hotkeys.md
  • docs/framework/octane/guides/formatting-display.md
  • docs/framework/octane/guides/held-key-state-helpers.md
  • docs/framework/octane/guides/hotkey-manager.md
  • docs/framework/octane/guides/hotkeys.md
  • docs/framework/preact/guides/app-hotkeys.md
  • docs/framework/preact/guides/formatting-display.md
  • docs/framework/preact/guides/held-key-state-helpers.md
  • docs/framework/preact/guides/hotkey-manager.md
  • docs/framework/preact/guides/hotkeys.md
  • docs/framework/react/guides/app-hotkeys.md
  • docs/framework/react/guides/formatting-display.md
  • docs/framework/react/guides/held-key-state-helpers.md
  • docs/framework/react/guides/hotkey-manager.md
  • docs/framework/react/guides/hotkeys.md
  • docs/framework/solid/guides/app-hotkeys.md
  • docs/framework/solid/guides/formatting-display.md
  • docs/framework/solid/guides/held-key-state-helpers.md
  • docs/framework/solid/guides/hotkey-manager.md
  • docs/framework/solid/guides/hotkeys.md
  • docs/framework/svelte/guides/app-hotkeys.md
  • docs/framework/svelte/guides/formatting-display.md
  • docs/framework/svelte/guides/held-key-state-helpers.md
  • docs/framework/svelte/guides/hotkey-manager.md
  • docs/framework/svelte/guides/hotkeys.md
  • docs/framework/vue/guides/app-hotkeys.md
  • docs/framework/vue/guides/formatting-display.md
  • docs/framework/vue/guides/held-key-state-helpers.md
  • docs/framework/vue/guides/hotkey-manager.md
  • docs/framework/vue/guides/hotkeys.md
  • docs/guides/sensible-defaults.md
  • examples/alpine/createHeldKeys/index.html
  • examples/alpine/createHeldKeys/src/main.ts
  • examples/angular/injectHeldKeys/package.json
  • examples/angular/injectHeldKeys/src/app/app.component.html
  • examples/angular/injectHeldKeys/src/app/app.component.ts
  • examples/angular/injectHotkey-sequences/package.json
  • examples/angular/injectHotkey/package.json
  • examples/angular/injectHotkeyRecorder-sequences/package.json
  • examples/angular/injectHotkeyRecorder-sequences/src/app/shortcut-list-item.component.html
  • examples/angular/injectHotkeyRecorder/package.json
  • examples/angular/injectHotkeyRecorder/src/app/shortcut-list-item.component.html
  • examples/angular/injectHotkeys-sequences/package.json
  • examples/angular/injectHotkeys/package.json
  • examples/angular/injectHotkeys/src/app/app.component.ts
  • examples/angular/injectKeyHold/package.json
  • examples/angular/kitchen-sink/package.json
  • examples/angular/scopes/package.json
  • examples/ember/useHeldKeys/app/templates/application.gts
  • examples/lit/held-keys/src/app.ts
  • examples/octane/useHeldKeys/src/main.tsrx
  • examples/preact/kitchen-sink/package.json
  • examples/preact/scopes/package.json
  • examples/preact/useHeldKeys/package.json
  • examples/preact/useHeldKeys/src/index.tsx
  • examples/preact/useHotkey-sequences/package.json
  • examples/preact/useHotkey/package.json
  • examples/preact/useHotkeyRecorder-sequences/package.json
  • examples/preact/useHotkeyRecorder/package.json
  • examples/preact/useHotkeys-sequences/package.json
  • examples/preact/useHotkeys/package.json
  • examples/preact/useKeyhold/package.json
  • examples/react/kitchen-sink/package.json
  • examples/react/scopes/package.json
  • examples/react/useHeldKeys/package.json
  • examples/react/useHeldKeys/src/index.tsx
  • examples/react/useHotkey-sequences/package.json
  • examples/react/useHotkey/package.json
  • examples/react/useHotkeyRecorder-sequences/package.json
  • examples/react/useHotkeyRecorder/package.json
  • examples/react/useHotkeys-sequences/package.json
  • examples/react/useHotkeys/package.json
  • examples/react/useKeyhold/package.json
  • examples/solid/createHeldKeys/package.json
  • examples/solid/createHeldKeys/src/index.tsx
  • examples/solid/createHotkey-sequences/package.json
  • examples/solid/createHotkey/package.json
  • examples/solid/createHotkeyRecorder-sequences/package.json
  • examples/solid/createHotkeyRecorder/package.json
  • examples/solid/createHotkeys-sequences/package.json
  • examples/solid/createHotkeys/package.json
  • examples/solid/createHotkeys/src/index.tsx
  • examples/solid/createKeyHold/package.json
  • examples/solid/kitchen-sink/package.json
  • examples/solid/scopes/package.json
  • examples/svelte/create-hotkey-recorder-sequences/package.json
  • examples/svelte/create-hotkey-recorder/package.json
  • examples/svelte/create-hotkey-sequences/package.json
  • examples/svelte/create-hotkey/package.json
  • examples/svelte/create-hotkeys-sequences/package.json
  • examples/svelte/create-hotkeys/package.json
  • examples/svelte/get-held-keys/package.json
  • examples/svelte/get-held-keys/src/App.svelte
  • examples/svelte/get-is-key-held/package.json
  • examples/svelte/kitchen-sink/package.json
  • examples/svelte/scopes/package.json
  • examples/vanilla/formatForDisplay/src/main.ts
  • examples/vue/kitchen-sink/package.json
  • examples/vue/scopes/package.json
  • examples/vue/useHeldKeys/package.json
  • examples/vue/useHeldKeys/src/App.vue
  • examples/vue/useHotkey-sequences/package.json
  • examples/vue/useHotkey/package.json
  • examples/vue/useHotkeyRecorder-sequences/package.json
  • examples/vue/useHotkeyRecorder/package.json
  • examples/vue/useHotkeys-sequences/package.json
  • examples/vue/useHotkeys/package.json
  • examples/vue/useKeyhold/package.json
  • package.json
  • packages/alpine-hotkeys/package.json
  • packages/alpine-hotkeys/src/scope.ts
  • packages/alpine-hotkeys/tsconfig.docs.json
  • packages/angular-hotkeys-devtools/package.json
  • packages/angular-hotkeys/package.json
  • packages/angular-hotkeys/src/_injectSelector.ts
  • packages/angular-hotkeys/src/hotkeys-provider.ts
  • packages/angular-hotkeys/src/injectHeldKeyCodes.ts
  • packages/angular-hotkeys/src/injectHeldKeys.ts
  • packages/angular-hotkeys/src/injectHotkeyHint.ts
  • packages/angular-hotkeys/src/injectHotkeyRecorder.ts
  • packages/angular-hotkeys/src/injectHotkeyRegistrations.ts
  • packages/angular-hotkeys/src/injectHotkeyScopesState.ts
  • packages/angular-hotkeys/src/injectKeyHold.ts
  • packages/angular-hotkeys/tsconfig.docs.json
  • packages/ember-hotkeys/package.json
  • packages/ember-hotkeys/src/utils.ts
  • packages/ember-hotkeys/tsconfig.docs.json
  • packages/hotkeys-devtools/package.json
  • packages/hotkeys-devtools/src/_trigger.ts
  • packages/hotkeys-devtools/src/components/ActionButtons.tsx
  • packages/hotkeys-devtools/src/components/HeldKeysTopbar.tsx
  • packages/hotkeys-devtools/tests/live-updates.test.tsx
  • packages/hotkeys-devtools/tests/trigger.test.ts
  • packages/hotkeys/package.json
  • packages/hotkeys/skills/hotkeys-core/SKILL.md
  • packages/hotkeys/src/_app-hotkeys-factory.ts
  • packages/hotkeys/src/_keyboard-event.ts
  • packages/hotkeys/src/_named-keys.ts
  • packages/hotkeys/src/_registration.ts
  • packages/hotkeys/src/_store.ts
  • packages/hotkeys/src/adapter.ts
  • packages/hotkeys/src/app-hotkeys.ts
  • packages/hotkeys/src/constants.ts
  • packages/hotkeys/src/format.ts
  • packages/hotkeys/src/hotkey-manager.ts
  • packages/hotkeys/src/hotkey-recorder.ts
  • packages/hotkeys/src/key-state-tracker.ts
  • packages/hotkeys/src/validate.ts
  • packages/hotkeys/tests/adapter.test.ts
  • packages/hotkeys/tests/format.test.ts
  • packages/hotkeys/tests/key-coverage.test.ts
  • packages/hotkeys/tests/key-tables.test.ts
  • packages/hotkeys/tests/match.test.ts
  • packages/hotkeys/tests/parse.test.ts
  • packages/hotkeys/tests/parsed-identity.test.ts
  • packages/hotkeys/tests/production-logs.test.ts
  • packages/hotkeys/tests/sequence-manager.test.ts
  • packages/hotkeys/tests/sequence-regressions.test.ts
  • packages/hotkeys/tests/store.test.ts
  • packages/hotkeys/tests/typed-behavior.test.ts
  • packages/hotkeys/tests/unified-hotkeys.test.ts
  • packages/hotkeys/tests/untrusted-input.test.ts
  • packages/hotkeys/tests/validate.test.ts
  • packages/hotkeys/tsconfig.json
  • packages/hotkeys/tsdown.config.ts
  • packages/lit-hotkeys/tests/ssr.test.ts
  • packages/lit-hotkeys/tsconfig.docs.json
  • packages/octane-hotkeys/package.json
  • packages/octane-hotkeys/src/HotkeysProvider.ts
  • packages/octane-hotkeys/src/internal.ts
  • packages/octane-hotkeys/src/useHeldKeyCodes.ts
  • packages/octane-hotkeys/src/useHeldKeys.ts
  • packages/octane-hotkeys/src/useHotkeyHint.ts
  • packages/octane-hotkeys/src/useHotkeyRecorder.ts
  • packages/octane-hotkeys/src/useHotkeyRegistrations.ts
  • packages/octane-hotkeys/src/useHotkeyScopesState.ts
  • packages/octane-hotkeys/src/useKeyHold.ts
  • packages/octane-hotkeys/tsconfig.docs.json
  • packages/preact-hotkeys-devtools/package.json
  • packages/preact-hotkeys-devtools/tests/panel.test.ts
  • packages/preact-hotkeys/package.json
  • packages/preact-hotkeys/src/HotkeysProvider.tsx
  • packages/preact-hotkeys/src/_appHotkeysStore.ts
  • packages/preact-hotkeys/src/_useSelector.ts
  • packages/preact-hotkeys/src/useHeldKeyCodes.ts
  • packages/preact-hotkeys/src/useHeldKeys.ts
  • packages/preact-hotkeys/src/useHotkeyHint.ts
  • packages/preact-hotkeys/src/useHotkeyRecorder.ts
  • packages/preact-hotkeys/src/useHotkeyRegistrations.ts
  • packages/preact-hotkeys/src/useHotkeyScopesState.ts
  • packages/preact-hotkeys/src/useKeyHold.ts
  • packages/preact-hotkeys/tsconfig.docs.json
  • packages/react-hotkeys-devtools/package.json
  • packages/react-hotkeys/package.json
  • packages/react-hotkeys/src/HotkeysProvider.tsx
  • packages/react-hotkeys/src/_appHotkeysStore.ts
  • packages/react-hotkeys/src/_useSelector.ts
  • packages/react-hotkeys/src/useHeldKeyCodes.ts
  • packages/react-hotkeys/src/useHeldKeys.ts
  • packages/react-hotkeys/src/useHotkeyHint.ts
  • packages/react-hotkeys/src/useHotkeyRecorder.ts
  • packages/react-hotkeys/src/useHotkeyRegistrations.ts
  • packages/react-hotkeys/src/useHotkeyScopesState.ts
  • packages/react-hotkeys/src/useKeyHold.ts
  • packages/react-hotkeys/tests/stores.test.tsx
  • packages/react-hotkeys/tsconfig.docs.json
  • packages/solid-hotkeys-devtools/package.json
  • packages/solid-hotkeys/package.json
  • packages/solid-hotkeys/src/HotkeysProvider.tsx
  • packages/solid-hotkeys/src/_useSelector.ts
  • packages/solid-hotkeys/src/createHeldKeyCodes.ts
  • packages/solid-hotkeys/src/createHeldKeys.ts
  • packages/solid-hotkeys/src/createHotkeyHint.ts
  • packages/solid-hotkeys/src/createHotkeyRecorder.ts
  • packages/solid-hotkeys/src/createHotkeyRegistrations.ts
  • packages/solid-hotkeys/src/createHotkeyScopesState.ts
  • packages/solid-hotkeys/src/createKeyHold.ts
  • packages/solid-hotkeys/src/defaultOptions.ts
  • packages/solid-hotkeys/tsconfig.docs.json
  • packages/svelte-hotkeys-devtools/package.json
  • packages/svelte-hotkeys/src/HotkeysCtx.ts
  • packages/svelte-hotkeys/tsconfig.docs.json
  • packages/vue-hotkeys-devtools/package.json
  • packages/vue-hotkeys/package.json
  • packages/vue-hotkeys/src/HotkeysProviderContext.ts
  • packages/vue-hotkeys/src/useHeldKeys.ts
  • packages/vue-hotkeys/src/useStoreSelector.ts
  • packages/vue-hotkeys/tests/ssr.test.ts
  • pnpm-workspace.yaml

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

  • Autofix · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@github-actions

Copy link
Copy Markdown
Contributor

🚀 Changeset Version Preview

18 package(s) bumped directly, 0 bumped as dependents.

🟨 Minor bumps

Package Version Reason
@tanstack/alpine-hotkeys 0.7.0 → 0.8.0 Changeset
@tanstack/angular-hotkeys 0.17.1 → 0.18.0 Changeset
@tanstack/angular-hotkeys-devtools 0.3.2 → 0.4.0 Changeset
@tanstack/ember-hotkeys 0.6.1 → 0.7.0 Changeset
@tanstack/hotkeys 0.19.0 → 0.20.0 Changeset
@tanstack/hotkeys-devtools 1.6.1 → 1.7.0 Changeset
@tanstack/lit-hotkeys 0.18.1 → 0.19.0 Changeset
@tanstack/octane-hotkeys 0.7.1 → 0.8.0 Changeset
@tanstack/preact-hotkeys 0.17.1 → 0.18.0 Changeset
@tanstack/preact-hotkeys-devtools 0.11.2 → 0.12.0 Changeset
@tanstack/react-hotkeys 0.18.0 → 0.19.0 Changeset
@tanstack/react-hotkeys-devtools 0.12.0 → 0.13.0 Changeset
@tanstack/solid-hotkeys 0.17.1 → 0.18.0 Changeset
@tanstack/solid-hotkeys-devtools 0.11.2 → 0.12.0 Changeset
@tanstack/svelte-hotkeys 0.17.1 → 0.18.0 Changeset
@tanstack/svelte-hotkeys-devtools 0.3.2 → 0.4.0 Changeset
@tanstack/vue-hotkeys 0.17.1 → 0.18.0 Changeset
@tanstack/vue-hotkeys-devtools 0.11.2 → 0.12.0 Changeset

@pkg-pr-new

pkg-pr-new Bot commented Oct 30, 2026 •

Copy link
Copy Markdown

Open in StackBlitz

@tanstack/alpine-hotkeys

npm i https://pkg.pr.new/@tanstack/alpine-hotkeys@211

@tanstack/angular-hotkeys

npm i https://pkg.pr.new/@tanstack/angular-hotkeys@211

@tanstack/angular-hotkeys-devtools

npm i https://pkg.pr.new/@tanstack/angular-hotkeys-devtools@211

@tanstack/ember-hotkeys

npm i https://pkg.pr.new/@tanstack/ember-hotkeys@211

@tanstack/hotkeys

npm i https://pkg.pr.new/@tanstack/hotkeys@211

@tanstack/hotkeys-devtools

npm i https://pkg.pr.new/@tanstack/hotkeys-devtools@211

@tanstack/lit-hotkeys

npm i https://pkg.pr.new/@tanstack/lit-hotkeys@211

@tanstack/octane-hotkeys

npm i https://pkg.pr.new/@tanstack/octane-hotkeys@211

@tanstack/preact-hotkeys

npm i https://pkg.pr.new/@tanstack/preact-hotkeys@211

@tanstack/preact-hotkeys-devtools

npm i https://pkg.pr.new/@tanstack/preact-hotkeys-devtools@211

@tanstack/react-hotkeys

npm i https://pkg.pr.new/@tanstack/react-hotkeys@211

@tanstack/react-hotkeys-devtools

npm i https://pkg.pr.new/@tanstack/react-hotkeys-devtools@211

@tanstack/solid-hotkeys

npm i https://pkg.pr.new/@tanstack/solid-hotkeys@211

@tanstack/solid-hotkeys-devtools

npm i https://pkg.pr.new/@tanstack/solid-hotkeys-devtools@211

@tanstack/svelte-hotkeys

npm i https://pkg.pr.new/@tanstack/svelte-hotkeys@211

@tanstack/svelte-hotkeys-devtools

npm i https://pkg.pr.new/@tanstack/svelte-hotkeys-devtools@211

@tanstack/vue-hotkeys

npm i https://pkg.pr.new/@tanstack/vue-hotkeys@211

@tanstack/vue-hotkeys-devtools

npm i https://pkg.pr.new/@tanstack/vue-hotkeys-devtools@211

commit: d3195a5

@socket-security

socket-security Bot commented Oct 30, 2026 •

Copy link
Copy Markdown

autofix-ci Bot and others added 3 commits October 30, 2026 17:11
…ables

Typed hotkeys and browser events don't need key aliases or case folding, so
those tables no longer ship in every bundle:

- normalizeKeyName uppercases letters and maps ' ' to Space; other names
  stay as written. Modifier aliases (Ctrl, Cmd, Option) still work.
- validateHotkey warns about keys not written like a known key, using a
  small pattern instead of ALL_KEYS. In development, registering such a
  hotkey warns that it may never fire.
- The recorder rejects whitespace keys directly instead of running
  validateHotkey.
- formatForDisplay accepts hotkeys only; formatKeyForDisplay formats single
  keys such as held keys.
- Key sets are built compactly and are dropped by bundles that don't import
  them.
- Lookups by untrusted names use own properties only, so saved custom
  hotkeys and display labels ignore names such as toString.

typed-behavior.test.ts fingerprints parsing, normalization, validation,
display, matching, recording, and firing for every typed hotkey and a wide
range of real events; the fingerprints match the previous implementation.
@KevinVandy KevinVandy changed the title perf: Drop @tanstack/store, load app hotkeys on demand, and log only in development perf: Shrink bundles by up to 40% by dropping @tanstack/store and the key-name tables Oct 30, 2026
@KevinVandy KevinVandy changed the title perf: Shrink bundles by up to 40% by dropping @tanstack/store and the key-name tables perf: Shrink bundles by dropping @tanstack/store and the key-name tables Oct 30, 2026
autofix-ci Bot and others added 4 commits October 30, 2026 18:12
…egistration to devtools

- Remove formatKeyForDisplay. formatForDisplay accepts typed hotkeys, which
  include single keys, plus modifiers on their own such as 'Shift'. Keys from
  a KeyboardEvent, such as held keys, are passed as { key }, which displays
  them exactly as before.
- Move HotkeyManager.triggerRegistration into the devtools package, built on
  the manager's public API. It was only used by the devtools Trigger button,
  and saves about 100 bytes (brotli) in every app.
@KevinVandy
KevinVandy merged commit 8b93ed5 into main Oct 30, 2026
14 checks passed
@KevinVandy
KevinVandy deleted the fix/devtools-peer-deps branch October 30, 2026 19:31
@github-actions github-actions Bot mentioned this pull request Oct 30, 2026
@ryansolid ryansolid mentioned this pull request Oct 30, 2026
1 of 5 tasks
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant