From xh
Authoritative reference for the @xh/hoist React framework -- use when writing, modifying, debugging, or explaining TypeScript/React code that touches Hoist, or when answering how Hoist works. Why this matters: Hoist's API evolves; decorator names shift between versions, `*Config` interfaces look like plain React props but aren't, and `loadAsync`/`addAutorun`/`addReaction` differ from plain MobX. Guessing produces code that type-checks but fails at runtime: silent persistence no-ops, leaked autoruns, ignored props, observable state that never re-renders. TRIGGER when the user mentions a Hoist symbol (`hoistCmp`, `HoistModel`, `HoistService`, `XH`, `Grid`, `Panel`, `TabContainer`, `Store`, `*Config`); a Hoist decorator (`@bindable`, `@managed`, `@persist`, etc.); a Hoist concept (persistence, autorun, reaction, `loadAsync`, refresh, element factory, MobX integration, grid columns); a `*Model.ts`/`*Panel.tsx` file with state/refresh/persistence/grid questions; a change under `client-app/` that introduces or modifies Hoist API usage -- NOT config-only refactors passing values through a Hoist component to a third-party lib (Highcharts, AG-Grid); Hoist docs/orientation/conventions; "Hoist"/"@xh/hoist"/"our framework"/"our app" in any React/TS context. SKIP for plain TypeScript with no Hoist surface, pure React/MobX without Hoist primitives, and files outside `client-app/`. Reach for the reference tools (MCP `mcp__hoist-react__*` or CLI `./bin/hoist-docs`/`./bin/hoist-ts`) first.
How this skill is triggered — by the user, by Claude, or both
Slash command
/xh:using-hoist-react-referenceThis skill is limited to the following tools:
The summary Claude sees in its skill listing — used to decide when to auto-load this skill
You're about to write or modify code that consumes the `@xh/hoist` framework. Consult the reference tools before authoring - Hoist's API surface is large, prop names and decorators are easy to misremember, and a wrong guess produces code that compiles but fails at runtime.
You're about to write or modify code that consumes the @xh/hoist framework. Consult the reference tools before authoring - Hoist's API surface is large, prop names and decorators are easy to misremember, and a wrong guess produces code that compiles but fails at runtime.
Each workflow step has two interfaces. Use the column that matches what's in your tool context.
| Step | MCP tool | CLI command |
|---|---|---|
| Search docs | mcp__hoist-react__hoist-search-docs | ./bin/hoist-docs search "<query>" |
| List docs by category | mcp__hoist-react__hoist-list-docs | ./bin/hoist-docs list -c <category> |
| Read a specific doc | mcp__hoist-react__hoist-search-docs (with id query) | ./bin/hoist-docs read <docId> |
| Search symbols / members | mcp__hoist-react__hoist-search-symbols | ./bin/hoist-ts search "<query>" |
| Get symbol details | mcp__hoist-react__hoist-get-symbol | ./bin/hoist-ts symbol <name> |
| List class members | mcp__hoist-react__hoist-get-members | ./bin/hoist-ts members <name> |
If mcp__hoist-react__* tools are listed in your tool context, prefer them. Otherwise use the CLI column. The MCP tool names look the same regardless of whether the server is running locally or as a deployed remote endpoint - transport is invisible to you.
The CLI launchers are project-local thin wrappers at <project>/bin/hoist-docs and <project>/bin/hoist-ts. They exec the @xh/hoist-provided binaries through client-app/node_modules/.bin/, so the consumer doesn't need to know where the frontend tree lives or change directories. Always invoke them as ./bin/hoist-... from the app project root.
Skip this if you're working through MCP only. For the CLI surface, before the first ./bin/hoist-docs or ./bin/hoist-ts call in a session, verify the launchers are present, current, and functional:
Check that ./bin/hoist-docs and ./bin/hoist-ts exist at the project root.
Read the first 3 lines of each. The second line should be exactly:
# hoist-ai-launcher: hoist-react/v2
Functional smoke check -- invoke one launcher and confirm it resolves its target. Run:
./bin/hoist-docs --help
Exit 0 with help/usage output is success. Exit non-zero with No such file or directory in stderr means the launcher's path resolution is broken (most often the $0 literal was lost in transit and dirname "" resolves to ., sending the exec target one level above the project root). Treat this the same as a missing-or-stale-stamp case.
If any check fails, jump to Installing the CLI launchers, follow it end to end (it's idempotent -- safe to re-run), then return here. Briefly mention the refresh in your next user-facing message (e.g. "refreshed hoist-react launchers to v2").
The preflight runs once per session -- once you've confirmed (or fixed) the launchers, you don't need to re-check on every CLI call.
Standard sequence for any Hoist authoring task:
mcp__hoist-react__hoist-list-docs, mcp__hoist-react__hoist-search-docs with a broad query, or ./bin/hoist-docs index) when you're new to the area. Find the right README."panel modal" finds ModalSupportModel via its JSDoc.get-symbol for full details, or get-members to list a class's properties and methods with types and decorators.filePath when symbol names collide (e.g. View exists in both cmp/viewmanager and data/cube).Look up a component's available props.
mcp__hoist-react__hoist-get-members with name: "GridConfig" (or whatever *Config interface fronts the component)../bin/hoist-ts members GridConfigFind which decorator a model property uses.
mcp__hoist-react__hoist-get-members with name: "<MyModelClass>"../bin/hoist-ts members <MyModelClass>Look up a service method by behavior, not name.
mcp__hoist-react__hoist-search-symbols with query: "fetch loadConfigs" (multi-word AND match against names + JSDoc)../bin/hoist-ts search "fetch loadConfigs"Find the convention for something cross-cutting (persistence, theming, lifecycle).
mcp__hoist-react__hoist-search-docs with query: "persistence MobX integration"../bin/hoist-docs search "persistence MobX integration"Read the docs index.
mcp__hoist-react__hoist-list-docs (or hoist-search-docs with a broad query)../bin/hoist-docs index (shorthand for read docs/README.md).Print coding conventions.
mcp__hoist-react__hoist-search-docs with query: "coding conventions" then read the matching id../bin/hoist-docs conventions"modal" may miss the answer. Use multi-word queries that include behavior keywords ("panel modal") - JSDoc matching surfaces symbols whose names don't include the term.*Config interface with its consuming class. GridModel (the class) and GridConfig (its config interface) both exist. GridModel's properties are runtime state; GridConfig's are configuration knobs. Use members on whichever you actually need - they answer different questions.search-symbols returns multiple matches with the same name (e.g. View in cmp/viewmanager AND data/cube), the tool will hint that you should pass a file path. Do so.Read on framework source. If the reference tools answer the question, prefer them - they expose JSDoc and decorator info more cleanly than reading source. Read the source only as a last resort.Trigger this section when:
The launchers are short shell scripts that exec the @xh/hoist-provided binaries through the npm node_modules/.bin/ symlinks. They live at the project root so they're invocable from the harness's default working directory with no cd required.
client-app/package.json lists @xh/hoist (direct or transitive).client-app/node_modules is populated (i.e. yarn install or npm install has been run from client-app/). The launchers themselves write fine without this, but they'll fail at runtime until packages are installed.If node_modules is missing, surface that to the user as a separate prerequisite step — don't skip the launcher install on its account, the two are independent.
The canonical launcher content lives in two template files shipped alongside this SKILL.md, at templates/hoist-docs and templates/hoist-ts. Copy them byte-for-byte into the project's bin/ rather than transcribing their content -- nested-double-quoted shell expansions like "$(dirname "$0")" can be mangled when content round-trips through serialization layers (the $0 literal has been observed disappearing in some skill-loading paths), and a byte-copy sidesteps that risk entirely.
Use Glob with pattern **/using-hoist-react-reference/templates/hoist-docs to locate the template directory on disk. The match path's parent is <plugin-cache>/.../using-hoist-react-reference/templates/ -- both launchers live there.
Use Bash to copy the templates into the project's bin/ and mark them executable:
mkdir -p bin
cp "<templates-dir>/hoist-docs" bin/hoist-docs
cp "<templates-dir>/hoist-ts" bin/hoist-ts
chmod +x bin/hoist-docs bin/hoist-ts
Substitute <templates-dir> with the directory path you got from the Glob result. Do not use Read + Write to copy content -- that path serializes the file body through tooling that can mangle nested-quoted shell content. cp is byte-exact.
Verify what landed:
grep -F '$0' bin/hoist-docs && grep -F '$0' bin/hoist-ts
Both should match. If either doesn't, the copy didn't preserve the literal $0 and the launcher is broken; do not proceed.
The templates are canonical for hoist-react/v2. If on-disk launchers exist but differ from the templates (different stamp version, missing $0, or any other delta), overwrite them -- the launcher is regenerated deterministically and there's no manual-edit case to preserve.
./bin/hoist-docs --help
./bin/hoist-docs index
./bin/hoist-ts members GridConfig
--help is the launcher-resolution smoke check: exit 0 with usage output means the launcher's path math is working. No such file or directory from --help means the launcher itself is broken (typically the $0 literal was lost during copy -- redo the procedure with Bash cp rather than Read+Write). If --help works but index / members fail with "command not found" or similar from the node_modules/.bin/ target, the client-app/node_modules install hasn't been run.
The launchers are deterministic from this skill's canonical content. Two valid stances:
bin/hoist-docs and bin/hoist-ts in .gitignore). Each fresh checkout's first agent invocation triggers the preflight, which installs them on demand.Either is fine — the preflight handles both states identically.
If neither the MCP tools (mcp__hoist-react__*) nor the CLI launchers (./bin/hoist-docs, ./bin/hoist-ts) are present in your context:
@xh/hoist installed in client-app/), jump to Installing the CLI launchers above and install them. The CLI works in any environment, including MCP-blocked ones, and is the recommended first move.@xh/hoist is installed locally, you may use Read on its package READMEs (e.g. client-app/node_modules/@xh/hoist/core/README.md) — but the recommended fix is to install the launchers via the procedure above.Provides behavioral guidelines to reduce common LLM coding mistakes, focusing on simplicity, surgical changes, assumption surfacing, and verifiable success criteria.
Searches, retrieves, and installs Agent Skills from prompts.chat registry using MCP tools like search_skills and get_skill. Activates for finding skills, browsing catalogs, or extending Claude.
Creates, edits, and optimizes skills for Claude Code, including drafting, evaluating with test prompts, iterating on performance, and improving skill descriptions for better triggering accuracy.
npx claudepluginhub xh/hoist-ai --plugin xh