synthesisui 0.16.47 → 0.16.49
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/dist/commands/import.js
CHANGED
|
@@ -336,7 +336,18 @@ export async function takeCensus(root) {
|
|
|
336
336
|
}
|
|
337
337
|
}
|
|
338
338
|
const d = diagnose(reports);
|
|
339
|
-
const
|
|
339
|
+
const inventory = tallyToInventory(tally);
|
|
340
|
+
// The verdict travels WITH the payload: the platform reads one reading rather
|
|
341
|
+
// than computing a second opinion from the same numbers, which is how two
|
|
342
|
+
// implementations of the same judgement start disagreeing.
|
|
343
|
+
const verdicts = new Map(crosswalk(inventory).map((r) => [
|
|
344
|
+
r.component.name,
|
|
345
|
+
{ bucket: r.bucket, canonical: r.canonical, because: r.because },
|
|
346
|
+
]));
|
|
347
|
+
const components = inventory.map((c) => ({
|
|
348
|
+
...c,
|
|
349
|
+
...(verdicts.get(c.name) ?? {}),
|
|
350
|
+
}));
|
|
340
351
|
const pkgRaw = await readFile(join(root, "package.json"), "utf8").catch(() => null);
|
|
341
352
|
let name = null;
|
|
342
353
|
if (pkgRaw) {
|
|
@@ -477,6 +488,20 @@ function printCrosswalk(mine) {
|
|
|
477
488
|
show(`Already in the catalogue (${exists.length})`, exists, 6);
|
|
478
489
|
show(`The same decision, twice (${nearly.length})`, nearly, 6);
|
|
479
490
|
show(`Only yours (${exclusive.length})`, exclusive, 8);
|
|
491
|
+
// Counted, never listed: four icons and a provider under "only yours" pad the
|
|
492
|
+
// one list worth reading with the least interesting thing in it.
|
|
493
|
+
const icons = of("icon").length;
|
|
494
|
+
const providers = of("provider").length;
|
|
495
|
+
if (icons > 0 || providers > 0) {
|
|
496
|
+
const bits = [
|
|
497
|
+
icons > 0 &&
|
|
498
|
+
`${icons} icon${icons === 1 ? "" : "s"} (a library, not recipes)`,
|
|
499
|
+
providers > 0 &&
|
|
500
|
+
`${providers} provider${providers === 1 ? "" : "s"} (no UI of their own)`,
|
|
501
|
+
].filter(Boolean);
|
|
502
|
+
console.log(body(paint.faint(`Set aside: ${bits.join(" · ")}`)));
|
|
503
|
+
console.log("");
|
|
504
|
+
}
|
|
480
505
|
console.log(body(paint.dim("Nothing was mapped. This is a reading - the adopting is a decision you make.")));
|
|
481
506
|
}
|
|
482
507
|
function printAgentContract() {
|
|
@@ -59,7 +59,19 @@ function looksLikeType(source, at) {
|
|
|
59
59
|
* of copy wearing the shape of a variant axis. An axis is a closed set somebody
|
|
60
60
|
* designed; a title is whatever that screen happens to say.
|
|
61
61
|
*/
|
|
62
|
-
const
|
|
62
|
+
const CONTENT_WORD = "class|className|style|key|ref|id|href|src|alt|type|name|value|placeholder|children|title|label|text|heading|subtitle|caption|description|message|content|tooltip|hint|error|helper";
|
|
63
|
+
/**
|
|
64
|
+
* Whole name, or the TAIL of a camelCase compound.
|
|
65
|
+
*
|
|
66
|
+
* `bodyClassName` and `infoContent` walked straight past a whole-name match
|
|
67
|
+
* (dono, 30/07), and `infoContent` brought four sentences of screen copy into
|
|
68
|
+
* what is supposed to be a list of variant axes. The tail is what says what a
|
|
69
|
+
* prop IS: `infoContent` is content, `bodyClassName` is a class name.
|
|
70
|
+
*
|
|
71
|
+
* Matching the tail rather than anywhere keeps `titleTone` - an axis whose name
|
|
72
|
+
* merely starts with a content word.
|
|
73
|
+
*/
|
|
74
|
+
const NOT_A_DECISION = new RegExp(`^(?:${CONTENT_WORD})$|[a-z](?:${CONTENT_WORD.replace(/\b([a-z])/g, (_, c) => `[${c}${c.toUpperCase()}]`)})$|^(?:on[A-Z]|data-|aria-)`);
|
|
63
75
|
/** `import X, { A, B as C } from "spec"` - who owns each local name. */
|
|
64
76
|
const IMPORT = /import\s+(?:type\s+)?([\s\S]*?)\s+from\s+["']([^"']+)["']/g;
|
|
65
77
|
function importedNames(source, internal = []) {
|
package/dist/doctor/crosswalk.js
CHANGED
|
@@ -207,6 +207,26 @@ export function axisOverlap(a, b) {
|
|
|
207
207
|
shared += 1;
|
|
208
208
|
return shared / new Set([...va, ...vb]).size;
|
|
209
209
|
}
|
|
210
|
+
/**
|
|
211
|
+
* Names that are not components in the sense this crosswalk means.
|
|
212
|
+
*
|
|
213
|
+
* An ICON is a glyph in a set, and a design system models it as a library
|
|
214
|
+
* rather than as a recipe with variant axes - so listing four of them under
|
|
215
|
+
* "only yours" pads the interesting list with the least interesting thing in
|
|
216
|
+
* it (dono, 30/07). A PROVIDER renders no UI at all.
|
|
217
|
+
*
|
|
218
|
+
* Both are reported as counts instead, which says more in one line than four
|
|
219
|
+
* lines of "nothing in the catalogue does this".
|
|
220
|
+
*/
|
|
221
|
+
const IS_ICON = /(^Icon|Icon$)/;
|
|
222
|
+
const IS_PROVIDER = /(Provider|Context)$/;
|
|
223
|
+
export function classifyAside(name) {
|
|
224
|
+
if (IS_ICON.test(name))
|
|
225
|
+
return "icon";
|
|
226
|
+
if (IS_PROVIDER.test(name))
|
|
227
|
+
return "provider";
|
|
228
|
+
return null;
|
|
229
|
+
}
|
|
210
230
|
/** Below this, two components share a value or two by accident. */
|
|
211
231
|
export const TWIN_OVERLAP = 0.5;
|
|
212
232
|
/**
|
|
@@ -254,6 +274,18 @@ export function crosswalk(components) {
|
|
|
254
274
|
}
|
|
255
275
|
return mine
|
|
256
276
|
.map((component) => {
|
|
277
|
+
const aside = classifyAside(component.name);
|
|
278
|
+
if (aside) {
|
|
279
|
+
return {
|
|
280
|
+
component,
|
|
281
|
+
canonical: null,
|
|
282
|
+
twins: [],
|
|
283
|
+
bucket: aside,
|
|
284
|
+
because: aside === "icon"
|
|
285
|
+
? "a glyph, which a system models as a library rather than a recipe"
|
|
286
|
+
: "renders no UI - infrastructure, not a component",
|
|
287
|
+
};
|
|
288
|
+
}
|
|
257
289
|
const canonical = canonicalName(component.name);
|
|
258
290
|
const twins = mine
|
|
259
291
|
.filter((o) => o.name !== component.name)
|
package/package.json
CHANGED