opsinjs

Agent skill

Install the opsinjs skill so that the clinical and token rules apply to every generation, without pasting them into a prompt each time.

Overview

The MCP server tells an assistant what exists. The skill tells it what it is allowed to do with that. They are complementary and the second one is the half that carries the safety argument.

A skill is a small bundle of instructions that a coding assistant loads automatically when it recognises the project. The opsinjs skill contains four rule files and an eval set, and it lives in this repository at skills/opsinjs/. You can therefore read every word of it before installing it, which is a property worth insisting on for anything that shapes generated health UI.

Install it

npx skills add prashantonomy/opsinjs

Restart your assistant. The skill activates when it finds a components.json with the @opsinjs registry configured, or an opsinjs dependency in package.json.

The skill is also just a directory. If you would rather not install anything from a network, copy skills/opsinjs/ out of this repository into your own project. That directory is five markdown files and a JSON eval set, with no build step and no runtime.

If your tool does not support skills, the rules are ordinary markdown. Read Rules for agents and paste it into your system prompt; you lose the project detection and keep the rules.

What it enforces

Four rule files, each one a prohibition with a check attached.

rules/tokens-not-values.md permits no hex, rgb, pixel radius or millisecond duration in generated code. Every appearance decision resolves to a token or to a utility that references one. The check is a regex over the diff: a literal colour in a generated file is a failure.

rules/status-and-colour.md requires clinical urgency to be expressed as a status level, never as a colour, and never as colour alone. Category and status never colour the same element. The check is structural: a status prop plus a colour class on the same element fails.

rules/never-invent.md holds that a component that is not in the catalogue does not exist, and neither does a prop that is not in the component's source. The rule binds in both directions, because the catalogue can hold two kinds of row. For a planned name the correct answer is to describe the specification, refuse to emit an import, and stop. No id sits there today, so that branch guards the mechanism rather than any current id. For one of the sixty built ids the correct answer is to install it and say, in the same breath, that a shipped API can change in any release and that nobody has reviewed it. A false refusal is the mirror image of an invention, and the rule file treats it as the same class of mistake.

rules/registry.md says never to emit add @opsinjs/<name> without first checking that components.json registers the namespace, and to offer the one-line addition before the install command rather than as a footnote after it. The failure it prevents is specific: an unresolvable namespace produces an error that reads like a network problem, and the next thing that happens is somebody hand-writes a component and calls it opsinjs. The rule also forbids claiming an item has files when the registry says it has none.

What it reads from your project

The skill is project-aware, which is what makes it more useful than a pasted prompt. On each activation it reads your configuration so that generated code matches your project's conventions rather than the documentation's. Configuration here means framework, aliases, icon library, base library, configured registries, and which components you have already installed.

It reads. It does not write, and it does not send your source anywhere.

What it deliberately does not do

It also does not lint your existing code. It shapes generation. For enforcement across a codebase, the lint rules described in Handbook tooling are the right instrument, and they are specified rather than built.

Verify it worked

The assistant refuses to invent

Ask for a component that is not in the catalogue at all. A correct response says it does not exist and stops. A confident API means the skill did not load. Then ask for one of the built ids. A refusal there is the opposite failure, and it means the skill loaded against a stale idea of what is built.

It reaches for tokens

Ask for "a card with a warning colour". Correct output uses the status vocabulary and a token-backed class. Output containing #f59e0b means the tokens-not-values rule is not active.

It knows your project

Ask what registries are configured. If it can answer, project detection is working; if it describes the documentation's setup instead of yours, it is running on general knowledge.

Troubleshooting

The skill does not activate. It looks for a components.json. A project without one will not trigger it, whether that is a plain library or a monorepo package. Add the file or paste the rules.

It activates but the rules are ignored on long tasks. Rules compete with a long conversation for attention. Re-anchoring helps: ask the assistant to restate the opsinjs rules before a generation step.

The rules conflict with our house style. Fork the skill. It is four markdown files in this repository, and a fork that keeps the clinical rules while changing the mechanical ones is a reasonable thing to maintain.

It suggested code that does not compile. Check which id and what shape. There is no published package, so an import from @opsinjs/react is always wrong and is a rule failure worth reporting as an eval case. A component copied in from the registry that does not compile is a different bug: the usual cause is a missing @/lib/utils, which shadcn init writes and a hand-made components.json does not, and it belongs in the component's tracker rather than the skill's.

Next

  • Rules for agents has the rules in full, readable form.
  • Evals shows how the skill's effect is measured rather than assumed.
  • Prompt recipes covers prompts written to work with the skill rather than against it.

On this page