@erclx/canon 4.93.0 → 4.95.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.
@@ -4,6 +4,10 @@ description: Enforce universal testing standards and best practices
4
4
 
5
5
  # Testing standards
6
6
 
7
+ ## Before writing a test
8
+
9
+ - Load the `canon:test-craft` skill before choosing the layer for a new test, and report it rather than proceeding silently when the skill does not resolve.
10
+
7
11
  ## Test structure
8
12
 
9
13
  - Structure tests using the Arrange, Act, Assert (AAA) pattern.
@@ -12,9 +16,7 @@ description: Enforce universal testing standards and best practices
12
16
 
13
17
  ## Test focus
14
18
 
15
- - Test user-visible behavior rather than implementation details.
16
19
  - Do not test private functions or internal state directly.
17
- - Cover critical paths and edge cases.
18
20
  - Do not target arbitrary coverage percentages.
19
21
 
20
22
  ## Organization and isolation
@@ -9,6 +9,10 @@ paths:
9
9
 
10
10
  # TypeScript/JavaScript testing tooling
11
11
 
12
+ ## Layer
13
+
14
+ - Load the `canon:test-craft` skill to pick the layer a test belongs at before choosing the tooling below, and report it rather than proceeding silently when the skill does not resolve.
15
+
12
16
  ## Unit and integration
13
17
 
14
18
  - Use Vitest for unit and integration tests.
@@ -8,6 +8,10 @@ paths:
8
8
 
9
9
  # Python testing tooling
10
10
 
11
+ ## Layer
12
+
13
+ - Load the `canon:test-craft` skill to pick the layer a test belongs at before choosing the tooling below, and report it rather than proceeding silently when the skill does not resolve.
14
+
11
15
  ## Framework
12
16
 
13
17
  - Use `pytest` for all tests. Do not use `unittest.TestCase`.
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@erclx/canon",
3
3
  "type": "module",
4
- "version": "4.93.0",
4
+ "version": "4.95.0",
5
5
  "description": "Infrastructure and quality tooling for developer workflows",
6
6
  "license": "MIT",
7
7
  "bin": {
@@ -54,6 +54,11 @@ export const MISC_CASES: readonly SkillCase[] = [
54
54
  "I'm about to write the retry helper we settled on and nothing covers it yet, so get the failing case in first.",
55
55
  expect: 'test-first',
56
56
  },
57
+ {
58
+ prompt:
59
+ 'The loading state already shipped. Should its test be an e2e test or a component one, and is the one I wrote any good?',
60
+ expect: 'test-craft',
61
+ },
57
62
  {
58
63
  prompt: 'Does our github about text still match what the readme says?',
59
64
  expect: 'repo-metadata',
@@ -225,11 +225,16 @@ const TEACH_CHROME: Component = {
225
225
  '--teach-chrome',
226
226
  '--teach-shadow',
227
227
  '--color-teach-accent-bg',
228
+ '--type-body-family',
229
+ '--type-code-family',
230
+ '--t3',
231
+ '--t4',
232
+ '--t5',
228
233
  ],
229
234
  rules: `:root {
230
- --teach-sans: 'Nunito', ui-rounded, 'Segoe UI', system-ui, sans-serif;
231
- --teach-hand: 'Virgil', 'Nunito', cursive;
232
- --teach-mono: 'Cascadia Code', ui-monospace, monospace;
235
+ --teach-sans: var(--type-body-family);
236
+ --teach-hand: 'Virgil', 'Excalifont', cursive;
237
+ --teach-mono: var(--type-code-family);
233
238
  --teach-measure: 52rem;
234
239
  --teach-chrome: 52rem;
235
240
  --teach-mast-h: 4.4rem;
@@ -268,7 +273,7 @@ body {
268
273
  background: var(--color-background);
269
274
  color: var(--color-text-body);
270
275
  font-family: var(--teach-sans);
271
- font-size: 1.125rem;
276
+ font-size: var(--t3);
272
277
  line-height: 1.62;
273
278
  -webkit-font-smoothing: antialiased;
274
279
  }
@@ -297,7 +302,7 @@ main { max-width: calc(var(--teach-measure) + 3rem); margin: 0 auto; padding: 2.
297
302
  justify-content: space-between;
298
303
  align-items: center;
299
304
  gap: 1rem;
300
- font-size: 0.8125rem;
305
+ font-size: var(--t5);
301
306
  color: var(--color-muted);
302
307
  }
303
308
 
@@ -332,7 +337,7 @@ main { max-width: calc(var(--teach-measure) + 3rem); margin: 0 auto; padding: 2.
332
337
  border-radius: 8px;
333
338
  text-decoration: none;
334
339
  color: var(--color-text-body);
335
- font-size: 0.9375rem;
340
+ font-size: var(--t4);
336
341
  font-weight: 600;
337
342
  line-height: 1.3;
338
343
  box-shadow: var(--teach-shadow);
@@ -370,14 +375,14 @@ main { max-width: calc(var(--teach-measure) + 3rem); margin: 0 auto; padding: 2.
370
375
  value for a character even a decorative one. */
371
376
  .crumb-sep {
372
377
  color: var(--color-muted);
373
- font-size: 0.9375rem;
378
+ font-size: var(--t4);
374
379
  user-select: none;
375
380
  }
376
381
 
377
382
  /* One arrow, on the first segment, since that is the only one that goes up. */
378
383
  .crumb-back {
379
384
  margin-right: 0.3rem;
380
- font-size: 0.9375rem;
385
+ font-size: var(--t4);
381
386
  line-height: 1;
382
387
  }
383
388
 
@@ -612,6 +617,9 @@ const TEACH_ARTICLE: Component = {
612
617
  '--color-accent',
613
618
  '--teach-hand',
614
619
  '--teach-mono',
620
+ '--t4',
621
+ '--t5',
622
+ '--t6',
615
623
  ],
616
624
  rules: `/* ---- Type ---- */
617
625
 
@@ -664,7 +672,7 @@ em { font-style: italic; }
664
672
  font-weight: 700;
665
673
  letter-spacing: 0.06em;
666
674
  text-transform: uppercase;
667
- font-size: 0.6875rem;
675
+ font-size: var(--t6);
668
676
  margin-bottom: 0.2rem;
669
677
  }
670
678
 
@@ -680,7 +688,7 @@ code {
680
688
 
681
689
  pre {
682
690
  font-family: var(--teach-mono);
683
- font-size: 0.8125rem;
691
+ font-size: var(--t5);
684
692
  line-height: 1.7;
685
693
  background: var(--color-surface);
686
694
  padding: 1.15rem 1.3rem;
@@ -745,12 +753,12 @@ tbody tr.mark td { background: var(--color-teach-accent-bg); }
745
753
  }
746
754
 
747
755
  .toc a:hover { background: var(--color-surface); }
748
- .toc .num { font-family: var(--teach-mono); font-size: 0.8125rem; color: var(--color-accent); }
756
+ .toc .num { font-family: var(--teach-mono); font-size: var(--t5); color: var(--color-accent); }
749
757
  .toc b { font-size: 1.0625rem; font-weight: 700; letter-spacing: -0.012em; }
750
758
 
751
759
  .toc .blurb {
752
760
  grid-column: 2;
753
- font-size: 0.9375rem;
761
+ font-size: var(--t4);
754
762
  line-height: 1.5;
755
763
  color: var(--color-text-secondary);
756
764
  margin-top: 0.1rem;
@@ -799,7 +807,7 @@ tbody tr.mark td { background: var(--color-teach-accent-bg); }
799
807
  ol.succ {
800
808
  margin: 0 0 2.5rem;
801
809
  padding-left: 1.35rem;
802
- font-size: 0.9375rem;
810
+ font-size: var(--t4);
803
811
  line-height: 1.6;
804
812
  color: var(--color-text-secondary);
805
813
  }
@@ -846,13 +854,13 @@ ol.succ li { margin-bottom: 0.4rem; }
846
854
 
847
855
  .road-n {
848
856
  font-family: var(--teach-mono);
849
- font-size: 0.8125rem;
857
+ font-size: var(--t5);
850
858
  color: var(--color-accent);
851
859
  }
852
860
 
853
861
  .road-b { display: block; }
854
862
  .road-b b { display: block; margin-bottom: 0.2rem; }
855
- .road-b span { color: var(--color-text-secondary); font-size: 0.9375rem; line-height: 1.55; }
863
+ .road-b span { color: var(--color-text-secondary); font-size: var(--t4); line-height: 1.55; }
856
864
 
857
865
  .road-t {
858
866
  font-family: var(--teach-mono);
@@ -889,6 +897,8 @@ const TEACH_QUIZ: Component = {
889
897
  '--teach-mono',
890
898
  '--teach-shadow',
891
899
  '--color-teach-accent-bg',
900
+ '--t4',
901
+ '--t5',
892
902
  ],
893
903
  rules: `/* ---- Quiz ---- */
894
904
 
@@ -907,7 +917,7 @@ const TEACH_QUIZ: Component = {
907
917
  margin-bottom: 0.45rem;
908
918
  cursor: pointer;
909
919
  font-family: var(--teach-sans);
910
- font-size: 0.9375rem;
920
+ font-size: var(--t4);
911
921
  background: transparent;
912
922
  width: 100%;
913
923
  text-align: left;
@@ -967,7 +977,7 @@ const TEACH_QUIZ: Component = {
967
977
 
968
978
  .fb {
969
979
  display: none;
970
- font-size: 0.9375rem;
980
+ font-size: var(--t4);
971
981
  line-height: 1.55;
972
982
  color: var(--color-text-secondary);
973
983
  background: var(--color-surface);
@@ -983,7 +993,7 @@ footer {
983
993
  margin-top: 4rem;
984
994
  padding-top: 1.4rem;
985
995
  border-top: 1px solid var(--color-border);
986
- font-size: 0.8125rem;
996
+ font-size: var(--t5);
987
997
  line-height: 1.6;
988
998
  color: var(--color-muted);
989
999
  }`,
@@ -1004,6 +1014,8 @@ const TEACH_GLOSSARY: Component = {
1004
1014
  '--color-accent',
1005
1015
  '--teach-sans',
1006
1016
  '--teach-mono',
1017
+ '--t4',
1018
+ '--t5',
1007
1019
  ],
1008
1020
  rules: `/* ---- Glossary view, generated from the markdown source ---- */
1009
1021
 
@@ -1022,7 +1034,7 @@ h2 .count {
1022
1034
  .filter {
1023
1035
  width: 100%;
1024
1036
  font-family: var(--teach-sans);
1025
- font-size: 0.9375rem;
1037
+ font-size: var(--t4);
1026
1038
  color: var(--color-text-body);
1027
1039
  background: var(--color-background);
1028
1040
  border: 1px solid var(--color-border);
@@ -1064,7 +1076,7 @@ h2 .count {
1064
1076
  display: none;
1065
1077
  padding: 1.2rem 0;
1066
1078
  color: var(--color-muted);
1067
- font-size: 0.9375rem;
1079
+ font-size: var(--t4);
1068
1080
  }
1069
1081
 
1070
1082
  .gloss.none .empty { display: block; }
@@ -1072,14 +1084,14 @@ h2 .count {
1072
1084
  .gterm {
1073
1085
  padding: 0.7rem 0;
1074
1086
  border-bottom: 1px solid var(--color-border);
1075
- font-size: 0.9375rem;
1087
+ font-size: var(--t4);
1076
1088
  line-height: 1.55;
1077
1089
  }
1078
1090
 
1079
1091
  .gloss-group {
1080
1092
  margin: 1.1rem 0 0.4rem;
1081
1093
  font-family: var(--teach-sans);
1082
- font-size: 0.8125rem;
1094
+ font-size: var(--t5);
1083
1095
  font-weight: 600;
1084
1096
  color: var(--color-muted);
1085
1097
  text-transform: uppercase;
@@ -1101,7 +1113,7 @@ h2 .count {
1101
1113
  ol.succ {
1102
1114
  margin: 0 0 2.5rem;
1103
1115
  padding-left: 1.35rem;
1104
- font-size: 0.9375rem;
1116
+ font-size: var(--t4);
1105
1117
  line-height: 1.6;
1106
1118
  color: var(--color-text-secondary);
1107
1119
  }
@@ -1137,6 +1149,7 @@ const TEACH_OUTLINE: Component = {
1137
1149
  '--teach-sans',
1138
1150
  '--teach-measure',
1139
1151
  '--teach-mast-h',
1152
+ '--t5',
1140
1153
  ],
1141
1154
  rules: `/* ---- In-lesson outline, in the gutter the measure leaves over ---- */
1142
1155
 
@@ -1151,7 +1164,7 @@ const TEACH_OUTLINE: Component = {
1151
1164
  width: calc(13rem + 8px);
1152
1165
  max-height: calc(100vh - var(--teach-mast-h) - 4rem);
1153
1166
  overflow-y: auto;
1154
- font-size: 0.8125rem;
1167
+ font-size: var(--t5);
1155
1168
  line-height: 1.45;
1156
1169
  }
1157
1170
 
@@ -1218,12 +1231,13 @@ const TEACH_REFERENCES: Component = {
1218
1231
  '--color-accent',
1219
1232
  '--teach-mono',
1220
1233
  '--color-teach-accent-bg',
1234
+ '--t5',
1221
1235
  ],
1222
1236
  rules: `footer {
1223
1237
  margin-top: 4rem;
1224
1238
  padding-top: 1.4rem;
1225
1239
  border-top: 1px solid var(--color-border);
1226
- font-size: 0.8125rem;
1240
+ font-size: var(--t5);
1227
1241
  line-height: 1.6;
1228
1242
  color: var(--color-muted);
1229
1243
  }
@@ -1252,7 +1266,7 @@ ol.refs {
1252
1266
  counter-reset: r;
1253
1267
  padding: 0;
1254
1268
  margin: 0.9rem 0 1.1rem;
1255
- font-size: 0.8125rem;
1269
+ font-size: var(--t5);
1256
1270
  line-height: 1.55;
1257
1271
  }
1258
1272