@ssheleg/make-skill 0.26.0 → 0.27.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/CHANGELOG.md
CHANGED
|
@@ -1,3 +1,65 @@
|
|
|
1
|
+
## v0.27.1 — the tarball stops shipping compiled Python, and the audit vocabulary the routing block promised becomes advertised
|
|
2
|
+
|
|
3
|
+
Family audit 2026-09-06, wave `AUDIT-WAVE-0906`. Two findings, both a gap between what
|
|
4
|
+
this member says and what it ships.
|
|
5
|
+
|
|
6
|
+
**The npm tarball carried a 33kB `.pyc` from a used checkout.** `files` includes
|
|
7
|
+
`plugins`, the gate imports the auditor, and Python drops
|
|
8
|
+
`scripts/__pycache__/audit_skill.cpython-314.pyc` beside it — so a publish from any
|
|
9
|
+
machine that had run the suite shipped bytecode nobody wrote. `.gitignore` already
|
|
10
|
+
covered it, and that is exactly why it looked handled: git never carried the file, but
|
|
11
|
+
npm's `files` allowlist does not read `.gitignore` inside a directory it was told to
|
|
12
|
+
include. The durable fix is the shape `seo-aeo-audit` already ships — `"!**/__pycache__"`
|
|
13
|
+
and `"!**/*.pyc"` in `files`. **Measured with the residue present on disk, not after
|
|
14
|
+
deleting it**: the `.pyc` was regenerated first, then `npm pack --dry-run | grep -c pyc`
|
|
15
|
+
→ **0**. The auditor's `BUNDLE_NESTED` GAP for that directory goes with it.
|
|
16
|
+
|
|
17
|
+
**The umbrella's routing block advertises "skill audit" / «аудит скилов», and the
|
|
18
|
+
description never did.** Both phrases now sit in the trigger enumeration, verbatim, after
|
|
19
|
+
the "сделай скилл" pair. The room was paid for by trimming **54** characters from the
|
|
20
|
+
non-trigger prose — "open standard and" → "standard,", "front-matter limits" → "limits",
|
|
21
|
+
"manifest schemas, component layout" → "manifests, layout", "the Claude Code plugin
|
|
22
|
+
reference" → "the plugin reference" — and **every previously advertised quoted phrase
|
|
23
|
+
survives verbatim**, which is what the umbrella's soundness fixture refuses a pin
|
|
24
|
+
without. Auditor before → after: description **965/970 → 943/970**, `DESC_WHAT` **550 →
|
|
25
|
+
582** chars beyond the triggers, body untouched at ~4677/4750, **0 GAP**.
|
|
26
|
+
|
|
27
|
+
## v0.27.0 — the standard-keeper asked WHEN nine times and WHAT never
|
|
28
|
+
|
|
29
|
+
`B-139`. `audit_skill.py` carried nine `DESC_*` rules — length, headroom, person, Russian
|
|
30
|
+
triggers, XML, target, the `Use when` opener — and **not one asked whether the
|
|
31
|
+
description says what the skill DOES.** That is the half of Anthropic's guidance `B-76`
|
|
32
|
+
quoted directly: *a description that never says what the skill does passes*. Measured
|
|
33
|
+
2026-09-03 across the family: **28 of 28 skills pass `DESC_USEWHEN`, 0 gaps** — the WHEN
|
|
34
|
+
half is universal and the WHAT half was unchecked.
|
|
35
|
+
|
|
36
|
+
`DESC_WHAT` measures the description with its mechanical parts removed — the `Use when`
|
|
37
|
+
opener, the trigger list, the `Not for` clause and the opt-out sentence — and refuses
|
|
38
|
+
what is left below 60 characters.
|
|
39
|
+
|
|
40
|
+
**Built on the PARSED description, which is the whole reason the previous attempt was
|
|
41
|
+
refused.** That prototype read raw front matter, reported a **0-character** WHAT half for
|
|
42
|
+
six skills and missed the opening clause of twenty, because several descriptions are YAML
|
|
43
|
+
block scalars (`>-`) a raw-text regex reads straight past. `parse_frontmatter` already
|
|
44
|
+
resolves them.
|
|
45
|
+
|
|
46
|
+
**The floor is stated with its margin.** Measured across the shipped family the smallest
|
|
47
|
+
honest WHAT half is **149** characters (`ux-audit`) and the largest **949**
|
|
48
|
+
(`seo-aeo-audit`), so 60 clears every real description by more than double while still
|
|
49
|
+
catching `Use when the user asks. Triggers - "делай" / "do it".`, whose WHAT half is
|
|
50
|
+
**13**. A case asserts that margin, so raising the floor without re-measuring fails.
|
|
51
|
+
|
|
52
|
+
**This rule finds no gap today and that is said out loud.** A standard is for the
|
|
53
|
+
description not yet written, and a rule that fires on nothing now is worth only what its
|
|
54
|
+
plants prove — so it was watched refusing a WHEN-only description and watched going
|
|
55
|
+
silent when disabled.
|
|
56
|
+
|
|
57
|
+
**One case was reworded after being caught claiming somebody else's work.** It asserted
|
|
58
|
+
the WHAT half is read from the parsed value rather than raw text — and the plant for that
|
|
59
|
+
property is caught by an existing case guarding `parse_frontmatter`'s folding, one layer
|
|
60
|
+
up. It now claims only what it holds: both spellings of one description reach the same
|
|
61
|
+
verdict, neither passes vacuously, and the parsed value carries no newline.
|
|
62
|
+
|
|
1
63
|
## v0.26.0 — where a rule lives decides whether it exists
|
|
2
64
|
|
|
3
65
|
`authoring.md` treated progressive disclosure as a budget question. It is also a
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ssheleg/make-skill",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.27.1",
|
|
4
4
|
"description": "Create, retrofit, audit, and ship agent skills & Claude Code plugins the proven ssheleg way \u2014 conformance to the Agent Skills open standard AND Anthropic's platform rules (front-matter limits, disclosure budgets, per-surface runtime limits, the Skills API, evals) plus the Claude Code plugin reference (manifest schemas, component layout, claude plugin validate --strict), marketplace repo layout, version sync, validator + CI, multi-channel distribution (plugin, vercel skills CLI, npx, Cursor), npm gotchas, the review checklist for third-party skills, and MCP / A2A rules for protocol-connected skills. This package is the installer CLI.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"skill",
|
|
@@ -36,7 +36,9 @@
|
|
|
36
36
|
"README.md",
|
|
37
37
|
"LICENSE",
|
|
38
38
|
"CHANGELOG.md",
|
|
39
|
-
"SECURITY.md"
|
|
39
|
+
"SECURITY.md",
|
|
40
|
+
"!**/__pycache__",
|
|
41
|
+
"!**/*.pyc"
|
|
40
42
|
],
|
|
41
43
|
"publishConfig": {
|
|
42
44
|
"access": "public"
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
"name": "make-skill",
|
|
4
4
|
"displayName": "Make Skill",
|
|
5
5
|
"description": "Create, retrofit, audit, and ship agent skills & Claude Code plugins the proven ssheleg way: conformance to the Agent Skills open standard, Anthropic's platform rules (surfaces, Skills API, evals) and the Claude Code plugin reference, marketplace repo layout, version sync, validator + CI, multi-channel distribution (plugin, vercel skills CLI, npx, Cursor), npm gotchas, end-to-end first publish, the review checklist for third-party skills, plus MCP / A2A references for protocol-connected skills.",
|
|
6
|
-
"version": "0.
|
|
6
|
+
"version": "0.27.1",
|
|
7
7
|
"author": {
|
|
8
8
|
"name": "ssheleg",
|
|
9
9
|
"url": "https://x.com/sshlg93"
|
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: make-skill
|
|
3
|
-
description: Use when creating, upgrading, auditing, or publishing agent skills and Claude Code plugins - "make a skill" / "сделай скилл", "wrap it in a plugin" / "заверни в плагин", "publish a skill" / "опубликуй скилл", "retrofit a skill to the standard" / "приведи скилл к стандарту", "does this skill match the spec" / "соответствует ли скилл стандарту", "claude plugin validate fails" / "проверь плагин по документации Anthropic", "is this skill safe to install" / "безопасно ли ставить этот скилл" - or when a skill must reach an MCP server or another agent over A2A. NOT for a version bump or release in a repo that ships anything but a skill or plugin. Encodes the Agent Skills
|
|
3
|
+
description: Use when creating, upgrading, auditing, or publishing agent skills and Claude Code plugins - "make a skill" / "сделай скилл", "skill audit" / «аудит скилов», "wrap it in a plugin" / "заверни в плагин", "publish a skill" / "опубликуй скилл", "retrofit a skill to the standard" / "приведи скилл к стандарту", "does this skill match the spec" / "соответствует ли скилл стандарту", "claude plugin validate fails" / "проверь плагин по документации Anthropic", "is this skill safe to install" / "безопасно ли ставить этот скилл" - or when a skill must reach an MCP server or another agent over A2A. NOT for a version bump or release in a repo that ships anything but a skill or plugin. Encodes the Agent Skills standard, Anthropic's platform rules (limits, budgets, Skills API, evals), the plugin reference (manifests, layout, validate --strict), plus the ssheleg pipeline - marketplace layout, version sync, validator+CI, distribution, npm gotchas.
|
|
4
4
|
license: MIT
|
|
5
5
|
compatibility: Authoring works on any agent. The bundled scripts/ need python3. Publishing steps need git, gh, node and npm; the plugin gates need the claude CLI. Not usable on the Claude API surface, which has no network and no runtime package install.
|
|
6
6
|
metadata:
|
|
7
7
|
author: ssheleg
|
|
8
|
-
version: "0.
|
|
8
|
+
version: "0.27.1"
|
|
9
9
|
homepage: https://github.com/ssheleg/make-skill
|
|
10
10
|
---
|
|
11
11
|
|
|
@@ -38,6 +38,48 @@ DESC_MAX = 1024 # spec: description is 1-1024 characters
|
|
|
38
38
|
# budget AND the field that must grow when a near-miss skill appears ("say what
|
|
39
39
|
# it is NOT for"). A description at 98% of cap cannot absorb that sentence.
|
|
40
40
|
DESC_TARGET = 970
|
|
41
|
+
# B-139 — the nine `DESC_*` rules ask WHEN and never WHAT.
|
|
42
|
+
#
|
|
43
|
+
# Anthropic's guidance asks a description to say what the skill DOES as well as when to
|
|
44
|
+
# use it, and `B-76` quoted the failure directly: *a description that never says what the
|
|
45
|
+
# skill does passes*. Measured 2026-09-03 across the family: **28 of 28 skills pass
|
|
46
|
+
# `DESC_USEWHEN`, 0 gaps** — the WHEN half is universal and the WHAT half was unchecked.
|
|
47
|
+
#
|
|
48
|
+
# The WHAT half is the description with its mechanical parts removed: the `Use when`
|
|
49
|
+
# opener, the trigger list, the `Not for` clause and the opt-out sentence. What remains is
|
|
50
|
+
# the prose that names the act. A description that is an opener plus a trigger list leaves
|
|
51
|
+
# almost nothing, which is exactly the shape the rule refuses.
|
|
52
|
+
#
|
|
53
|
+
# The floor is 60 and it is deliberately permissive. Measured on the shipped family, the
|
|
54
|
+
# smallest honest WHAT half is **149** characters (`ux-audit`) and the largest 949, so 60
|
|
55
|
+
# clears every real description by more than double and still catches
|
|
56
|
+
# `Use when the user asks. Triggers - "x" / "у".`, whose WHAT half is 13.
|
|
57
|
+
#
|
|
58
|
+
# **This rule finds no gap today, and that is stated rather than hidden.** A standard is
|
|
59
|
+
# for the description not yet written; a rule that fires on nothing now is only worth
|
|
60
|
+
# anything if it was watched firing on a plant, which `test/checker_parity_test.py` does.
|
|
61
|
+
DESC_WHAT_MIN = 60
|
|
62
|
+
|
|
63
|
+
# Built on the PARSED description, never the raw front matter. A prototype was built
|
|
64
|
+
# against raw text and refused: it reported a 0-character WHAT half for six skills and
|
|
65
|
+
# missed the opening clause of twenty, because several descriptions are YAML block
|
|
66
|
+
# scalars (`>-`) that a raw-text regex reads straight past. `parse_frontmatter` already
|
|
67
|
+
# resolves them, and the prototype did not use it.
|
|
68
|
+
_WHAT_OPENER = re.compile(r"^use when\s+", re.I)
|
|
69
|
+
_WHAT_STRIP = (
|
|
70
|
+
re.compile(r"\bTriggers?\s*[-–—:].*", re.S | re.I),
|
|
71
|
+
re.compile(r"\bNot for\b.*", re.S | re.I),
|
|
72
|
+
re.compile(r"\bsay\s+['\"«].*", re.S | re.I),
|
|
73
|
+
)
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
def what_half(description):
|
|
77
|
+
"""The prose that names the act, with the mechanical parts removed."""
|
|
78
|
+
core = _WHAT_OPENER.sub("", " ".join(str(description or "").split()))
|
|
79
|
+
for rx in _WHAT_STRIP:
|
|
80
|
+
core = rx.sub("", core)
|
|
81
|
+
return core.strip(" .,;—-")
|
|
82
|
+
|
|
41
83
|
COMPAT_MAX = 500 # spec: compatibility is 1-500 characters
|
|
42
84
|
BODY_MAX_LINES = 500 # spec + Anthropic: keep the body under 500 lines
|
|
43
85
|
BODY_MAX_TOKENS = 5000 # spec + Anthropic: level-2 budget
|
|
@@ -270,6 +312,17 @@ def _check_description(a, fm, lines, rel, house):
|
|
|
270
312
|
a.gap("DESC_RU", "description carries no Russian trigger phrases (house rule)", rel, ln)
|
|
271
313
|
else:
|
|
272
314
|
a.ok("DESC_RU", "description carries Russian trigger phrases (house rule)", rel, ln)
|
|
315
|
+
what = what_half(desc)
|
|
316
|
+
if len(what) < DESC_WHAT_MIN:
|
|
317
|
+
a.gap("DESC_WHAT", "description says WHEN and never WHAT: %d chars remain "
|
|
318
|
+
"after the opener, the trigger list and the refusal are removed, and "
|
|
319
|
+
"the floor is %d (house rule). Anthropic's guidance asks for both "
|
|
320
|
+
"halves, and a description that is an opener plus a trigger list "
|
|
321
|
+
"selects the skill without telling the model what it will do"
|
|
322
|
+
% (len(what), DESC_WHAT_MIN), rel, ln)
|
|
323
|
+
else:
|
|
324
|
+
a.ok("DESC_WHAT", "description states WHAT the skill does in %d chars "
|
|
325
|
+
"beyond its triggers (house rule)" % len(what), rel, ln)
|
|
273
326
|
if DESC_TARGET < len(desc) <= DESC_MAX:
|
|
274
327
|
a.gap("DESC_HEADROOM", "description is %d chars — inside the %d cap but past the "
|
|
275
328
|
"%d working limit (house rule): leave room for the 'what this is NOT for' "
|