omakit 0.1.9 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +44 -217
- package/package.json +2 -2
- package/skills/omarchy-plugin-check/SKILL.md +102 -0
- package/skills/omarchy-plugin-submit/SKILL.md +4 -0
- package/skills/omarchy-plugin-weigh/SKILL.md +128 -0
- package/tools/marketplace/README.md +18 -1
- package/tools/marketplace/cli.mjs +165 -8
- package/tools/marketplace/completion-check.mjs +224 -0
- package/tools/marketplace/completion.mjs +103 -25
- package/tools/marketplace/doctor.mjs +9 -1
- package/tools/marketplace/options.mjs +72 -0
- package/tools/marketplace/paths.mjs +13 -0
- package/tools/marketplace/report.mjs +3 -2
- package/tools/marketplace/setup.mjs +90 -24
- package/tools/marketplace/upgrade.mjs +31 -5
- package/tools/marketplace/usage.mjs +30 -4
- package/tools/weigh/audit.mjs +666 -0
- package/tools/weigh/commands.mjs +69 -0
- package/tools/weigh/config.mjs +131 -0
- package/tools/weigh/confirm.mjs +32 -0
- package/tools/weigh/contract.mjs +167 -0
- package/tools/weigh/list.mjs +90 -0
- package/tools/weigh/proc.mjs +150 -0
- package/tools/weigh/report.mjs +196 -0
- package/tools/weigh/stats.mjs +63 -0
package/README.md
CHANGED
|
@@ -2,51 +2,13 @@
|
|
|
2
2
|
<img src="docs/media/banner.gif" alt="omakit" width="440">
|
|
3
3
|
</p>
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
The safe place to find out: everything knowable about an Omarchy Quattro plugin submission before you post it, on your own machine. Agent-first, read-only against the marketplace, posts nothing, zero dependencies.
|
|
6
6
|
|
|
7
|
-
|
|
8
|
-
before you post it:** the tree, the manifest, the form, the commit, and the
|
|
9
|
-
marketplace's own security baseline with its outcome reported as it is. A
|
|
10
|
-
submission is judged at one exact commit and drifts from it the moment you
|
|
11
|
-
push; `watch` says when that has happened. All of it runs on your own machine
|
|
12
|
-
and publishes nothing: no issue, no comment, no label, nobody's attention spent
|
|
13
|
-
until you choose to.
|
|
7
|
+
[](https://github.com/tcballard/omarchy-badges) [](https://www.npmjs.com/package/omakit) [](https://github.com/mtolhuys/omakit/actions/workflows/ci.yml) [](https://socket.dev/npm/package/omakit)
|
|
14
8
|
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
and warned about a fourth: it ships instruction files an agent will read once
|
|
19
|
-
installed. **103 marketplace issues mention exactly that, and no automated check
|
|
20
|
-
reports it, so today an author finds out from a human review round.** It is a
|
|
21
|
-
warning and not a refusal, because the marketplace does list plugins that ship
|
|
22
|
-
them: 6 of 34 inspected do, at the commit that was listed.
|
|
23
|
-
|
|
24
|
-
```bash
|
|
25
|
-
omakit submit <plugin-repo> --category Widgets --tags bar,quickshell
|
|
26
|
-
```
|
|
27
|
-
|
|
28
|
-
Fifteen checks, each naming its source and, when it fails, the measured reason it
|
|
29
|
-
exists. A blocking failure produces no submission body at all, because a refusal
|
|
30
|
-
that still hands you the body is only a suggestion.
|
|
31
|
-
|
|
32
|
-
## Why it exists
|
|
33
|
-
|
|
34
|
-
Four numbers, all measured on public marketplace data on 2026-09-12. Method,
|
|
35
|
-
limits and the rest of the figures: [docs/MEASUREMENTS.md](docs/MEASUREMENTS.md).
|
|
36
|
-
|
|
37
|
-
| Measured | Consequence |
|
|
38
|
-
| --- | --- |
|
|
39
|
-
| 39 submissions fell out on the title prefix alone, and 11 more are malformed in the body, one by a single word | the format is generated from the pinned form and judged by the marketplace's own parser |
|
|
40
|
-
| 1,215 of the 2,916 listings with a recorded baseline needed a human to look, because of a capability | the official baseline runs locally on the exact commit first, and names the capability |
|
|
41
|
-
| 103 issues mention agent-control files, which no automated check reports | submit names every one with its remedy, before a reviewer has to |
|
|
42
|
-
| 73% of parked submissions have a HEAD the marketplace never saw; 46% of the maintainer's own revalidation requests never produced one | a validation watch that names the one action which re-runs validation |
|
|
43
|
-
|
|
44
|
-
It does not claim to unblock the maintainer. His review writing barely repeats,
|
|
45
|
-
his median time from submission to publication is hours, and the queue waiting on
|
|
46
|
-
him is a median half a day old. The honest size of what this saves him is the
|
|
47
|
-
staleness paragraph he has written by hand on 358 issues, roughly 5.5% of his
|
|
48
|
-
review writing. The rest of the benefit is the submitter's.
|
|
49
|
-
[docs/MARKETPLACE.md](docs/MARKETPLACE.md) states that in full.
|
|
9
|
+
`omakit` is a zero-dependency Node CLI that checks an Omarchy Quattro plugin submission on your machine.
|
|
10
|
+
It is for a coding agent or a person submitting a plugin.
|
|
11
|
+
It never posts to the marketplace or writes into a plugin tree.
|
|
50
12
|
|
|
51
13
|
## Install
|
|
52
14
|
|
|
@@ -55,203 +17,65 @@ npm install --global omakit
|
|
|
55
17
|
omakit setup
|
|
56
18
|
```
|
|
57
19
|
|
|
58
|
-
|
|
59
|
-
(measured: an npm global prefix under `~/.local/share` whose `bin` no shell
|
|
60
|
-
searched). Run `"$(npm prefix --global)/bin/omakit" setup` once: it prints the
|
|
61
|
-
one line that puts that directory on PATH for the shell in `$SHELL`, and the
|
|
62
|
-
rc file to keep it in; `omakit doctor` reports the same as `omakit.path`.
|
|
63
|
-
Nothing writes to your rc file.
|
|
20
|
+
See [docs/INSTALL.md](docs/INSTALL.md) for the clone route, PATH, requirements and upgrading.
|
|
64
21
|
|
|
65
|
-
|
|
22
|
+
## Commands
|
|
23
|
+
|
|
24
|
+
| Command | What it does |
|
|
25
|
+
| --- | --- |
|
|
26
|
+
| [`omakit setup`](docs/COMMANDS.md) | The environment, the pin, tab completion, and what to try first. |
|
|
27
|
+
| [`omakit submit <plugin-repo>`](docs/SUBMIT.md) | Every check, the issue title and body; asks for a category and tags at a terminal. |
|
|
28
|
+
| [`omakit watch <issue-url>`](docs/VALIDATION_WATCH.md) | The commit the marketplace validated, against the plugin's current HEAD. |
|
|
29
|
+
| [`omakit verify <plugin-repo>`](docs/COMMANDS.md) | The official security baseline over the local transport; `--json` for the document. |
|
|
30
|
+
| [`omakit parity`](docs/COMMANDS.md) | The baseline over GitHub versus the local transport, on real listings; writes the evidence. |
|
|
31
|
+
| [`omakit weigh <plugin>`](docs/WEIGH.md) | What a plugin weighs on the shell, measured by restarting it without and with the plugin; asks first. |
|
|
32
|
+
| [`omakit doctor`](docs/COMMANDS.md) | What is installed, what is pinned, and what has moved. |
|
|
33
|
+
| [`omakit pin`](docs/COMMANDS.md) | What setup does for the pin, on its own. |
|
|
34
|
+
| [`omakit upgrade`](docs/COMMANDS.md) | Updates omakit through its own installer: npm, or a fast-forward. |
|
|
35
|
+
| [`omakit help --agent`](docs/COMMANDS.md) | The operating instructions, for the agent running this. |
|
|
36
|
+
|
|
37
|
+
### `submit`
|
|
66
38
|
|
|
67
39
|
```bash
|
|
68
|
-
|
|
69
|
-
ln -s ~/.local/share/omakit/bin/omakit ~/.local/bin/omakit
|
|
70
|
-
omakit setup
|
|
40
|
+
omakit submit <plugin-repo> --category Widgets --tags bar,quickshell
|
|
71
41
|
```
|
|
72
42
|
|
|
73
|
-
|
|
74
|
-
| --- | --- |
|
|
75
|
-
| Node 22 or newer | the tool is plain ESM with no dependencies and no build step. A stock Omarchy has Node and npm through `mise`, along with `git`, `gh` and `ttfx` |
|
|
76
|
-
| `git` | the pin, and reading a subject's tree at an exact commit |
|
|
77
|
-
| network, once | `omakit pin`. After that, `submit` and `verify` on a local repository need none at all |
|
|
78
|
-
| 15 MB on disk | the pinned checkout, in `$XDG_CACHE_HOME/omakit/marketplace`, or `~/.cache/omakit/marketplace` |
|
|
43
|
+
It decides whether the plugin is ready, refused, or already listed; [103 issues mention agent-control files that no automated check reports](docs/MEASUREMENTS.md).
|
|
79
44
|
|
|
80
|
-
|
|
81
|
-
`npm` for the package, at the exact version the registry names, and a
|
|
82
|
-
fast-forward for a clone. `omakit doctor` says when a newer version is
|
|
83
|
-
published. Nothing in omakit fetches and runs its own replacement, and
|
|
84
|
-
`omarchy-mise-install npm:omakit` would, so it is not the way in.
|
|
45
|
+

|
|
85
46
|
|
|
86
|
-
|
|
47
|
+
Read more: [docs/SUBMIT.md](docs/SUBMIT.md).
|
|
87
48
|
|
|
88
|
-
|
|
49
|
+
### `watch`
|
|
89
50
|
|
|
90
51
|
```bash
|
|
91
52
|
omakit watch <submission-issue-url>
|
|
92
53
|
```
|
|
93
54
|
|
|
94
|
-
|
|
95
|
-
findings. It is stuck because the marketplace validated one exact commit, and
|
|
96
|
-
the only action that makes it validate a newer one is editing the issue body. Pushing the fix does
|
|
97
|
-
nothing. Commenting "fixed in `abc123`" does nothing. **73% of the 464
|
|
98
|
-
submissions parked in their author's court have a default-branch HEAD the
|
|
99
|
-
marketplace never saw.**
|
|
55
|
+
It decides whether the marketplace validated the plugin's current commit; [73% of parked submissions have a HEAD the marketplace never saw](docs/MEASUREMENTS.md).
|
|
100
56
|
|
|
101
|
-
|
|
57
|
+

|
|
58
|
+
|
|
59
|
+
Read more: [docs/VALIDATION_WATCH.md](docs/VALIDATION_WATCH.md).
|
|
102
60
|
|
|
103
|
-
|
|
104
|
-
owner's behalf. Zero dependencies, plain ESM, one entry point, no build step.
|
|
61
|
+
### `weigh`
|
|
105
62
|
|
|
106
63
|
```bash
|
|
107
|
-
omakit
|
|
108
|
-
omakit submit <plugin-repo> # every check, the issue title and body; asks for a category and tags at a terminal
|
|
109
|
-
omakit watch <issue-url> # the commit the marketplace validated, against the plugin's current HEAD
|
|
110
|
-
omakit verify <plugin-repo> # the official security baseline over the local transport; --json for the document
|
|
111
|
-
omakit parity # the baseline over GitHub versus the local transport, on real listings; writes the evidence
|
|
112
|
-
omakit doctor # what is installed, what is pinned, and what has moved
|
|
113
|
-
omakit pin # what setup does for the pin, on its own
|
|
114
|
-
omakit upgrade # updates omakit through its own installer: npm, or a fast-forward
|
|
115
|
-
omakit help --agent # the operating instructions, for the agent running this
|
|
64
|
+
omakit weigh <plugin-id-or-dir>
|
|
116
65
|
```
|
|
117
66
|
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
`omakit setup` checks the environment, fetches the marketplace checkout that
|
|
121
|
-
every rule is read from, installs tab completion for the shell you run it from
|
|
122
|
-
(bash, zsh or fish, read from `$SHELL`), and tells you what to try first. It is
|
|
123
|
-
idempotent. The fetch takes about 2 seconds and 15 MB, because it takes only the
|
|
124
|
-
seven files omakit reads out of that repository rather than the 325 MB it is at
|
|
125
|
-
that commit. The completion script knows the subcommands and their flags,
|
|
126
|
-
completes a directory for `<target>`, and offers the categories and tags the
|
|
127
|
-
pin's submission form actually has.
|
|
128
|
-
|
|
129
|
-
`omakit verify` prints the official baseline result alone, with no Omakit
|
|
130
|
-
check around it: the subject, the pin, the transport and what the local
|
|
131
|
-
adapter assumes, then the marketplace's own outcome, each finding as a block
|
|
132
|
-
with its rule id, whether it blocks publication under the pinned policy, the
|
|
133
|
-
file and line, and the official text verbatim, then the marketplace's own
|
|
134
|
-
statement. `--json` prints the document itself, unchanged from earlier
|
|
135
|
-
releases, and `--out <file>` writes it; agents and the skills use those.
|
|
136
|
-
|
|
137
|
-
`omakit submit` reads the marketplace's registry first, and a run has three
|
|
138
|
-
outcomes. `READY`, exit 0: every blocking check passed and the title and body
|
|
139
|
-
follow. `REFUSED`, exit 1: a blocking check failed and no body is produced.
|
|
140
|
-
`LISTED`, exit 0: the plugin is already listed by its own repository (the
|
|
141
|
-
manifest id is in the catalog, and the listing's repository is the subject's
|
|
142
|
-
declared `origin`, compared as owner and name), so the submission form is not
|
|
143
|
-
the route. Nothing is wrong and nothing was refused: `identity.available`
|
|
144
|
-
passes with the listing's record (since when, which commit, verified or not),
|
|
145
|
-
the five checks that exist only for the body are omitted, nothing is asked,
|
|
146
|
-
and the closing block names the commit the marketplace lists, the local
|
|
147
|
-
commit, whether they are the same, and the marketplace's verification form
|
|
148
|
-
with the choice that lists a newer commit, read from the pin's
|
|
149
|
-
`verify-plugin.yml`. Measured on 0.1.6: this state printed `FAIL
|
|
150
|
-
identity.available`, `REFUSED`, and "Fix it, then run submit again" under a
|
|
151
|
-
remedy that said there was nothing to submit. An id taken by another
|
|
152
|
-
repository, a retired id or a reserved one is still refused. In `--json`, the
|
|
153
|
-
outcome is `outcome: "ready" | "refused" | "listed"`, `ready` stays a boolean
|
|
154
|
-
that is true for the first only, and a listed run carries a `listing` object.
|
|
155
|
-
|
|
156
|
-
An unlisted plugin needs a category and tags, and they are an editorial
|
|
157
|
-
choice nobody else can make: at a terminal it asks, once each, with the form's
|
|
158
|
-
own lists numbered and the marketplace's own default for the manifest's kinds
|
|
159
|
-
offered where it is on the list; in a pipe, from an agent, or with `--json` it
|
|
160
|
-
is the usage error with the same lists, exit 2. A listed plugin is asked for
|
|
161
|
-
neither. A `READY` or `REFUSED` report ends with the command line that repeats
|
|
162
|
-
the run without asking, and `--json` carries it as `reproduce`.
|
|
163
|
-
|
|
164
|
-
There is nothing to authenticate. If you have `gh auth login` done, omakit
|
|
165
|
-
reads that credential for GET requests and stores nothing; a token in
|
|
166
|
-
`GH_TOKEN` or `GITHUB_TOKEN` reaches it the same way, because `gh` honours
|
|
167
|
-
those itself. Without either, `watch` and `parity` share GitHub's
|
|
168
|
-
60-requests-an-hour unauthenticated allowance; `submit` reads two things
|
|
169
|
-
online, the subject's default-branch HEAD and the marketplace's current
|
|
170
|
-
registry, and `--offline` turns both off; `verify` on a local repository does
|
|
171
|
-
not touch the network at all (a `<url>@<sha>` target is fetched once, over
|
|
172
|
-
git, into the cache). omakit reads no environment variable of its own, and
|
|
173
|
-
`omakit doctor` names the credential source it found, or that it found none.
|
|
174
|
-
|
|
175
|
-
Every colour omakit prints is an ANSI palette index, so your Omarchy theme
|
|
176
|
-
decides what it looks like, and nothing is said by colour alone. What the
|
|
177
|
-
terminal shows and why is [docs/TUI.md](docs/TUI.md); which index each role
|
|
178
|
-
gets, measured over all 32 installed themes, is
|
|
179
|
-
[docs/PALETTE.md](docs/PALETTE.md).
|
|
180
|
-
|
|
181
|
-
## What it is doing
|
|
182
|
-
|
|
183
|
-
Nothing about the submission format is written down in this repository. The
|
|
184
|
-
title prefix, the six form headings in order, the nine categories, the thirteen
|
|
185
|
-
tags and the exact text of the five checklist items are all read from
|
|
186
|
-
`.github/ISSUE_TEMPLATE/submit-plugin.yml` in a marketplace checkout pinned to an
|
|
187
|
-
exact commit. The rendered body is then handed to the marketplace's own
|
|
188
|
-
`parseCurrentSubmission` from that same commit. If it accepts the body here, it
|
|
189
|
-
accepts it there. The one exception is data, not rules: the registry and the
|
|
190
|
-
catalog that say which ids and repositories are already listed are read from
|
|
191
|
-
the marketplace's current HEAD when the network is there, because the pin's
|
|
192
|
-
copy is stale within hours (4,201 of 4,293 commits in 30 days touched only
|
|
193
|
-
`registry.json`), and from the pin with `--offline`.
|
|
67
|
+
It measures what a plugin weighs on the shell, CPU and child processes, against a baseline taken the same minute; [in the lab, a 180 ms timer fixture measured 2.73% CPU above a 0.13% floor](docs/MEASUREMENTS.md).
|
|
194
68
|
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
pinned commit instead of reimplementing their rules, where a different
|
|
198
|
-
language would mean a copy that can drift.
|
|
199
|
-
|
|
200
|
-
The security baseline is the marketplace's own code, imported unmodified and run
|
|
201
|
-
over a local snapshot with no network. Omakit adds no rule, renames no outcome,
|
|
202
|
-
and never restates the result as a safety claim: the baseline does no data-flow
|
|
203
|
-
analysis and is not a security review, and the output says so in the
|
|
204
|
-
marketplace's own words.
|
|
205
|
-
|
|
206
|
-
Every check is labelled. `[marketplace-pin]` is the marketplace's rule, read from
|
|
207
|
-
the pin. `[omakit]` is this project's own check, derived from public issue data.
|
|
208
|
-
Those are not marketplace policy and do not claim to be.
|
|
209
|
-
|
|
210
|
-
## Updating
|
|
211
|
-
|
|
212
|
-
Two different things could mean "upgrade" here, and only one of them may ever
|
|
213
|
-
move on its own. That distinction is now enforced rather than argued.
|
|
214
|
-
|
|
215
|
-
**The tool:**
|
|
216
|
-
|
|
217
|
-
```bash
|
|
218
|
-
omakit upgrade # the npm package, or a clone: through its own installer
|
|
219
|
-
omakit upgrade --dry-run
|
|
69
|
+
```text
|
|
70
|
+
Weighs no CPU above the floor (0.13%) and runs 2 child processes using 8.2 MB and 0.1% CPU, on Omarchy 4.0.0.alpha, measured with omakit weigh on 2026-09-14
|
|
220
71
|
```
|
|
221
72
|
|
|
222
|
-
It is
|
|
223
|
-
about: it never fetches and runs its own replacement. On an npm install it asks
|
|
224
|
-
the registry for the newest version and, if that is newer, runs the `npm` on
|
|
225
|
-
PATH with frozen arguments (`npm install --global --ignore-scripts omakit@<that
|
|
226
|
-
version>`, never `@latest`, never with sudo), and it refuses when the npm on
|
|
227
|
-
PATH is not the one that installed it. On a clone it fast-forwards from the
|
|
228
|
-
remote you cloned it from, and refuses a dirty tree, a detached HEAD, a remote
|
|
229
|
-
that is not this repository, and anything that is not a fast-forward. In every
|
|
230
|
-
refusal it names what to run yourself. `git -C ~/.local/share/omakit pull`
|
|
231
|
-
still works on a clone and does the same thing.
|
|
73
|
+
It restarts your shell and asks first. Memory is a shell fact; CPU and child processes are the weight.
|
|
232
74
|
|
|
233
|
-
|
|
234
|
-
either: a test asserts that its source does not so much as mention the pin or
|
|
235
|
-
the cache. Bumping it changes where the submission contract and the baseline
|
|
236
|
-
policy are read from, and the procedure in
|
|
237
|
-
[docs/UPSTREAM_CONTRACT.md](docs/UPSTREAM_CONTRACT.md) ends in re-proving
|
|
238
|
-
transport parity and committing the evidence. `omakit doctor` tells you when the
|
|
239
|
-
pin is behind in something omakit reads from it, names which paths changed,
|
|
240
|
-
and then leaves it alone: `registry.json` and `site/catalog.json` moving is
|
|
241
|
-
fine, because those are read live from HEAD (about 140 commits a day touch
|
|
242
|
-
only `registry.json`, so "behind" alone would be true of every run); the
|
|
243
|
-
marketplace's code or forms moving is a note, and what you can do about it
|
|
244
|
-
is run `omakit upgrade`, since a newer omakit may already carry the new pin,
|
|
245
|
-
and otherwise open an issue naming the paths. That the
|
|
246
|
-
pin can go stale unnoticed is the same defect class `omakit watch` reports, so it
|
|
247
|
-
would be poor form to hide it here.
|
|
75
|
+
Read more: [docs/WEIGH.md](docs/WEIGH.md).
|
|
248
76
|
|
|
249
77
|
## Evidence, not claims
|
|
250
78
|
|
|
251
|
-
```bash
|
|
252
|
-
npm test # node --test, no dependencies; green from `git archive` too
|
|
253
|
-
```
|
|
254
|
-
|
|
255
79
|
| Claim | Proof |
|
|
256
80
|
| --- | --- |
|
|
257
81
|
| The local transport produces the marketplace's own result | 30 of 30 identical, [docs/evidence/parity/](docs/evidence/parity/) |
|
|
@@ -259,17 +83,20 @@ npm test # node --test, no dependencies; green from `git archive` too
|
|
|
259
83
|
| The generated body is well formed | the marketplace's own parser, `tests/unit/issue.test.mjs` |
|
|
260
84
|
| Nothing writes to the marketplace | `tests/unit/read-only.test.mjs`, over every source file |
|
|
261
85
|
| No agent-control file can reach a plugin | `tests/unit/self-containment.test.mjs` |
|
|
86
|
+
| `weigh` restores `shell.json` on every exit path, and runs a frozen list of Omarchy commands | `tests/unit/weigh.test.mjs` against a fake `/proc` and stub commands, `tests/unit/read-only.test.mjs` |
|
|
262
87
|
| The GIFs above are real output | captures and renderer in [docs/media/](docs/media/) |
|
|
263
88
|
|
|
264
|
-
Committed evidence records a digest of each side rather than the results
|
|
265
|
-
themselves: findings about a specific third-party plugin are not this project's
|
|
266
|
-
to publish.
|
|
89
|
+
Committed evidence records a digest of each side rather than the results themselves, because findings about a specific third-party plugin are not this project's to publish.
|
|
267
90
|
|
|
268
91
|
## Documentation
|
|
269
92
|
|
|
270
93
|
| Document | For |
|
|
271
94
|
| --- | --- |
|
|
95
|
+
| [docs/INSTALL.md](docs/INSTALL.md) | install details, PATH, requirements, upgrading, and what Socket reports and why |
|
|
96
|
+
| [docs/HOW.md](docs/HOW.md) | what omakit is doing, why it uses Node, the baseline and check labels |
|
|
97
|
+
| [docs/COMMANDS.md](docs/COMMANDS.md) | command details, authentication and network behaviour |
|
|
272
98
|
| [docs/SUBMIT.md](docs/SUBMIT.md) | every check and what it decides |
|
|
99
|
+
| [docs/WEIGH.md](docs/WEIGH.md) | what `weigh` measures, the noise floor, the `shell.json` mutation and its restore, and the JSON contract |
|
|
273
100
|
| [docs/VALIDATION_WATCH.md](docs/VALIDATION_WATCH.md) | the validation watch: what the marketplace validated, and what moves it |
|
|
274
101
|
| [docs/MEASUREMENTS.md](docs/MEASUREMENTS.md) | every number, its method and its limits |
|
|
275
102
|
| [docs/UPSTREAM_CONTRACT.md](docs/UPSTREAM_CONTRACT.md) | the seam, the pin, the boundaries |
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "omakit",
|
|
3
|
-
"version": "0.1
|
|
4
|
-
"description": "The safe place to find out: everything knowable about an Omarchy Quattro plugin submission before you post it, on your own machine. Agent-first, read-only, posts nothing, zero dependencies.",
|
|
3
|
+
"version": "0.2.1",
|
|
4
|
+
"description": "The safe place to find out: everything knowable about an Omarchy Quattro plugin submission before you post it, on your own machine. Agent-first, read-only against the marketplace, posts nothing, zero dependencies.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": "Maarten Tolhuijs",
|
|
7
7
|
"keywords": [
|
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: omarchy-plugin-check
|
|
3
|
+
description: Check an Omarchy Quattro plugin while building or changing it, before committing or pushing. Use whenever you create, edit, refactor or test an Omarchy plugin, when asked whether a plugin is marketplace-ready, or before any push to its default branch. Runs the marketplace's own security baseline and submission checks locally, read-only, and reports what the marketplace would refuse.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Checking a plugin while you build it
|
|
7
|
+
|
|
8
|
+
## Run this the way you run a test suite
|
|
9
|
+
|
|
10
|
+
After every meaningful change to an Omarchy plugin, run both, from the
|
|
11
|
+
plugin's repository root or with its path:
|
|
12
|
+
|
|
13
|
+
```bash
|
|
14
|
+
omakit verify <path-to-the-plugin-repo> --json
|
|
15
|
+
omakit submit <path-to-the-plugin-repo> --category <category> --tags <a,b> --json --offline
|
|
16
|
+
```
|
|
17
|
+
|
|
18
|
+
`verify` is the marketplace's own security baseline over this exact commit,
|
|
19
|
+
verbatim, with no Omakit check around it. `submit` is every pre-submission
|
|
20
|
+
check the marketplace applies, rendered from the marketplace's own form and
|
|
21
|
+
judged by the marketplace's own parser.
|
|
22
|
+
|
|
23
|
+
**Always pass `--category` and `--tags`.** A run without them asks a person
|
|
24
|
+
at a terminal, and an agent must never wait on a keyboard. If you do not know
|
|
25
|
+
the allowed values, run once without them in a pipe or with `--json`: that is
|
|
26
|
+
a usage error (exit 2) whose message lists the controlled values, read from
|
|
27
|
+
the pinned form. Pick the category and tags with the owner; they are an
|
|
28
|
+
editorial choice about where the plugin belongs.
|
|
29
|
+
|
|
30
|
+
`--offline` belongs in this loop and nowhere else: it skips the one check that
|
|
31
|
+
needs the network and reads the listed ids from the pin. For the real
|
|
32
|
+
submission, drop it, and use `skills/omarchy-plugin-submit/SKILL.md`.
|
|
33
|
+
|
|
34
|
+
## If omakit is not installed
|
|
35
|
+
|
|
36
|
+
```bash
|
|
37
|
+
npm install --global omakit # Omarchy ships Node and npm through mise
|
|
38
|
+
omakit doctor # node, git, the pin, the credential source, and whether omakit is on PATH
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
If `omakit` is not found after the install, run
|
|
42
|
+
`"$(npm prefix --global)/bin/omakit" setup`: it prints the one line that puts
|
|
43
|
+
npm's bin on PATH for the shell in `$SHELL`. Keep it current with
|
|
44
|
+
`omakit upgrade`. The first `submit` or `verify` needs the pin: `omakit pin`
|
|
45
|
+
fetches a sparse read-only checkout of one marketplace commit under
|
|
46
|
+
`$XDG_CACHE_HOME/omakit/marketplace` (or `~/.cache/omakit/marketplace`).
|
|
47
|
+
|
|
48
|
+
## Reading the result
|
|
49
|
+
|
|
50
|
+
`submit --json` ends with `outcome`:
|
|
51
|
+
|
|
52
|
+
- `ready`, exit 0: every blocking check passed. The plugin would be accepted
|
|
53
|
+
by the marketplace's automated checks as it is now.
|
|
54
|
+
- `refused`, exit 1: a blocking check failed. `blocking` lists the root
|
|
55
|
+
causes; each check carries `detail`, `paths`, `remedy` and `why`.
|
|
56
|
+
- `listed`, exit 0: the plugin is already listed by this repository.
|
|
57
|
+
`listing` names the reviewed commit and whether the local commit is it.
|
|
58
|
+
|
|
59
|
+
Each check has a `verdict`: `pass`, `fail`, `unknown` (it could not run
|
|
60
|
+
because a check it depends on failed; fix that one first) or `skipped` (not
|
|
61
|
+
run under `--offline`). `severity` is `blocking` or `advisory`; an advisory
|
|
62
|
+
check never turns `ready` into `refused`.
|
|
63
|
+
|
|
64
|
+
Each check names a `source`. `marketplace-pin` is the marketplace's own rule,
|
|
65
|
+
read from the pinned checkout. `omakit` is this tool's own check, derived
|
|
66
|
+
from public issue data with the measurement in `why`. Never describe an
|
|
67
|
+
`omakit` check to the owner as a marketplace requirement.
|
|
68
|
+
|
|
69
|
+
Fix the cause the remedy names. Do not work around a check, do not strip files
|
|
70
|
+
from the owner's tree on your own, and never change the plugin id to get past
|
|
71
|
+
`identity.available` when the listing is this repository's own.
|
|
72
|
+
|
|
73
|
+
## What the baseline result means
|
|
74
|
+
|
|
75
|
+
`verify` and the `baseline.preflight` check report the official outcome:
|
|
76
|
+
|
|
77
|
+
- `passed`: nothing in the baseline holds the plugin back.
|
|
78
|
+
- `review-required`: no findings, but one or more of the seven capabilities is
|
|
79
|
+
present, so a maintainer must look at this exact commit. Not a defect; worth
|
|
80
|
+
explaining in the submission's `--notes` rather than hiding.
|
|
81
|
+
- `needs-fixes`: findings, each with a rule id, the file, and the marketplace's
|
|
82
|
+
own remedy text. Only `sudoers-dangerous-passwordless-command` and
|
|
83
|
+
`privileged-process-control-from-shared-temp` block publication under the
|
|
84
|
+
current enforcement mode; the rest a maintainer may accept for that commit.
|
|
85
|
+
Fixing them first avoids a human round either way.
|
|
86
|
+
|
|
87
|
+
Never restate any of this as a safety claim. The baseline performs no data-flow
|
|
88
|
+
analysis and is not a security review; the output says so in the marketplace's
|
|
89
|
+
own words, and so should you.
|
|
90
|
+
|
|
91
|
+
## The commit rule
|
|
92
|
+
|
|
93
|
+
The marketplace validates the pushed default-branch HEAD, not whatever is
|
|
94
|
+
checked out locally. Run the check on the commit that will be pushed, then
|
|
95
|
+
commit and push before the real submission. Of the 464 submissions parked in
|
|
96
|
+
their author's court, 73% have a HEAD the marketplace never saw; that is the
|
|
97
|
+
round this loop is meant to prevent.
|
|
98
|
+
|
|
99
|
+
## When the plugin is ready
|
|
100
|
+
|
|
101
|
+
Hand over to `skills/omarchy-plugin-submit/SKILL.md`. The owner decides
|
|
102
|
+
whether to submit, and you never open the issue yourself.
|
|
@@ -32,6 +32,10 @@ omakit pin # once, and after any pin change: fetches the pinned marketplace
|
|
|
32
32
|
omakit submit <path-to-the-plugin-repo> --category <category> --tags <a,b>
|
|
33
33
|
```
|
|
34
34
|
|
|
35
|
+
While a plugin is still being built or changed, run the check loop in
|
|
36
|
+
`skills/omarchy-plugin-check/SKILL.md` instead; this skill is for the
|
|
37
|
+
submission itself.
|
|
38
|
+
|
|
35
39
|
The pin is a sparse read-only checkout of one marketplace commit under
|
|
36
40
|
`$XDG_CACHE_HOME/omakit/marketplace` (or `~/.cache/omakit/marketplace`). Every
|
|
37
41
|
rule is read from it; nothing about the format is written in the tool.
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: omarchy-plugin-weigh
|
|
3
|
+
description: Weigh an Omarchy Quattro plugin on the shell, in CPU and child processes, by restarting the shell without it and with it. Use before a submission, after a change that adds a timer, a process or a file watcher, or when asked how heavy a plugin is. Restarts the person's shell, so it must never run without their explicit agreement.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# What a plugin weighs on the shell
|
|
7
|
+
|
|
8
|
+
## The one thing to get right
|
|
9
|
+
|
|
10
|
+
**This command restarts the shell.** `omakit weigh` measures a plugin by
|
|
11
|
+
starting the person's `omarchy-shell` without the plugin and with it, several
|
|
12
|
+
times, and it edits `~/.config/omarchy/shell.json` for the duration. Every
|
|
13
|
+
other omakit command is read-only; this one is not. So:
|
|
14
|
+
|
|
15
|
+
- Never run it with `--yes` unless the person has just agreed, in this
|
|
16
|
+
conversation, to have their shell restarted that many times. The command
|
|
17
|
+
prints the count and the estimated minutes before it asks; put those in
|
|
18
|
+
front of the person and wait for their answer.
|
|
19
|
+
- Never run it while they are in the middle of something on that desktop.
|
|
20
|
+
The bar, every panel and every plugin go away and come back on each
|
|
21
|
+
restart, (1 + plugins) × runs times, and a restart costs about a minute
|
|
22
|
+
(a 30 s settle and a 15 s window after each). One plugin at three runs is
|
|
23
|
+
six restarts, about five minutes. `--all` is sized for a lab machine, not
|
|
24
|
+
a working desktop: 47 enabled plugins is 144 restarts and about two hours
|
|
25
|
+
at three runs, three and a half at five. Offer `--all` only for a machine
|
|
26
|
+
nobody is using.
|
|
27
|
+
- Never run it on your own machine's shell as a stand-in for theirs. The
|
|
28
|
+
weight is the weight on the machine the plugin runs on.
|
|
29
|
+
|
|
30
|
+
Without `--yes`, from a pipe or with `--json`, the command prints the plan
|
|
31
|
+
and refuses with `█ NOT WEIGHED` (exit 2); nothing is touched. That refusal
|
|
32
|
+
is the correct outcome of an agent running it unasked. The same word, with
|
|
33
|
+
one sentence naming what is missing, is how it refuses an Omarchy it cannot
|
|
34
|
+
weigh on: no `omarchy-shell` (an install older than the Quattro shell), no
|
|
35
|
+
`omarchy-restart-shell`, no readable version, a shell that does not answer
|
|
36
|
+
`ping`, or an IPC target without the four methods it relies on. Report that
|
|
37
|
+
sentence to the person as it is; do not work around it.
|
|
38
|
+
|
|
39
|
+
## When to run it
|
|
40
|
+
|
|
41
|
+
- Before submitting: the README sentence it produces belongs in the
|
|
42
|
+
plugin's README, next to what the plugin does. The question a person
|
|
43
|
+
asks is how heavy it is; this answers it with a measurement.
|
|
44
|
+
- After a change that adds a `Timer`, a `Process`, a `FileView` with
|
|
45
|
+
`watchChanges`, a `SystemClock`, or a `Connections` to a busy service. A
|
|
46
|
+
declared interval says nothing about what runs; this measures it.
|
|
47
|
+
- When the owner asks how heavy the plugin is. Answer with the measured
|
|
48
|
+
figures and their noise floor, never with an estimate from the source.
|
|
49
|
+
|
|
50
|
+
## Run it
|
|
51
|
+
|
|
52
|
+
```bash
|
|
53
|
+
omakit weigh <plugin-id-or-dir> # one plugin, asks first
|
|
54
|
+
omakit weigh <plugin-id-or-dir> --yes --json # only after the person agreed
|
|
55
|
+
omakit weigh --all --yes # every enabled third-party plugin
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
The plugin must be installed and enabled in the running shell: the
|
|
59
|
+
measurement puts it back exactly where the person has it. A plugin of kind
|
|
60
|
+
`bar` is refused (replacing the whole bar is not a weight), and so is a locked
|
|
61
|
+
session. `--runs` (default 3), `--window` (default 15 s) and `--settle`
|
|
62
|
+
(default 30 s) trade time for a lower noise floor; leave them at their
|
|
63
|
+
defaults unless the floor is too high to answer the question.
|
|
64
|
+
|
|
65
|
+
If `omakit` is not installed: `npm install --global omakit` (Omarchy ships
|
|
66
|
+
Node and npm through mise), then `omakit doctor`. `weigh` needs no pin and no
|
|
67
|
+
network.
|
|
68
|
+
|
|
69
|
+
## Reading the verdicts
|
|
70
|
+
|
|
71
|
+
The header prints the **noise floor** once: the spread of the baseline's
|
|
72
|
+
own CPU across its runs. A plugin whose median CPU delta is not larger than
|
|
73
|
+
that floor has **no measurable CPU**, in those words, and the row is `ok`.
|
|
74
|
+
A row is `note` when CPU is above the floor, and `?` when no run of it
|
|
75
|
+
completed.
|
|
76
|
+
|
|
77
|
+
- `no measurable CPU` means the measurement cannot tell the plugin from
|
|
78
|
+
nothing at this run count and window. It does not mean zero. Say "no
|
|
79
|
+
measurable CPU against a floor of N%", with the number.
|
|
80
|
+
- `above noise on CPU` is a measured weight. Report the median and its
|
|
81
|
+
spread, and the children line separately: a plugin that adds 0.1% in the
|
|
82
|
+
shell and runs a 40 MB helper weighs both.
|
|
83
|
+
- **Memory is the shell's, not the plugin's, for now.** The memory delta is
|
|
84
|
+
printed with its spread, and the header labels it "within the shell's own
|
|
85
|
+
startup variance (N MB)". Never turn it into a sentence about the plugin
|
|
86
|
+
("costs N MB", "under N MB"): the shell comes to rest on one of two
|
|
87
|
+
levels 35 MB apart after a restart, and that difference is not the
|
|
88
|
+
plugin's (`docs/MEASUREMENTS.md`, C1 and C2). If the owner asks about
|
|
89
|
+
memory, say exactly that and show the figure with the variance beside it.
|
|
90
|
+
- A negative median is printed as measured. Do not round it to zero and do
|
|
91
|
+
not explain it away; it means the delta is inside the noise.
|
|
92
|
+
- Never describe a weight as acceptable or unacceptable. The verdict is a
|
|
93
|
+
comparison with the floor; whether the number is fine is the owner's
|
|
94
|
+
call, made with the number in front of them.
|
|
95
|
+
|
|
96
|
+
In `--json`, each row carries `verdict.memory` and `verdict.cpu`
|
|
97
|
+
(`within-noise`, `above-noise`, `unknown`), `withinNoise` with the floors,
|
|
98
|
+
the stats objects (`median`, `spread`, `min`, `max`, `runs`), and `origin`
|
|
99
|
+
naming the `/proc` paths and the arithmetic. `config.md5Before` and
|
|
100
|
+
`config.md5After` must be equal and `config.restored` true; if they are not,
|
|
101
|
+
tell the person at once and name `config.backup`, which is kept. The full
|
|
102
|
+
contract is `docs/WEIGH.md`.
|
|
103
|
+
|
|
104
|
+
## What to paste into the README
|
|
105
|
+
|
|
106
|
+
The last thing the command prints is the sentence, per plugin, and the path
|
|
107
|
+
of the JSON that is its evidence:
|
|
108
|
+
|
|
109
|
+
```text
|
|
110
|
+
Weighs no CPU above the floor (0.13%) and runs 2 child processes using 8.2 MB and 0.1% CPU, on Omarchy 4.0.0.alpha, measured with omakit weigh on 2026-09-14
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
Paste it as it is, under a heading such as "What it weighs", and keep the
|
|
114
|
+
JSON with the plugin's evidence or link to it. It names the CPU floor even
|
|
115
|
+
when the plugin is under it, and the child processes with their memory;
|
|
116
|
+
it never names the shell's memory, and neither should you in that README.
|
|
117
|
+
Re-run and replace the sentence after any change that adds a timer,
|
|
118
|
+
a process or a watcher; a sentence measured on an older commit is a claim
|
|
119
|
+
about a plugin that no longer exists.
|
|
120
|
+
|
|
121
|
+
## What the measurement does not know
|
|
122
|
+
|
|
123
|
+
Per-plugin memory inside the shell is knowable only by this A/B, because Qt
|
|
124
|
+
allocates from shared heaps. RSS never falls when a plugin is unloaded and
|
|
125
|
+
every bar widget rebuilds on any layout change, so nothing here measures a
|
|
126
|
+
running shell before and after; both sides start fresh. The weight of a panel
|
|
127
|
+
only while it is open, and any weight that depends on another plugin, are not
|
|
128
|
+
measured. Do not extrapolate either.
|
|
@@ -28,12 +28,29 @@ local commit through the transport seam the marketplace tests itself
|
|
|
28
28
|
| `report.mjs` | Text rendering of submit, watch, doctor and verify for the agent that runs this tool, and the person reading over its shoulder. |
|
|
29
29
|
| `path-hint.mjs` | Is `omakit` reachable as a bare command, and if not, the one line that makes it so for the install that is here: a symlink for a clone, the npm prefix's `bin` on PATH for a package, said for the shell in `$SHELL`. `setup` and `doctor` print it; nothing writes an rc file. |
|
|
30
30
|
| `usage.mjs` | The help text, as data. |
|
|
31
|
+
| `options.mjs` | Every option every command accepts, in one table, and the parser that reads a command line against it before anything runs; `tests/unit/options.test.mjs` holds the help signatures, and through them the completion scripts, to the table. |
|
|
31
32
|
| `completion.mjs` | A completion script for bash, zsh or fish, derived from the help data and the pin's form: the subcommands and flags are read out of `COMMANDS`, the categories and tags out of the pinned submission form, and the script says which pin it came from. `setup` installs it for the shell in `$SHELL`, the one file this tool writes outside its own checkout. |
|
|
33
|
+
| `completion-check.mjs` | Whether tab completion actually works: a frozen probe per shell run interactively, asking the loader to load `omakit` the way TAB does; the one marked block `setup` may append to an rc file after a yes, looked for by its marker first; the installed script's version and pin read from its first line; `doctor`'s `omakit.completion`; and the once-a-day stale notice. |
|
|
32
34
|
| `banner.mjs` | The wordmark, on a bare `omakit` and in `setup` only. |
|
|
33
35
|
| `effect.mjs` | The one text effect: the wordmark through `ttfx` where it is drawn, with frozen arguments, a hard budget, no colour of its own, and nothing at all when `ttfx` is not there. |
|
|
34
36
|
| `progress.mjs` | The progress line, on stderr, only when a person is looking. |
|
|
35
37
|
| `paths.mjs` | Omakit's cache directory, following XDG, and `withHomeAbbreviated()`: a path under `$HOME` written as `~/...` for a person, applied where doctor, setup and pin render text and never where a result is built, so `--json` keeps every path absolute. |
|
|
36
|
-
| `cli.mjs` | The one entry point behind `bin/omakit`, and the one register every failure is reported in. `submit` exits on the outcome: 1 for `refused`, 0 for `ready` and `listed`. |
|
|
38
|
+
| `cli.mjs` | The one entry point behind `bin/omakit`, and the one register every failure is reported in. `submit` exits on the outcome: 1 for `refused`, 0 for `ready` and `listed`. `weigh` confirms before its first restart and exits 130 when interrupted, after the restore. |
|
|
39
|
+
|
|
40
|
+
`tools/weigh/` is `omakit weigh`, the one command that changes the user's own
|
|
41
|
+
machine (docs/WEIGH.md):
|
|
42
|
+
|
|
43
|
+
| File | Purpose |
|
|
44
|
+
| --- | --- |
|
|
45
|
+
| `weigh/commands.mjs` | The frozen table of Omarchy commands the measurement runs (`omarchy-shell`, `omarchy-restart-shell`, `omarchy plugin list`, `omarchy-plugin-catalog`, `qs list`, the session-lock check, `systemctl --user show-environment`, `getconf`), and the one spawn call site under `tools/weigh/`. |
|
|
46
|
+
| `weigh/proc.mjs` | Reading `/proc`: `utime+stime` and `cutime+cstime` from `stat`, `VmRSS` from `status`, `Pss` from `smaps_rollup`, and a descendant walk by parent id, all against a root that tests point at a directory. |
|
|
47
|
+
| `weigh/config.mjs` | Where `shell.json` is, the pure transform that removes a set of plugin ids from the effective configuration, the byte-for-byte backup, the restore and its md5 verification. |
|
|
48
|
+
| `weigh/stats.mjs` | Median, spread, the stats object, and the within-noise comparison. |
|
|
49
|
+
| `weigh/audit.mjs` | `planWeigh()` reads and decides (what runs, how many restarts, the estimate) and writes nothing; `measureWeigh()` restarts, samples and restores in a `finally`; `buildDocument()` turns the samples into the document. |
|
|
50
|
+
| `weigh/contract.mjs` | The JSON contract of docs/WEIGH.md as a validator, run by the unit tests and by the lab over a real document. |
|
|
51
|
+
| `weigh/list.mjs` | `weigh --list`: every installed plugin with its last weighing from the documents under the state directory, read-only, unweighed enabled plugins first. |
|
|
52
|
+
| `weigh/report.mjs` | The confirmation and the report for a person, drawn with `style.mjs`; the README sentence and the evidence path come last. |
|
|
53
|
+
| `weigh/confirm.mjs` | The one question, at a terminal, on stderr. |
|
|
37
54
|
|
|
38
55
|
```text
|
|
39
56
|
omakit pin
|