Imported from CamParry/astromech (
packages/plugins/AGENTS.md). Install upstream withnpx skills add CamParry/astromech --skill plugins. Copyright stays with the author.
packages/plugins
The first-party plugins, each a separately published package consuming core only through its public surface. Root AGENTS.md applies; this adds what is local to plugins.
- A plugin package may import
astromech,astromech/uiandastromech/ui/app, and nothing else from core.astromechand theastromech/uicomponent kit load under plain Node.astromech/ui/app—useAstromechPlugin,CommandPalette, the AI-context hooks,ApiErrorPanel— does not, so only a source-shipped./admin/*component may import it, never the plugin entry. Every other subpath reachesvirtual:astromech/configand throws at import time. Type-only imports from any subpath are fine because they erase. Everything else arrives onctx.ARCHITECTURE.md("Plugin runtime boundary") has the mechanism. - A plugin's tests live in its own
tests/, run withpnpm -F @astromech/<name> test:run, and resolve core to source throughpackages/astromech/tests/_support/plugin-vitest-config.ts, so the plugin and its tests share one module graph.@astromech/assistantis the exception, resolving core throughdist; its ownvitest.config.tssays why. - Each plugin has a
tsconfig.test.jsonand alintscript, whichpnpm run typecheckandpnpm run lintrun. The test config addstests/and maps core's import paths to source, the same module graph its vitest config builds (the assistant keepsdist, as above).tsconfig.jsonstays source-only, because tsup's declaration build reads it. - A package a plugin's admin component imports goes in
admin.optimizeDeps.include, exceptastromech, its subpaths and React, and it must be a dependency or peer of the plugin. The plugin's own test fails on an import the list misses. - Tables live in
src/tables/and are published as a./tablessubpath where a consumer needs them.astromech plugin:generatediffs them against the package's own migration snapshot.index.tsalso adds them toAstromechPluginTables, so a site'sdbhandle is typed with them;apps/docs/plugins/authoring.mdhas the block. - Plugins own their migrations. Generate into the plugin's own
migrations/; the app merges the chains. - A new platform feature is added to
ctx, never as a published subpath a plugin is expected to import. The rootastromechbarrel is the sanctioned second route — a plugin may already import it, so a feature that is a pure function over a registry ships from there instead of growingctx(getModel/hasModel).