A MUST-have plugin
April 10, 2026 ยท View on GitHub
Automatically replaces text patterns in your prompts before they're sent to the LLM.
Installation
From npm
Add the published package to your OpenCode config:
{
"$schema": "https://opencode.ai/config.json",
"plugin": ["@ariane-emory/must-have-plugin"]
}
OpenCode installs npm plugins automatically at startup.
The published package also includes MUST-have-plugin.custom-sample.jsonc as a starter config you can copy into ~/.config/opencode/MUST-have-plugin.jsonc.
From Source
npm install
npm run build
Then copy the built file into your OpenCode plugins directory:
mkdir -p ~/.config/opencode/plugins
cp dist/index.js ~/.config/opencode/plugins/MUST-have-plugin.js
The sample config file is available at the package root as MUST-have-plugin.custom-sample.jsonc.
What It Does
Performs case-insensitive string replacements on user-typed prompts. The primary use case is auto-capitalizing RFC2119 keywords (MUST, SHOULD, MAY, etc.) in technical specifications.
Example: Typing "the system must validate input" becomes "the system MUST validate input".
Features
- Case-insensitive matching:
must,Must, andMUSTall match - Word boundary aware: Won't replace
mayinsidemaybe - Multi-word phrases:
must notis matched as a unit (beforemustalone) - Hot reload: Config changes take effect immediately (no restart needed)
- JSONC support: Comments and trailing commas allowed in config file
Scope
- Only replaces text in user-typed prompts
- Does NOT modify file content attached via
@mentions - Does NOT modify slash command output
Configuration
Config file: ~/.config/opencode/MUST-have-plugin.jsonc
If the config file doesn't exist, it's automatically created with RFC2119 defaults.
Default Configuration
{
// Uncomment to enable debug logging (logs appear in OpenCode's log file)
// "debug": true,
"replacements": {
"must": "MUST",
"must not": "MUST NOT",
"required": "REQUIRED",
"shall": "SHALL",
"shall not": "SHALL NOT",
"should": "SHOULD",
"should not": "SHOULD NOT",
"recommended": "RECOMMENDED",
"not recommended": "NOT RECOMMENDED",
"may": "MAY",
"optional": "OPTIONAL"
}
}
Custom Replacements
Add your own replacement pairs to the replacements object:
{
// Uncomment to enable debug logging (view with: tail -f /tmp/opencode-replacer-debug.log)
// "debug": true,
"replacements": {
"bl.md": "~/.config/opencode/supplemental/md/branch-list.md",
"dfp": "Diagnose and fix this problem: ",
"mnm": "Make no mistakes!",
"rfc!": "The key words \"**MUST**\", \"**MUST NOT**\", \"**REQUIRED**\", \"**SHALL**\", \"**SHALL NOT**\", \"**SHOULD**\", \"**SHOULD NOT**\", \"**RECOMMENDED**\", \"**MAY**\", and \"**OPTIONAL**\" in this message are to be interpreted as described in RFC2119.\n\n",
"pto": "push that to origin,",
"mb": "return to the initial branch and merge the new branch back in.",
"always": "**ALWAYS**",
"ever": "**EVER**",
"head": "HEAD",
"may not": "**MAY NOT**",
"may": "**MAY**",
"must always": "**MUST ALWAYS**",
"must never" : "**MUST NEVER**",
"must not" : "**MUST NOT**",
"must": "**MUST**",
"mustn't" : "**MUST NOT**",
"never": "**NEVER**",
"not recommended": "**NOT RECOMMENDED**",
"nothing": "**NOTHING**",
"not": "**NOT**",
"optional": "**OPTIONAL**",
"ought": "**SHOULD**",
"oughtn't": "**SHOULD NOT**",
"recommended": "**RECOMMENDED**",
"required": "**REQUIRED**",
"shall not": "**SHALL NOT**",
"shan't": "**SHALL NOT**",
"shall": "**SHALL**",
"should not": "**SHOULD NOT**",
"shouldn't": "**SHOULD NOT**",
"should": "**SHOULD**",
}
}
Configuration Options
| Option | Type | Default | Description |
|---|---|---|---|
debug | boolean | false | Enable debug logging to OpenCode's log file |
replacements | object | RFC2119 keywords | Key-value pairs for text replacement |
Debug Logging
Logs are written to OpenCode's unified log file using the SDK logging system.
Log location: ~/.local/share/opencode/log/dev.log
Enable debug mode to see what replacements are being made:
- Edit
~/.config/opencode/MUST-have-plugin.jsonc - Uncomment or add
"debug": true - View logs in real-time (filtering by this plugin):
tail -f ~/.local/share/opencode/log/dev.log | grep "MUST-have-plugin"
Or view all recent plugin logs:
grep "MUST-have-plugin" ~/.local/share/opencode/log/dev.log | tail -20
Log Format
Logs use OpenCode's standard format with structured metadata:
INFO 2026-01-20T15:30:42 +2ms service=MUST-have-plugin Plugin loaded
INFO 2026-01-20T15:31:05 +5ms service=MUST-have-plugin Applied 3 replacement(s) replacements={"must":{"value":"MUST","count":2},"should":{"value":"SHOULD","count":1}}
RFC2119 Keywords
The default configuration includes all keywords from RFC 2119, which defines requirement levels for use in technical specifications:
| Keyword | Meaning |
|---|---|
| MUST / REQUIRED / SHALL | Absolute requirement |
| MUST NOT / SHALL NOT | Absolute prohibition |
| SHOULD / RECOMMENDED | Recommended, but valid reasons may exist to ignore |
| SHOULD NOT / NOT RECOMMENDED | Not recommended, but may be acceptable in some cases |
| MAY / OPTIONAL | Truly optional |
Troubleshooting
Replacements not working
- Check that the config file exists:
cat ~/.config/opencode/MUST-have-plugin.jsonc - Verify JSONC syntax is valid (comments and trailing commas are allowed)
- Enable debug mode and check the log file
Unexpected replacements
- Replacements use word boundaries, so
mustwon't match insidecustomer - Multi-word phrases are matched first, so
must notwon't becomeMUST not - Check for typos in your replacement keys
Config changes not taking effect
The plugin re-reads the config on every message, so changes should be immediate. If not:
- Verify you saved the config file
- Check for JSONC syntax errors
- Restart OpenCode as a last resort
Publishing
npm install
npm login
npm run build
npm publish --access public
npm publish does not install dev dependencies for you. Run npm install first in a fresh checkout so typescript and @types/node are available for the prepublishOnly build.
For a preflight check before publishing, run npm publish --dry-run.