@domandigital/craft 0.10.0 → 0.11.0
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 +19 -0
- package/README.md +35 -0
- package/dist/{audit-EGDNWSQB.js → audit-QIPXL7E4.js} +1 -1
- package/dist/audit.cjs +3 -1
- package/dist/audit.js +3 -1
- package/dist/{chunk-JKIDWHG3.js → chunk-2AJB27BJ.js} +282 -29
- package/dist/{chunk-APO4BT2F.js → chunk-3OZQ4C5R.js} +5 -4
- package/dist/{chunk-2NQFIDLE.js → chunk-HOHHQB4N.js} +7 -6
- package/dist/{chunk-TSKRBIOC.js → chunk-JP75P2DU.js} +3 -1
- package/dist/chunk-MSQ57PJU.js +206 -0
- package/dist/{cli-PRWTNFVP.js → cli-4ESXOLKV.js} +2 -2
- package/dist/{cli-ADQQURNR.js → cli-DBZMVYYV.js} +17 -11
- package/dist/{cli-EK3GSAOW.js → cli-T5RD2BTK.js} +6 -4
- package/dist/{cli-2WBGTBKD.js → cli-U3SZVHSK.js} +4 -3
- package/dist/{cli-VQUNNIZM.js → cli-VREYWCT4.js} +3 -3
- package/dist/cli.js +1 -1
- package/dist/index.cjs +216 -0
- package/dist/index.d.cts +185 -1
- package/dist/index.d.ts +185 -1
- package/dist/index.js +202 -0
- package/package.json +13 -6
- package/dist/chunk-U2JTFQKO.js +0 -112
package/dist/index.cjs
CHANGED
|
@@ -23,10 +23,12 @@ __export(index_exports, {
|
|
|
23
23
|
AI_PHRASES: () => AI_PHRASES,
|
|
24
24
|
AI_VIOLET: () => AI_VIOLET,
|
|
25
25
|
AI_WORDS: () => AI_WORDS,
|
|
26
|
+
BASELINE_VERSION: () => BASELINE_VERSION,
|
|
26
27
|
BUZZWORDS: () => BUZZWORDS,
|
|
27
28
|
CATALOGUE: () => CATALOGUE,
|
|
28
29
|
CATALOGUE_VERSION: () => CATALOGUE_VERSION,
|
|
29
30
|
CHOICE_KEYS: () => CHOICE_KEYS,
|
|
31
|
+
DEFAULT_IGNORE: () => DEFAULT_IGNORE,
|
|
30
32
|
DENSITIES: () => DENSITIES,
|
|
31
33
|
DENSITY_NAMES: () => DENSITY_NAMES,
|
|
32
34
|
DIRECTION_VERSION: () => DIRECTION_VERSION,
|
|
@@ -41,6 +43,7 @@ __export(index_exports, {
|
|
|
41
43
|
HOUSE: () => HOUSE,
|
|
42
44
|
HOUSE_BUDGET: () => HOUSE_BUDGET,
|
|
43
45
|
HOUSE_TYPE: () => HOUSE_TYPE,
|
|
46
|
+
JSON_SCHEMA_VERSION: () => JSON_SCHEMA_VERSION,
|
|
44
47
|
LIGHTNESS_CURVE: () => LIGHTNESS_CURVE,
|
|
45
48
|
MIN_DECIDED: () => MIN_DECIDED,
|
|
46
49
|
MIN_RUNS: () => MIN_RUNS,
|
|
@@ -71,7 +74,9 @@ __export(index_exports, {
|
|
|
71
74
|
accentFork: () => accentFork,
|
|
72
75
|
addSite: () => addSite,
|
|
73
76
|
apcaContrast: () => apcaContrast,
|
|
77
|
+
applyBaseline: () => applyBaseline,
|
|
74
78
|
applyHouseGate: () => applyHouseGate,
|
|
79
|
+
applySeverity: () => applySeverity,
|
|
75
80
|
auditSnapshot: () => auditSnapshot,
|
|
76
81
|
catalogueTable: () => catalogueTable,
|
|
77
82
|
characterReport: () => characterReport,
|
|
@@ -82,6 +87,7 @@ __export(index_exports, {
|
|
|
82
87
|
compareFacts: () => compareFacts,
|
|
83
88
|
compareToEstate: () => compareToEstate,
|
|
84
89
|
craftTokens: () => craftTokens,
|
|
90
|
+
createBaseline: () => createBaseline,
|
|
85
91
|
deltaEOk: () => deltaEOk,
|
|
86
92
|
deltaEOkHex: () => deltaEOkHex,
|
|
87
93
|
densityCss: () => densityCss,
|
|
@@ -93,6 +99,7 @@ __export(index_exports, {
|
|
|
93
99
|
extractHtml: () => extractHtml,
|
|
94
100
|
findClaims: () => findClaims,
|
|
95
101
|
findColours: () => findColours,
|
|
102
|
+
findingKey: () => findingKey,
|
|
96
103
|
fingerprint: () => fingerprint,
|
|
97
104
|
fingerprintDistance: () => fingerprintDistance,
|
|
98
105
|
fluidClamp: () => fluidClamp,
|
|
@@ -103,12 +110,14 @@ __export(index_exports, {
|
|
|
103
110
|
formatComparison: () => formatComparison,
|
|
104
111
|
formatHex: () => formatHex,
|
|
105
112
|
formatReport: () => formatReport,
|
|
113
|
+
globToRegExp: () => globToRegExp,
|
|
106
114
|
groundName: () => groundName,
|
|
107
115
|
harvest: () => harvest,
|
|
108
116
|
hexToOklch: () => hexToOklch,
|
|
109
117
|
houseRule: () => houseRule,
|
|
110
118
|
hueName: () => hueName,
|
|
111
119
|
hueSwatch: () => hueSwatch,
|
|
120
|
+
ignoreMatcher: () => ignoreMatcher,
|
|
112
121
|
inP3Gamut: () => inP3Gamut,
|
|
113
122
|
inSrgbGamut: () => inSrgbGamut,
|
|
114
123
|
initDirection: () => initDirection,
|
|
@@ -123,7 +132,9 @@ __export(index_exports, {
|
|
|
123
132
|
oklchToHex: () => oklchToHex,
|
|
124
133
|
oklchToRgb: () => oklchToRgb,
|
|
125
134
|
paletteFromPixels: () => paletteFromPixels,
|
|
135
|
+
parseBaseline: () => parseBaseline,
|
|
126
136
|
parseColour: () => parseColour,
|
|
137
|
+
parseCraftConfig: () => parseCraftConfig,
|
|
127
138
|
parseHex: () => parseHex,
|
|
128
139
|
propose: () => propose,
|
|
129
140
|
protectedFacts: () => protectedFacts,
|
|
@@ -134,6 +145,7 @@ __export(index_exports, {
|
|
|
134
145
|
scanSource: () => scanSource,
|
|
135
146
|
sectionRhythm: () => sectionRhythm,
|
|
136
147
|
semantic: () => semantic,
|
|
148
|
+
severityExceptions: () => severityExceptions,
|
|
137
149
|
shapeName: () => shapeName,
|
|
138
150
|
sharedParts: () => sharedParts,
|
|
139
151
|
shouldAnimate: () => shouldAnimate,
|
|
@@ -142,6 +154,8 @@ __export(index_exports, {
|
|
|
142
154
|
tailwindV4Theme: () => tailwindV4Theme,
|
|
143
155
|
tellById: () => tellById,
|
|
144
156
|
toGamut: () => toGamut,
|
|
157
|
+
toJson: () => toJson,
|
|
158
|
+
toSarif: () => toSarif,
|
|
145
159
|
typeFeatureTokens: () => typeFeatureTokens,
|
|
146
160
|
typicality: () => typicality,
|
|
147
161
|
validateDirection: () => validateDirection,
|
|
@@ -4752,6 +4766,194 @@ function formatClaims(report2, label = "craft copy claims") {
|
|
|
4752
4766
|
return lines.join("\n");
|
|
4753
4767
|
}
|
|
4754
4768
|
|
|
4769
|
+
// src/character/baseline.ts
|
|
4770
|
+
var BASELINE_VERSION = 1;
|
|
4771
|
+
function fnv1a(text) {
|
|
4772
|
+
let hash = 2166136261;
|
|
4773
|
+
for (let i = 0; i < text.length; i += 1) {
|
|
4774
|
+
hash ^= text.charCodeAt(i);
|
|
4775
|
+
hash = Math.imul(hash, 16777619);
|
|
4776
|
+
}
|
|
4777
|
+
return (hash >>> 0).toString(16).padStart(8, "0");
|
|
4778
|
+
}
|
|
4779
|
+
var excerptHash = (f4) => fnv1a(f4.excerpt.replace(/\s+/g, " ").trim());
|
|
4780
|
+
var keyOf = (tell, path, excerpt) => `${tell}\0${path}\0${excerpt}`;
|
|
4781
|
+
function findingKey(f4) {
|
|
4782
|
+
return keyOf(f4.tell, f4.path, excerptHash(f4));
|
|
4783
|
+
}
|
|
4784
|
+
function createBaseline(report2) {
|
|
4785
|
+
const counts = /* @__PURE__ */ new Map();
|
|
4786
|
+
for (const f4 of report2.findings) {
|
|
4787
|
+
const excerpt = excerptHash(f4);
|
|
4788
|
+
const key = keyOf(f4.tell, f4.path, excerpt);
|
|
4789
|
+
const entry = counts.get(key);
|
|
4790
|
+
if (entry) entry.count += 1;
|
|
4791
|
+
else counts.set(key, { tell: f4.tell, path: f4.path, excerpt, count: 1 });
|
|
4792
|
+
}
|
|
4793
|
+
const entries = [...counts.values()].sort((a, b) => a.path.localeCompare(b.path) || a.tell.localeCompare(b.tell) || a.excerpt.localeCompare(b.excerpt));
|
|
4794
|
+
return { version: BASELINE_VERSION, catalogueVersion: report2.catalogueVersion, entries };
|
|
4795
|
+
}
|
|
4796
|
+
function parseBaseline(data, source = "baseline") {
|
|
4797
|
+
const b = data;
|
|
4798
|
+
if (!b || typeof b !== "object" || b.version !== BASELINE_VERSION || !Array.isArray(b.entries)) {
|
|
4799
|
+
throw new Error(`${source}: not a craft baseline (version ${BASELINE_VERSION})`);
|
|
4800
|
+
}
|
|
4801
|
+
for (const e of b.entries) {
|
|
4802
|
+
if (typeof e?.tell !== "string" || typeof e.path !== "string" || typeof e.excerpt !== "string" || !Number.isInteger(e.count) || e.count < 1) {
|
|
4803
|
+
throw new Error(`${source}: malformed entry ${JSON.stringify(e)}`);
|
|
4804
|
+
}
|
|
4805
|
+
}
|
|
4806
|
+
return b;
|
|
4807
|
+
}
|
|
4808
|
+
function recount(report2, findings) {
|
|
4809
|
+
const byGeneration = { 1: 0, 2: 0, 3: 0 };
|
|
4810
|
+
const byTell = {};
|
|
4811
|
+
for (const f4 of findings) {
|
|
4812
|
+
byGeneration[f4.generation] += 1;
|
|
4813
|
+
byTell[f4.tell] = (byTell[f4.tell] ?? 0) + 1;
|
|
4814
|
+
}
|
|
4815
|
+
return {
|
|
4816
|
+
...report2,
|
|
4817
|
+
findings,
|
|
4818
|
+
summary: { ...report2.summary, findings: findings.length, byGeneration, byTell, blocking: findings.filter((f4) => f4.severity === "block").length }
|
|
4819
|
+
};
|
|
4820
|
+
}
|
|
4821
|
+
function applyBaseline(report2, baseline) {
|
|
4822
|
+
const remaining = /* @__PURE__ */ new Map();
|
|
4823
|
+
for (const e of baseline.entries) {
|
|
4824
|
+
const key = keyOf(e.tell, e.path, e.excerpt);
|
|
4825
|
+
remaining.set(key, (remaining.get(key) ?? 0) + e.count);
|
|
4826
|
+
}
|
|
4827
|
+
const kept = [];
|
|
4828
|
+
let baselined = 0;
|
|
4829
|
+
for (const f4 of report2.findings) {
|
|
4830
|
+
const key = findingKey(f4);
|
|
4831
|
+
const left = remaining.get(key) ?? 0;
|
|
4832
|
+
if (left > 0) {
|
|
4833
|
+
remaining.set(key, left - 1);
|
|
4834
|
+
baselined += 1;
|
|
4835
|
+
} else kept.push(f4);
|
|
4836
|
+
}
|
|
4837
|
+
return { ...recount(report2, kept), baselined };
|
|
4838
|
+
}
|
|
4839
|
+
|
|
4840
|
+
// src/character/config.ts
|
|
4841
|
+
var DEFAULT_IGNORE = [".claude", ".agents", ".cursor"];
|
|
4842
|
+
var KEYS = /* @__PURE__ */ new Set(["$schema", "ignore", "copyPaths", "severity"]);
|
|
4843
|
+
var LEVELS = /* @__PURE__ */ new Set(["warn", "block", "off"]);
|
|
4844
|
+
var MIN_BECAUSE = 12;
|
|
4845
|
+
var isRecord = (v) => typeof v === "object" && v !== null && !Array.isArray(v);
|
|
4846
|
+
var isStringArray = (v) => Array.isArray(v) && v.every((s) => typeof s === "string");
|
|
4847
|
+
function parseCraftConfig(data, knownTells, source = "craft.config.json") {
|
|
4848
|
+
if (!isRecord(data)) throw new Error(`${source}: expected an object`);
|
|
4849
|
+
for (const key of Object.keys(data)) if (!KEYS.has(key)) throw new Error(`${source}: unknown key "${key}"`);
|
|
4850
|
+
const ignore = data.ignore ?? [];
|
|
4851
|
+
if (!isStringArray(ignore)) throw new Error(`${source}: "ignore" must be an array of glob strings`);
|
|
4852
|
+
if (data.copyPaths !== void 0 && !isStringArray(data.copyPaths)) throw new Error(`${source}: "copyPaths" must be an array of paths`);
|
|
4853
|
+
const severity = {};
|
|
4854
|
+
const raw = data.severity ?? {};
|
|
4855
|
+
if (!isRecord(raw)) throw new Error(`${source}: "severity" must map a tell id to { level, because }`);
|
|
4856
|
+
for (const [tell, value] of Object.entries(raw)) {
|
|
4857
|
+
if (!knownTells.has(tell)) throw new Error(`${source}: severity names no tell called "${tell}"`);
|
|
4858
|
+
if (!isRecord(value) || !LEVELS.has(value.level)) {
|
|
4859
|
+
throw new Error(`${source}: severity.${tell} needs a level of "warn", "block" or "off"`);
|
|
4860
|
+
}
|
|
4861
|
+
if (typeof value.because !== "string" || value.because.trim().length < MIN_BECAUSE) {
|
|
4862
|
+
throw new Error(`${source}: severity.${tell} needs a because of at least a sentence`);
|
|
4863
|
+
}
|
|
4864
|
+
severity[tell] = { level: value.level, because: value.because };
|
|
4865
|
+
}
|
|
4866
|
+
return { ignore, severity, ...data.copyPaths ? { copyPaths: data.copyPaths } : {} };
|
|
4867
|
+
}
|
|
4868
|
+
function globToRegExp(glob) {
|
|
4869
|
+
const pattern = glob.replace(/^\.\//, "").replace(/\/$/, "").replace(/\/\*\*$/, "");
|
|
4870
|
+
let body = "";
|
|
4871
|
+
for (let i = 0; i < pattern.length; i += 1) {
|
|
4872
|
+
const c = pattern[i];
|
|
4873
|
+
if (c === "*" && pattern[i + 1] === "*") {
|
|
4874
|
+
const slash = pattern[i + 2] === "/";
|
|
4875
|
+
body += slash ? "(?:.*/)?" : ".*";
|
|
4876
|
+
i += slash ? 2 : 1;
|
|
4877
|
+
} else if (c === "*") body += "[^/]*";
|
|
4878
|
+
else if (c === "?") body += "[^/]";
|
|
4879
|
+
else body += c.replace(/[.+^${}()|[\]\\]/g, "\\$&");
|
|
4880
|
+
}
|
|
4881
|
+
const anywhere = !pattern.includes("/");
|
|
4882
|
+
return new RegExp(`^${anywhere ? "(?:.*/)?" : ""}${body}(?:/.*)?$`);
|
|
4883
|
+
}
|
|
4884
|
+
function ignoreMatcher(patterns) {
|
|
4885
|
+
const res = patterns.map(globToRegExp);
|
|
4886
|
+
return (path) => {
|
|
4887
|
+
const p = path.replace(/\\/g, "/").replace(/^\.\//, "");
|
|
4888
|
+
return res.some((re) => re.test(p));
|
|
4889
|
+
};
|
|
4890
|
+
}
|
|
4891
|
+
function severityExceptions(config) {
|
|
4892
|
+
return Object.entries(config.severity).filter(([, o]) => o.level === "off").map(([tell, o]) => ({ tell, because: `craft.config.json: ${o.because}` }));
|
|
4893
|
+
}
|
|
4894
|
+
function applySeverity(report2, config) {
|
|
4895
|
+
const findings = report2.findings.map((f4) => {
|
|
4896
|
+
const o = config.severity[f4.tell];
|
|
4897
|
+
return o && o.level !== "off" ? { ...f4, severity: o.level } : f4;
|
|
4898
|
+
});
|
|
4899
|
+
return { ...report2, findings, summary: { ...report2.summary, blocking: findings.filter((f4) => f4.severity === "block").length } };
|
|
4900
|
+
}
|
|
4901
|
+
|
|
4902
|
+
// src/character/sarif.ts
|
|
4903
|
+
var isUrl = (path) => /^[a-z][a-z0-9+.-]*:\/\//i.test(path);
|
|
4904
|
+
function toSarif(report2, options) {
|
|
4905
|
+
const byId = new Map(options.tells.map((t) => [t.id, t]));
|
|
4906
|
+
const ids = [...new Set(report2.findings.map((f4) => f4.tell))].sort();
|
|
4907
|
+
const index = new Map(ids.map((id, i) => [id, i]));
|
|
4908
|
+
const rules = ids.map((id) => {
|
|
4909
|
+
const t = byId.get(id);
|
|
4910
|
+
return {
|
|
4911
|
+
id,
|
|
4912
|
+
name: t?.name ?? id,
|
|
4913
|
+
shortDescription: { text: t?.name ?? id },
|
|
4914
|
+
...t ? { fullDescription: { text: t.why }, help: { text: t.fix } } : {}
|
|
4915
|
+
};
|
|
4916
|
+
});
|
|
4917
|
+
const results = report2.findings.map((f4) => ({
|
|
4918
|
+
ruleId: f4.tell,
|
|
4919
|
+
ruleIndex: index.get(f4.tell),
|
|
4920
|
+
level: f4.severity === "block" ? "error" : "warning",
|
|
4921
|
+
message: { text: `${f4.message}. ${f4.fix}` },
|
|
4922
|
+
locations: [
|
|
4923
|
+
{
|
|
4924
|
+
physicalLocation: {
|
|
4925
|
+
artifactLocation: { uri: isUrl(f4.path) ? f4.path : f4.path.replace(/\\/g, "/") },
|
|
4926
|
+
...f4.line > 0 ? { region: { startLine: f4.line, snippet: { text: f4.excerpt } } } : {}
|
|
4927
|
+
}
|
|
4928
|
+
}
|
|
4929
|
+
],
|
|
4930
|
+
partialFingerprints: { "craftFinding/v1": fnv1a(findingKey(f4)) }
|
|
4931
|
+
}));
|
|
4932
|
+
return {
|
|
4933
|
+
$schema: "https://json.schemastore.org/sarif-2.1.0.json",
|
|
4934
|
+
version: "2.1.0",
|
|
4935
|
+
runs: [
|
|
4936
|
+
{
|
|
4937
|
+
tool: {
|
|
4938
|
+
driver: {
|
|
4939
|
+
name: "craft",
|
|
4940
|
+
version: report2.catalogueVersion,
|
|
4941
|
+
informationUri: options.informationUri ?? "https://www.npmjs.com/package/@domandigital/craft",
|
|
4942
|
+
rules
|
|
4943
|
+
}
|
|
4944
|
+
},
|
|
4945
|
+
results
|
|
4946
|
+
}
|
|
4947
|
+
]
|
|
4948
|
+
};
|
|
4949
|
+
}
|
|
4950
|
+
|
|
4951
|
+
// src/character/json.ts
|
|
4952
|
+
var JSON_SCHEMA_VERSION = 1;
|
|
4953
|
+
function toJson(data) {
|
|
4954
|
+
return JSON.stringify({ schemaVersion: JSON_SCHEMA_VERSION, ...data }, null, 2);
|
|
4955
|
+
}
|
|
4956
|
+
|
|
4755
4957
|
// src/fingerprint/index.ts
|
|
4756
4958
|
var FINGERPRINT_VERSION = 1;
|
|
4757
4959
|
var CHROMATIC = 0.03;
|
|
@@ -5647,10 +5849,12 @@ function retrofitPlan(report2, direction) {
|
|
|
5647
5849
|
AI_PHRASES,
|
|
5648
5850
|
AI_VIOLET,
|
|
5649
5851
|
AI_WORDS,
|
|
5852
|
+
BASELINE_VERSION,
|
|
5650
5853
|
BUZZWORDS,
|
|
5651
5854
|
CATALOGUE,
|
|
5652
5855
|
CATALOGUE_VERSION,
|
|
5653
5856
|
CHOICE_KEYS,
|
|
5857
|
+
DEFAULT_IGNORE,
|
|
5654
5858
|
DENSITIES,
|
|
5655
5859
|
DENSITY_NAMES,
|
|
5656
5860
|
DIRECTION_VERSION,
|
|
@@ -5665,6 +5869,7 @@ function retrofitPlan(report2, direction) {
|
|
|
5665
5869
|
HOUSE,
|
|
5666
5870
|
HOUSE_BUDGET,
|
|
5667
5871
|
HOUSE_TYPE,
|
|
5872
|
+
JSON_SCHEMA_VERSION,
|
|
5668
5873
|
LIGHTNESS_CURVE,
|
|
5669
5874
|
MIN_DECIDED,
|
|
5670
5875
|
MIN_RUNS,
|
|
@@ -5695,7 +5900,9 @@ function retrofitPlan(report2, direction) {
|
|
|
5695
5900
|
accentFork,
|
|
5696
5901
|
addSite,
|
|
5697
5902
|
apcaContrast,
|
|
5903
|
+
applyBaseline,
|
|
5698
5904
|
applyHouseGate,
|
|
5905
|
+
applySeverity,
|
|
5699
5906
|
auditSnapshot,
|
|
5700
5907
|
catalogueTable,
|
|
5701
5908
|
characterReport,
|
|
@@ -5706,6 +5913,7 @@ function retrofitPlan(report2, direction) {
|
|
|
5706
5913
|
compareFacts,
|
|
5707
5914
|
compareToEstate,
|
|
5708
5915
|
craftTokens,
|
|
5916
|
+
createBaseline,
|
|
5709
5917
|
deltaEOk,
|
|
5710
5918
|
deltaEOkHex,
|
|
5711
5919
|
densityCss,
|
|
@@ -5717,6 +5925,7 @@ function retrofitPlan(report2, direction) {
|
|
|
5717
5925
|
extractHtml,
|
|
5718
5926
|
findClaims,
|
|
5719
5927
|
findColours,
|
|
5928
|
+
findingKey,
|
|
5720
5929
|
fingerprint,
|
|
5721
5930
|
fingerprintDistance,
|
|
5722
5931
|
fluidClamp,
|
|
@@ -5727,12 +5936,14 @@ function retrofitPlan(report2, direction) {
|
|
|
5727
5936
|
formatComparison,
|
|
5728
5937
|
formatHex,
|
|
5729
5938
|
formatReport,
|
|
5939
|
+
globToRegExp,
|
|
5730
5940
|
groundName,
|
|
5731
5941
|
harvest,
|
|
5732
5942
|
hexToOklch,
|
|
5733
5943
|
houseRule,
|
|
5734
5944
|
hueName,
|
|
5735
5945
|
hueSwatch,
|
|
5946
|
+
ignoreMatcher,
|
|
5736
5947
|
inP3Gamut,
|
|
5737
5948
|
inSrgbGamut,
|
|
5738
5949
|
initDirection,
|
|
@@ -5747,7 +5958,9 @@ function retrofitPlan(report2, direction) {
|
|
|
5747
5958
|
oklchToHex,
|
|
5748
5959
|
oklchToRgb,
|
|
5749
5960
|
paletteFromPixels,
|
|
5961
|
+
parseBaseline,
|
|
5750
5962
|
parseColour,
|
|
5963
|
+
parseCraftConfig,
|
|
5751
5964
|
parseHex,
|
|
5752
5965
|
propose,
|
|
5753
5966
|
protectedFacts,
|
|
@@ -5758,6 +5971,7 @@ function retrofitPlan(report2, direction) {
|
|
|
5758
5971
|
scanSource,
|
|
5759
5972
|
sectionRhythm,
|
|
5760
5973
|
semantic,
|
|
5974
|
+
severityExceptions,
|
|
5761
5975
|
shapeName,
|
|
5762
5976
|
sharedParts,
|
|
5763
5977
|
shouldAnimate,
|
|
@@ -5766,6 +5980,8 @@ function retrofitPlan(report2, direction) {
|
|
|
5766
5980
|
tailwindV4Theme,
|
|
5767
5981
|
tellById,
|
|
5768
5982
|
toGamut,
|
|
5983
|
+
toJson,
|
|
5984
|
+
toSarif,
|
|
5769
5985
|
typeFeatureTokens,
|
|
5770
5986
|
typicality,
|
|
5771
5987
|
validateDirection,
|
package/dist/index.d.cts
CHANGED
|
@@ -1188,6 +1188,190 @@ declare function namedSources(sentence: string): string[];
|
|
|
1188
1188
|
declare function findClaims(files: SourceFile[]): ClaimsReport;
|
|
1189
1189
|
declare function formatClaims(report: ClaimsReport, label?: string): string;
|
|
1190
1190
|
|
|
1191
|
+
/**
|
|
1192
|
+
* Baselines: adopt craft on a repo that already has findings, and fail only
|
|
1193
|
+
* on new ones.
|
|
1194
|
+
*
|
|
1195
|
+
* A finding is keyed on its tell, its path and a hash of its excerpt with the
|
|
1196
|
+
* whitespace collapsed, never on its line: an edit above a known finding
|
|
1197
|
+
* moves it, and a moved finding is not a new one. Keys are counted, so a file
|
|
1198
|
+
* with two identical findings and a baseline of one reports the second.
|
|
1199
|
+
*
|
|
1200
|
+
* Pure. The command line reads and writes the file.
|
|
1201
|
+
*/
|
|
1202
|
+
|
|
1203
|
+
declare const BASELINE_VERSION = 1;
|
|
1204
|
+
interface BaselineEntry {
|
|
1205
|
+
tell: string;
|
|
1206
|
+
path: string;
|
|
1207
|
+
/** FNV-1a of the excerpt, whitespace collapsed. */
|
|
1208
|
+
excerpt: string;
|
|
1209
|
+
count: number;
|
|
1210
|
+
}
|
|
1211
|
+
interface Baseline {
|
|
1212
|
+
version: typeof BASELINE_VERSION;
|
|
1213
|
+
catalogueVersion: string;
|
|
1214
|
+
entries: BaselineEntry[];
|
|
1215
|
+
}
|
|
1216
|
+
/** The key a finding is matched on. Also the SARIF partial fingerprint. */
|
|
1217
|
+
declare function findingKey(f: Finding): string;
|
|
1218
|
+
/** Every finding in a report, as a baseline. */
|
|
1219
|
+
declare function createBaseline(report: CheckReport): Baseline;
|
|
1220
|
+
/** Validate a parsed baseline file. */
|
|
1221
|
+
declare function parseBaseline(data: unknown, source?: string): Baseline;
|
|
1222
|
+
/**
|
|
1223
|
+
* The report without the findings the baseline already knows about.
|
|
1224
|
+
* `baselined` is how many were removed, so the output can say so: a
|
|
1225
|
+
* baseline that hides findings silently is a hole.
|
|
1226
|
+
*/
|
|
1227
|
+
declare function applyBaseline(report: CheckReport, baseline: Baseline): CheckReport & {
|
|
1228
|
+
baselined: number;
|
|
1229
|
+
};
|
|
1230
|
+
|
|
1231
|
+
/**
|
|
1232
|
+
* `craft.config.json`: what a repo tells craft about itself.
|
|
1233
|
+
*
|
|
1234
|
+
* Pure: the command line reads the file and hands the parsed JSON here. The
|
|
1235
|
+
* design choices live in `art-direction.json`; this file is about the tool:
|
|
1236
|
+
* which paths are not the site, where the copy is, and a repo's own decisions
|
|
1237
|
+
* about a tell's severity.
|
|
1238
|
+
*
|
|
1239
|
+
* {
|
|
1240
|
+
* "ignore": ["docs/archive/**", "*.stories.tsx"],
|
|
1241
|
+
* "copyPaths": ["content", "src/app"],
|
|
1242
|
+
* "severity": {
|
|
1243
|
+
* "ai-violet": { "level": "off", "because": "The client's shopfront has been this violet since 1998." },
|
|
1244
|
+
* "em-dash": { "level": "block", "because": "House style for this client bans them outright." }
|
|
1245
|
+
* }
|
|
1246
|
+
* }
|
|
1247
|
+
*
|
|
1248
|
+
* A severity change needs a `because`, like an exception in
|
|
1249
|
+
* `art-direction.json`, and for the same reason: a tell switched off with no
|
|
1250
|
+
* reason is a guard nobody can audit. `off` becomes an exception, so the
|
|
1251
|
+
* report still lists what it silenced.
|
|
1252
|
+
*/
|
|
1253
|
+
|
|
1254
|
+
type SeverityLevel = "warn" | "block" | "off";
|
|
1255
|
+
interface SeverityOverride {
|
|
1256
|
+
level: SeverityLevel;
|
|
1257
|
+
because: string;
|
|
1258
|
+
}
|
|
1259
|
+
interface CraftConfig {
|
|
1260
|
+
/** Glob patterns for paths that are not the site. Added to `DEFAULT_IGNORE`. */
|
|
1261
|
+
ignore: string[];
|
|
1262
|
+
/** Where `craft copy` looks when no path is given. */
|
|
1263
|
+
copyPaths?: string[];
|
|
1264
|
+
severity: Record<string, SeverityOverride>;
|
|
1265
|
+
}
|
|
1266
|
+
/**
|
|
1267
|
+
* Agent and tool folders: instructions for the people and models building
|
|
1268
|
+
* the site, not copy a visitor reads. Always ignored by a directory walk.
|
|
1269
|
+
*/
|
|
1270
|
+
declare const DEFAULT_IGNORE: string[];
|
|
1271
|
+
/**
|
|
1272
|
+
* Validate a parsed `craft.config.json`. Throws with the file name and the
|
|
1273
|
+
* key at fault: a config that half-applies is worse than one that stops the
|
|
1274
|
+
* run.
|
|
1275
|
+
*/
|
|
1276
|
+
declare function parseCraftConfig(data: unknown, knownTells: ReadonlySet<string>, source?: string): CraftConfig;
|
|
1277
|
+
/**
|
|
1278
|
+
* A glob as a regular expression over a `/`-separated relative path.
|
|
1279
|
+
* `*` is one segment's worth, `**` any depth, `?` one character. A pattern
|
|
1280
|
+
* with no `/` matches a file or folder of that name anywhere; otherwise it is
|
|
1281
|
+
* anchored at the repo root. Anything under a matched folder matches too.
|
|
1282
|
+
*/
|
|
1283
|
+
declare function globToRegExp(glob: string): RegExp;
|
|
1284
|
+
/** A matcher for a set of globs. Paths are normalised to `/` before matching. */
|
|
1285
|
+
declare function ignoreMatcher(patterns: string[]): (path: string) => boolean;
|
|
1286
|
+
/** `off` entries, as exceptions: applied, and listed as silenced in the report. */
|
|
1287
|
+
declare function severityExceptions(config: CraftConfig): TellException[];
|
|
1288
|
+
/** `warn` and `block` entries, applied to a finished report. */
|
|
1289
|
+
declare function applySeverity(report: CheckReport, config: CraftConfig): CheckReport;
|
|
1290
|
+
|
|
1291
|
+
/**
|
|
1292
|
+
* A report as SARIF 2.1.0, for GitHub code scanning and any other tool that
|
|
1293
|
+
* reads it. Pure.
|
|
1294
|
+
*
|
|
1295
|
+
* One rule per tell the report names, carrying the tell's `why` and `fix`.
|
|
1296
|
+
* `block` findings are errors, `warn` findings warnings. A finding on a
|
|
1297
|
+
* rendered page has the URL as its location and no line: GitHub code
|
|
1298
|
+
* scanning only shows results in files of the repo, so those appear in the
|
|
1299
|
+
* SARIF file but not in the Security tab.
|
|
1300
|
+
*/
|
|
1301
|
+
|
|
1302
|
+
interface SarifTell {
|
|
1303
|
+
id: string;
|
|
1304
|
+
name: string;
|
|
1305
|
+
why: string;
|
|
1306
|
+
fix: string;
|
|
1307
|
+
}
|
|
1308
|
+
interface SarifOptions {
|
|
1309
|
+
/** The catalogue, for each rule's description. */
|
|
1310
|
+
tells: readonly SarifTell[];
|
|
1311
|
+
/** Where a reader learns more. */
|
|
1312
|
+
informationUri?: string;
|
|
1313
|
+
}
|
|
1314
|
+
declare function toSarif(report: CheckReport, options: SarifOptions): {
|
|
1315
|
+
$schema: string;
|
|
1316
|
+
version: "2.1.0";
|
|
1317
|
+
runs: {
|
|
1318
|
+
tool: {
|
|
1319
|
+
driver: {
|
|
1320
|
+
name: string;
|
|
1321
|
+
version: string;
|
|
1322
|
+
informationUri: string;
|
|
1323
|
+
rules: {
|
|
1324
|
+
fullDescription?: {
|
|
1325
|
+
text: string;
|
|
1326
|
+
} | undefined;
|
|
1327
|
+
help?: {
|
|
1328
|
+
text: string;
|
|
1329
|
+
} | undefined;
|
|
1330
|
+
id: string;
|
|
1331
|
+
name: string;
|
|
1332
|
+
shortDescription: {
|
|
1333
|
+
text: string;
|
|
1334
|
+
};
|
|
1335
|
+
}[];
|
|
1336
|
+
};
|
|
1337
|
+
};
|
|
1338
|
+
results: {
|
|
1339
|
+
ruleId: string;
|
|
1340
|
+
ruleIndex: number;
|
|
1341
|
+
level: "error" | "warning";
|
|
1342
|
+
message: {
|
|
1343
|
+
text: string;
|
|
1344
|
+
};
|
|
1345
|
+
locations: {
|
|
1346
|
+
physicalLocation: {
|
|
1347
|
+
region?: {
|
|
1348
|
+
startLine: number;
|
|
1349
|
+
snippet: {
|
|
1350
|
+
text: string;
|
|
1351
|
+
};
|
|
1352
|
+
} | undefined;
|
|
1353
|
+
artifactLocation: {
|
|
1354
|
+
uri: string;
|
|
1355
|
+
};
|
|
1356
|
+
};
|
|
1357
|
+
}[];
|
|
1358
|
+
partialFingerprints: {
|
|
1359
|
+
"craftFinding/v1": string;
|
|
1360
|
+
};
|
|
1361
|
+
}[];
|
|
1362
|
+
}[];
|
|
1363
|
+
};
|
|
1364
|
+
|
|
1365
|
+
/**
|
|
1366
|
+
* The `--json` contract. Every JSON document a craft command prints carries
|
|
1367
|
+
* `schemaVersion`, so a script reading it can refuse a shape it does not
|
|
1368
|
+
* know instead of misreading it. Bump it when a field is removed or changes
|
|
1369
|
+
* meaning; adding a field is not a bump.
|
|
1370
|
+
*/
|
|
1371
|
+
declare const JSON_SCHEMA_VERSION = 1;
|
|
1372
|
+
/** A command's JSON output, versioned. */
|
|
1373
|
+
declare function toJson(data: object): string;
|
|
1374
|
+
|
|
1191
1375
|
/**
|
|
1192
1376
|
* The rendered detection path for tells that can be seen on a live page.
|
|
1193
1377
|
*
|
|
@@ -1820,4 +2004,4 @@ declare function characterReport(input: CharacterInputs, copyTells?: Set<string>
|
|
|
1820
2004
|
|
|
1821
2005
|
declare function retrofitPlan(report: CharacterReport, direction?: ArtDirection | null): string;
|
|
1822
2006
|
|
|
1823
|
-
export { AI_PHRASES, AI_VIOLET, AI_WORDS, type AccentFork, type AccentForkOptions, type Action, type Area, type ArtDirection, BUZZWORDS, CATALOGUE, CATALOGUE_VERSION, CHOICE_KEYS, type CandidateKind, type CharacterInputs, type CharacterReport, type CheckOptions, type CheckReport, type CheckRestraintInput, type ChoiceKey, type Claim, type ClaimsReport, type ContrastCheck, type ContrastReport, type CopyTell, type CraftTokensInput, type CraftTokensResult, DENSITIES, DENSITY_NAMES, DIRECTION_VERSION, DISTANCE_WEIGHTS, DURATION_MS, DURATION_S, type DensityCssOptions, type DensityName, type DirectionChoice, type DirectionProblem, type DirectionReport, type DirectionSource, type DurationName, EASE, EASE_TUPLE, ESTATE_VERSION, EXIT_RATIO, type EaseName, type EmitCssOptions, type EstateMatch, type EstatePair, type EstateRegister, type EstateSite, FINGERPRINT_VERSION, type Fact, type FactComparison, type FactKind, type Finding, type Fingerprint, type FingerprintDistance, type FluidSpaceOptions, type FluidTypeOptions, type FluidTypeResult, type FontClass, type Gamut, type Generation, HOUSE, HOUSE_BUDGET, HOUSE_TYPE, type HarvestCandidate, type HarvestOptions, type Hit, type HouseRule, type HouseTier, LIGHTNESS_CURVE, MIN_DECIDED, MIN_RUNS, type MotionDecision, type MotionKind, NEGATIVE_REASSURANCE, NULL_VERSION, type NullModel, type NullRun, type Oklch, type OklchToHexOptions, PILL_LIMIT, PLAINER_WORDS, PROPOSED, type PaletteColour, type Proposal, type ProposeInput, RAMP_STEPS, REFLEX_FONTS_1, REFLEX_FONTS_2, RENDERED_PATHS, REVEAL_LIMIT, REVIEW_PHRASES, type Ramp, type RampFromAnchorsOptions, type RampOptions, type RampStep, type RestraintBudget, type RestraintReport, type RestraintSeverity, type RestraintViolation, type Rgb, SCALE, SHADCN_LIMIT, SHADCN_PRIMITIVES, SIBLING_AT, SNAPSHOT_VERSION, SOURCE_KINDS, SPACE_STEPS, SPRING, STOCK_PHRASES, type SectionKind, type SectionRhythmOptions, type SemanticInput, type SemanticResult, type Severity, type ShouldAnimateInput, type SignalResult, type Snapshot, type SnapshotColour, type SnapshotControl, type SnapshotEffects, type SnapshotFont, type SnapshotGradient, type SnapshotHeading, type SnapshotMotion, type SnapshotPatch, type SnapshotSection, type SourceFile, type SourceKind, type SourceTell, type SpaceStep, type Surface, TELL_HEAVY, TYPE_STEPS, TYPICAL_AT, type TailwindPreset, type Tell, type TellException, type TypeStep, type Typicality, VAGUE_WORDS, type ValidateContext, type Verdict, accentFork, addSite, apcaContrast, applyHouseGate, auditSnapshot, catalogueTable, characterReport, checkCopy, checkPair, checkRestraint, choicesOf, compareFacts, compareToEstate, craftTokens, deltaEOk, deltaEOkHex, densityCss, densityTokens, emitCss, emptyEstate, estatePairs, exitDuration, extractHtml, findClaims, findColours, fingerprint, fingerprintDistance, fluidClamp, fluidSpace, fluidType, fontClass, formatClaims, formatComparison, formatHex, formatReport, groundName, harvest, hexToOklch, houseRule, hueName, hueSwatch, inP3Gamut, inSrgbGamut, initDirection, isAiViolet, isCream, makeSnapshot, motionTokens, namedSources, nearest, normaliseFamily, nullPrompt, oklchToHex, oklchToRgb, paletteFromPixels, parseColour, parseHex, propose, protectedFacts, ramp, rampFromAnchors, retrofitPlan, runTell, scanSource, sectionRhythm, semantic, shapeName, sharedParts, shouldAnimate, siblingLine, tailwindV3Preset, tailwindV4Theme, tellById, toGamut, typeFeatureTokens, typicality, validateDirection, visibleText, wcagContrast, wordListsJson };
|
|
2007
|
+
export { AI_PHRASES, AI_VIOLET, AI_WORDS, type AccentFork, type AccentForkOptions, type Action, type Area, type ArtDirection, BASELINE_VERSION, BUZZWORDS, type Baseline, type BaselineEntry, CATALOGUE, CATALOGUE_VERSION, CHOICE_KEYS, type CandidateKind, type CharacterInputs, type CharacterReport, type CheckOptions, type CheckReport, type CheckRestraintInput, type ChoiceKey, type Claim, type ClaimsReport, type ContrastCheck, type ContrastReport, type CopyTell, type CraftConfig, type CraftTokensInput, type CraftTokensResult, DEFAULT_IGNORE, DENSITIES, DENSITY_NAMES, DIRECTION_VERSION, DISTANCE_WEIGHTS, DURATION_MS, DURATION_S, type DensityCssOptions, type DensityName, type DirectionChoice, type DirectionProblem, type DirectionReport, type DirectionSource, type DurationName, EASE, EASE_TUPLE, ESTATE_VERSION, EXIT_RATIO, type EaseName, type EmitCssOptions, type EstateMatch, type EstatePair, type EstateRegister, type EstateSite, FINGERPRINT_VERSION, type Fact, type FactComparison, type FactKind, type Finding, type Fingerprint, type FingerprintDistance, type FluidSpaceOptions, type FluidTypeOptions, type FluidTypeResult, type FontClass, type Gamut, type Generation, HOUSE, HOUSE_BUDGET, HOUSE_TYPE, type HarvestCandidate, type HarvestOptions, type Hit, type HouseRule, type HouseTier, JSON_SCHEMA_VERSION, LIGHTNESS_CURVE, MIN_DECIDED, MIN_RUNS, type MotionDecision, type MotionKind, NEGATIVE_REASSURANCE, NULL_VERSION, type NullModel, type NullRun, type Oklch, type OklchToHexOptions, PILL_LIMIT, PLAINER_WORDS, PROPOSED, type PaletteColour, type Proposal, type ProposeInput, RAMP_STEPS, REFLEX_FONTS_1, REFLEX_FONTS_2, RENDERED_PATHS, REVEAL_LIMIT, REVIEW_PHRASES, type Ramp, type RampFromAnchorsOptions, type RampOptions, type RampStep, type RestraintBudget, type RestraintReport, type RestraintSeverity, type RestraintViolation, type Rgb, SCALE, SHADCN_LIMIT, SHADCN_PRIMITIVES, SIBLING_AT, SNAPSHOT_VERSION, SOURCE_KINDS, SPACE_STEPS, SPRING, STOCK_PHRASES, type SarifOptions, type SarifTell, type SectionKind, type SectionRhythmOptions, type SemanticInput, type SemanticResult, type Severity, type SeverityLevel, type SeverityOverride, type ShouldAnimateInput, type SignalResult, type Snapshot, type SnapshotColour, type SnapshotControl, type SnapshotEffects, type SnapshotFont, type SnapshotGradient, type SnapshotHeading, type SnapshotMotion, type SnapshotPatch, type SnapshotSection, type SourceFile, type SourceKind, type SourceTell, type SpaceStep, type Surface, TELL_HEAVY, TYPE_STEPS, TYPICAL_AT, type TailwindPreset, type Tell, type TellException, type TypeStep, type Typicality, VAGUE_WORDS, type ValidateContext, type Verdict, accentFork, addSite, apcaContrast, applyBaseline, applyHouseGate, applySeverity, auditSnapshot, catalogueTable, characterReport, checkCopy, checkPair, checkRestraint, choicesOf, compareFacts, compareToEstate, craftTokens, createBaseline, deltaEOk, deltaEOkHex, densityCss, densityTokens, emitCss, emptyEstate, estatePairs, exitDuration, extractHtml, findClaims, findColours, findingKey, fingerprint, fingerprintDistance, fluidClamp, fluidSpace, fluidType, fontClass, formatClaims, formatComparison, formatHex, formatReport, globToRegExp, groundName, harvest, hexToOklch, houseRule, hueName, hueSwatch, ignoreMatcher, inP3Gamut, inSrgbGamut, initDirection, isAiViolet, isCream, makeSnapshot, motionTokens, namedSources, nearest, normaliseFamily, nullPrompt, oklchToHex, oklchToRgb, paletteFromPixels, parseBaseline, parseColour, parseCraftConfig, parseHex, propose, protectedFacts, ramp, rampFromAnchors, retrofitPlan, runTell, scanSource, sectionRhythm, semantic, severityExceptions, shapeName, sharedParts, shouldAnimate, siblingLine, tailwindV3Preset, tailwindV4Theme, tellById, toGamut, toJson, toSarif, typeFeatureTokens, typicality, validateDirection, visibleText, wcagContrast, wordListsJson };
|