chaffjs 0.21.0 → 0.22.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.
Files changed (214) hide show
  1. package/README.md +2 -1
  2. package/dist/cli-text.d.ts.map +1 -1
  3. package/dist/cli-text.js +4 -0
  4. package/dist/cli-text.js.map +1 -1
  5. package/dist/cli.d.ts.map +1 -1
  6. package/dist/cli.js +4 -11
  7. package/dist/cli.js.map +1 -1
  8. package/dist/commands/init-command.d.ts +4 -0
  9. package/dist/commands/init-command.d.ts.map +1 -0
  10. package/dist/commands/init-command.js +15 -0
  11. package/dist/commands/init-command.js.map +1 -0
  12. package/dist/commands/plugin-init.d.ts +20 -0
  13. package/dist/commands/plugin-init.d.ts.map +1 -0
  14. package/dist/commands/plugin-init.js +129 -0
  15. package/dist/commands/plugin-init.js.map +1 -0
  16. package/dist/commands/plugin-test.d.ts +11 -0
  17. package/dist/commands/plugin-test.d.ts.map +1 -0
  18. package/dist/commands/plugin-test.js +81 -0
  19. package/dist/commands/plugin-test.js.map +1 -0
  20. package/dist/custom/problems.d.ts.map +1 -1
  21. package/dist/custom/problems.js +1 -2
  22. package/dist/custom/problems.js.map +1 -1
  23. package/dist/detectors/amount-for-count.d.ts +21 -0
  24. package/dist/detectors/amount-for-count.d.ts.map +1 -0
  25. package/dist/detectors/amount-for-count.js +55 -0
  26. package/dist/detectors/amount-for-count.js.map +1 -0
  27. package/dist/detectors/currency-notation.d.ts +29 -0
  28. package/dist/detectors/currency-notation.d.ts.map +1 -0
  29. package/dist/detectors/currency-notation.js +58 -0
  30. package/dist/detectors/currency-notation.js.map +1 -0
  31. package/dist/detectors/dangling-opener.d.ts +14 -0
  32. package/dist/detectors/dangling-opener.d.ts.map +1 -0
  33. package/dist/detectors/dangling-opener.js +55 -0
  34. package/dist/detectors/dangling-opener.js.map +1 -0
  35. package/dist/detectors/footnote-mismatch.d.ts +11 -0
  36. package/dist/detectors/footnote-mismatch.d.ts.map +1 -0
  37. package/dist/detectors/footnote-mismatch.js +55 -0
  38. package/dist/detectors/footnote-mismatch.js.map +1 -0
  39. package/dist/detectors/form-minority.d.ts +13 -0
  40. package/dist/detectors/form-minority.d.ts.map +1 -0
  41. package/dist/detectors/form-minority.js +19 -0
  42. package/dist/detectors/form-minority.js.map +1 -0
  43. package/dist/detectors/heading-end-mark.d.ts +10 -0
  44. package/dist/detectors/heading-end-mark.d.ts.map +1 -0
  45. package/dist/detectors/heading-end-mark.js +59 -0
  46. package/dist/detectors/heading-end-mark.js.map +1 -0
  47. package/dist/detectors/list-marker.d.ts +7 -0
  48. package/dist/detectors/list-marker.d.ts.map +1 -0
  49. package/dist/detectors/list-marker.js +50 -0
  50. package/dist/detectors/list-marker.js.map +1 -0
  51. package/dist/detectors/markdown-slip.d.ts +19 -0
  52. package/dist/detectors/markdown-slip.d.ts.map +1 -0
  53. package/dist/detectors/markdown-slip.js +122 -0
  54. package/dist/detectors/markdown-slip.js.map +1 -0
  55. package/dist/detectors/numeral-opener.d.ts +10 -0
  56. package/dist/detectors/numeral-opener.d.ts.map +1 -0
  57. package/dist/detectors/numeral-opener.js +65 -0
  58. package/dist/detectors/numeral-opener.js.map +1 -0
  59. package/dist/detectors/ordinal-suffix.d.ts +12 -0
  60. package/dist/detectors/ordinal-suffix.d.ts.map +1 -0
  61. package/dist/detectors/ordinal-suffix.js +33 -0
  62. package/dist/detectors/ordinal-suffix.js.map +1 -0
  63. package/dist/detectors/range-notation.d.ts +15 -0
  64. package/dist/detectors/range-notation.d.ts.map +1 -0
  65. package/dist/detectors/range-notation.js +58 -0
  66. package/dist/detectors/range-notation.js.map +1 -0
  67. package/dist/detectors/registry/amount-for-count.d.ts +3 -0
  68. package/dist/detectors/registry/amount-for-count.d.ts.map +1 -0
  69. package/dist/detectors/registry/amount-for-count.js +3 -0
  70. package/dist/detectors/registry/amount-for-count.js.map +1 -0
  71. package/dist/detectors/registry/currency-notation.d.ts +3 -0
  72. package/dist/detectors/registry/currency-notation.d.ts.map +1 -0
  73. package/dist/detectors/registry/currency-notation.js +3 -0
  74. package/dist/detectors/registry/currency-notation.js.map +1 -0
  75. package/dist/detectors/registry/dangling-opener.d.ts +3 -0
  76. package/dist/detectors/registry/dangling-opener.d.ts.map +1 -0
  77. package/dist/detectors/registry/dangling-opener.js +3 -0
  78. package/dist/detectors/registry/dangling-opener.js.map +1 -0
  79. package/dist/detectors/registry/footnote-mismatch.d.ts +3 -0
  80. package/dist/detectors/registry/footnote-mismatch.d.ts.map +1 -0
  81. package/dist/detectors/registry/footnote-mismatch.js +3 -0
  82. package/dist/detectors/registry/footnote-mismatch.js.map +1 -0
  83. package/dist/detectors/registry/heading-end-punctuation.d.ts +3 -0
  84. package/dist/detectors/registry/heading-end-punctuation.d.ts.map +1 -0
  85. package/dist/detectors/registry/heading-end-punctuation.js +3 -0
  86. package/dist/detectors/registry/heading-end-punctuation.js.map +1 -0
  87. package/dist/detectors/registry/list-marker.d.ts +3 -0
  88. package/dist/detectors/registry/list-marker.d.ts.map +1 -0
  89. package/dist/detectors/registry/list-marker.js +3 -0
  90. package/dist/detectors/registry/list-marker.js.map +1 -0
  91. package/dist/detectors/registry/numeral-opener.d.ts +3 -0
  92. package/dist/detectors/registry/numeral-opener.d.ts.map +1 -0
  93. package/dist/detectors/registry/numeral-opener.js +3 -0
  94. package/dist/detectors/registry/numeral-opener.js.map +1 -0
  95. package/dist/detectors/registry/ordinal-suffix.d.ts +3 -0
  96. package/dist/detectors/registry/ordinal-suffix.d.ts.map +1 -0
  97. package/dist/detectors/registry/ordinal-suffix.js +3 -0
  98. package/dist/detectors/registry/ordinal-suffix.js.map +1 -0
  99. package/dist/detectors/registry/range-notation.d.ts +3 -0
  100. package/dist/detectors/registry/range-notation.d.ts.map +1 -0
  101. package/dist/detectors/registry/range-notation.js +3 -0
  102. package/dist/detectors/registry/range-notation.js.map +1 -0
  103. package/dist/detectors/registry/relative-pronoun-mix.d.ts +3 -0
  104. package/dist/detectors/registry/relative-pronoun-mix.d.ts.map +1 -0
  105. package/dist/detectors/registry/relative-pronoun-mix.js +3 -0
  106. package/dist/detectors/registry/relative-pronoun-mix.js.map +1 -0
  107. package/dist/detectors/registry/share-over-hundred.d.ts +3 -0
  108. package/dist/detectors/registry/share-over-hundred.d.ts.map +1 -0
  109. package/dist/detectors/registry/share-over-hundred.js +3 -0
  110. package/dist/detectors/registry/share-over-hundred.js.map +1 -0
  111. package/dist/detectors/registry/step-reference.d.ts +3 -0
  112. package/dist/detectors/registry/step-reference.d.ts.map +1 -0
  113. package/dist/detectors/registry/step-reference.js +3 -0
  114. package/dist/detectors/registry/step-reference.js.map +1 -0
  115. package/dist/detectors/registry/table-row-overflow.d.ts +3 -0
  116. package/dist/detectors/registry/table-row-overflow.d.ts.map +1 -0
  117. package/dist/detectors/registry/table-row-overflow.js +3 -0
  118. package/dist/detectors/registry/table-row-overflow.js.map +1 -0
  119. package/dist/detectors/registry/toc-heading.d.ts +3 -0
  120. package/dist/detectors/registry/toc-heading.d.ts.map +1 -0
  121. package/dist/detectors/registry/toc-heading.js +3 -0
  122. package/dist/detectors/registry/toc-heading.js.map +1 -0
  123. package/dist/detectors/registry/unclosed-code-fence.d.ts +3 -0
  124. package/dist/detectors/registry/unclosed-code-fence.d.ts.map +1 -0
  125. package/dist/detectors/registry/unclosed-code-fence.js +3 -0
  126. package/dist/detectors/registry/unclosed-code-fence.js.map +1 -0
  127. package/dist/detectors/registry/unrendered-emphasis.d.ts +3 -0
  128. package/dist/detectors/registry/unrendered-emphasis.d.ts.map +1 -0
  129. package/dist/detectors/registry/unrendered-emphasis.js +3 -0
  130. package/dist/detectors/registry/unrendered-emphasis.js.map +1 -0
  131. package/dist/detectors/relative-pronoun-mix.d.ts +19 -0
  132. package/dist/detectors/relative-pronoun-mix.d.ts.map +1 -0
  133. package/dist/detectors/relative-pronoun-mix.js +60 -0
  134. package/dist/detectors/relative-pronoun-mix.js.map +1 -0
  135. package/dist/detectors/share-over-hundred.d.ts +20 -0
  136. package/dist/detectors/share-over-hundred.d.ts.map +1 -0
  137. package/dist/detectors/share-over-hundred.js +55 -0
  138. package/dist/detectors/share-over-hundred.js.map +1 -0
  139. package/dist/detectors/step-reference.d.ts +20 -0
  140. package/dist/detectors/step-reference.d.ts.map +1 -0
  141. package/dist/detectors/step-reference.js +57 -0
  142. package/dist/detectors/step-reference.js.map +1 -0
  143. package/dist/detectors/toc-heading.d.ts +10 -0
  144. package/dist/detectors/toc-heading.d.ts.map +1 -0
  145. package/dist/detectors/toc-heading.js +99 -0
  146. package/dist/detectors/toc-heading.js.map +1 -0
  147. package/dist/list-marks.d.ts +21 -0
  148. package/dist/list-marks.d.ts.map +1 -0
  149. package/dist/list-marks.js +82 -0
  150. package/dist/list-marks.js.map +1 -0
  151. package/dist/rule-fields.d.ts +5 -0
  152. package/dist/rule-fields.d.ts.map +1 -1
  153. package/dist/rule-fields.js +21 -0
  154. package/dist/rule-fields.js.map +1 -1
  155. package/package.json +3 -3
  156. package/rules/cliche.yaml +67 -0
  157. package/rules/currency-notation-consistency.yaml +77 -0
  158. package/rules/dangling-participle.yaml +58 -0
  159. package/rules/footnote-mismatch.yaml +91 -0
  160. package/rules/heading-end-punctuation-mix.yaml +158 -0
  161. package/rules/less-for-fewer.yaml +59 -0
  162. package/rules/list-marker-mix.yaml +111 -0
  163. package/rules/nonstandard-word.yaml +80 -0
  164. package/rules/numeral-sentence-start.yaml +56 -0
  165. package/rules/ordinal-suffix-mismatch.yaml +65 -0
  166. package/rules/range-notation-consistency.yaml +73 -0
  167. package/rules/share-over-hundred.yaml +65 -0
  168. package/rules/step-reference-missing.yaml +85 -0
  169. package/rules/table-row-overflow.yaml +90 -0
  170. package/rules/toc-heading-mismatch.yaml +136 -0
  171. package/rules/unclosed-code-fence.yaml +107 -0
  172. package/rules/uncomparable-graded.yaml +65 -0
  173. package/rules/unrendered-emphasis.yaml +73 -0
  174. package/rules/which-that-consistency.yaml +64 -0
  175. package/skills/chaff/SKILL.md +7 -7
  176. package/src/cli-text.ts +4 -0
  177. package/src/cli.ts +5 -9
  178. package/src/commands/init-command.ts +13 -0
  179. package/src/commands/plugin-init.ts +150 -0
  180. package/src/commands/plugin-test.ts +111 -0
  181. package/src/custom/problems.ts +1 -3
  182. package/src/detectors/amount-for-count.ts +90 -0
  183. package/src/detectors/currency-notation.ts +90 -0
  184. package/src/detectors/dangling-opener.ts +74 -0
  185. package/src/detectors/footnote-mismatch.ts +72 -0
  186. package/src/detectors/form-minority.ts +21 -0
  187. package/src/detectors/heading-end-mark.ts +82 -0
  188. package/src/detectors/list-marker.ts +60 -0
  189. package/src/detectors/markdown-slip.ts +140 -0
  190. package/src/detectors/numeral-opener.ts +72 -0
  191. package/src/detectors/ordinal-suffix.ts +40 -0
  192. package/src/detectors/range-notation.ts +76 -0
  193. package/src/detectors/registry/amount-for-count.ts +4 -0
  194. package/src/detectors/registry/currency-notation.ts +4 -0
  195. package/src/detectors/registry/dangling-opener.ts +4 -0
  196. package/src/detectors/registry/footnote-mismatch.ts +4 -0
  197. package/src/detectors/registry/heading-end-punctuation.ts +4 -0
  198. package/src/detectors/registry/list-marker.ts +4 -0
  199. package/src/detectors/registry/numeral-opener.ts +4 -0
  200. package/src/detectors/registry/ordinal-suffix.ts +4 -0
  201. package/src/detectors/registry/range-notation.ts +4 -0
  202. package/src/detectors/registry/relative-pronoun-mix.ts +4 -0
  203. package/src/detectors/registry/share-over-hundred.ts +4 -0
  204. package/src/detectors/registry/step-reference.ts +4 -0
  205. package/src/detectors/registry/table-row-overflow.ts +4 -0
  206. package/src/detectors/registry/toc-heading.ts +4 -0
  207. package/src/detectors/registry/unclosed-code-fence.ts +4 -0
  208. package/src/detectors/registry/unrendered-emphasis.ts +4 -0
  209. package/src/detectors/relative-pronoun-mix.ts +79 -0
  210. package/src/detectors/share-over-hundred.ts +75 -0
  211. package/src/detectors/step-reference.ts +83 -0
  212. package/src/detectors/toc-heading.ts +125 -0
  213. package/src/list-marks.ts +106 -0
  214. package/src/rule-fields.ts +28 -0
@@ -0,0 +1,136 @@
1
+ id: toc-heading-mismatch
2
+ layer: L3
3
+ status: stable
4
+ how_to_find: toc-heading
5
+ requires: [markdown]
6
+ severity: warning
7
+
8
+ name:
9
+ ja: 見出しの無い目次の項目
10
+ en: A table-of-contents entry with no heading
11
+
12
+ why:
13
+ ja: 目次に「3.2 費用」とあるのに本文にその見出しが無ければ、読み手は目次から探しても行き着けません。見出しを書き換えたり節を消したりしたあとに、目次だけが古いまま残ると起きます。目次の項目と見出しの言葉を突き合わせれば、機械で言えます。
14
+ en: When the table of contents lists "3.2 Costs" and the text has no such heading, the reader cannot get there from the contents. It happens when a heading is renamed or a section removed and the contents are left as they were. Matching the entries against the headings is mechanical.
15
+
16
+ message:
17
+ ja: 目次の「{entry}」に合う見出しがありません
18
+ en: 'No heading matches the contents entry "{entry}"'
19
+
20
+ how_to_fix:
21
+ ja: 目次を見出しに合わせて直すか、消えた節の項目を目次から消してください。
22
+ en: Update the entry to match the heading, or remove the entry for a section that is gone.
23
+
24
+ levels: { normal: warning, relaxed: info }
25
+
26
+ use_for: [business, technical, blog, legal, docs, academic, literature, speech]
27
+
28
+ group: structure
29
+ summary:
30
+ ja: 目次(「目次」「Contents」の見出しの下の箇条書き)の項目のうち、文書のどの見出しとも合わないもの
31
+ en: An entry of the table of contents (the list under a "Contents" heading) that matches no heading of the document
32
+ example:
33
+ ja:
34
+ before: |
35
+ ## 目次
36
+
37
+ - 1 概要
38
+ - 2 費用
39
+ - 3 日程
40
+
41
+ ## 1 概要
42
+
43
+ 本書の概要です。
44
+
45
+ ## 2 料金
46
+
47
+ 料金の説明です。
48
+
49
+ ## 3 日程
50
+
51
+ 日程の説明です。
52
+ after: |
53
+ ## 目次
54
+
55
+ - 1 概要
56
+ - 2 料金
57
+ - 3 日程
58
+
59
+ ## 1 概要
60
+
61
+ 本書の概要です。
62
+
63
+ ## 2 料金
64
+
65
+ 料金の説明です。
66
+
67
+ ## 3 日程
68
+
69
+ 日程の説明です。
70
+ en:
71
+ before: |
72
+ ## Contents
73
+
74
+ - 1 Overview
75
+ - 2 Costs
76
+ - 3 Schedule
77
+
78
+ ## 1 Overview
79
+
80
+ An overview.
81
+
82
+ ## 2 Fees
83
+
84
+ The fees.
85
+
86
+ ## 3 Schedule
87
+
88
+ The schedule.
89
+ after: |
90
+ ## Contents
91
+
92
+ - 1 Overview
93
+ - 2 Fees
94
+ - 3 Schedule
95
+
96
+ ## 1 Overview
97
+
98
+ An overview.
99
+
100
+ ## 2 Fees
101
+
102
+ The fees.
103
+
104
+ ## 3 Schedule
105
+
106
+ The schedule.
107
+
108
+ not_flagged:
109
+ ja: 項目と見出しは、空白・記号・大文字小文字を無視して比べ、頭の番号(1.2、2-1)と、ページ番号(…… 12)を外しても比べます。リンクの項目は字の部分を比べます(リンクの行き先は broken-link が見ます)。目次の項目の半分より多くが見出しに合わない文書は、本文と別の章立ての目次と読んで言いません。Markdown の見出しのある文書だけを見ます。
110
+ en: Entries and headings are compared ignoring spaces, punctuation and case, and again without a leading number (1.2, 2-1) or a page number (.... 12). For a linked entry the link text is compared (broken-link checks where it points). When more than half of the entries match no heading, the contents are read as following another outline and nothing is reported. Only Markdown documents with headings are checked.
111
+
112
+ rewrite:
113
+ ja:
114
+ direction: 目次の項目を、本文の見出しの言葉と番号に合わせてください。節を消したのなら、その項目を目次から消します。
115
+ pairs:
116
+ - before: 目次の「2 費用」(見出しは「2 料金」)
117
+ after: 目次の「2 料金」
118
+ - before: 目次の「4 付録」(本文に付録の節が無い)
119
+ after: 目次から「4 付録」を消す
120
+ keep:
121
+ - 本文の見出し
122
+ - 目次の並び順
123
+ avoid:
124
+ - 目次に合わせて本文の見出しを書き換える
125
+ en:
126
+ direction: Make each contents entry match the heading's words and number. If a section was removed, remove its entry.
127
+ pairs:
128
+ - before: The contents entry "2 Costs" (the heading is "2 Fees")
129
+ after: The contents entry "2 Fees"
130
+ - before: The contents entry "4 Appendix" (no appendix in the text)
131
+ after: The entry "4 Appendix" removed
132
+ keep:
133
+ - the headings in the text
134
+ - the order of the contents
135
+ avoid:
136
+ - renaming a heading in the text to match the contents
@@ -0,0 +1,107 @@
1
+ id: unclosed-code-fence
2
+ layer: L1
3
+ status: stable
4
+ how_to_find: unclosed-code-fence
5
+ requires: [markdown]
6
+ severity: warning
7
+
8
+ name:
9
+ ja: 閉じていないコードブロック
10
+ en: Unclosed code fence
11
+
12
+ why:
13
+ ja: 「```」で始めたコードブロックを閉じ忘れると、Markdown は文書の終わり(リストの項目の中ならその項目の終わり)までをすべてコードとして表示します。後ろの見出しも本文も等幅の字の塊になり、読み手には文書が壊れて見えます。
14
+ en: A code block opened with "```" and never closed runs to the end of the document (or of the list item it is in), so Markdown shows everything after it as code. The headings and text that follow turn into one block of monospaced text, and the document looks broken.
15
+
16
+ message:
17
+ ja: 「{fence}」で始めたコードブロックが閉じていません
18
+ en: 'The code block opened with "{fence}" is never closed'
19
+
20
+ how_to_fix:
21
+ ja: コードの終わりに、始めと同じ記号を同じ数以上並べた行(「```」)を足してください。
22
+ en: Add a line after the code with the same character, at least as many ("```").
23
+
24
+ placeholders:
25
+ fence:
26
+ ja: 記号
27
+ en: the fence
28
+
29
+ levels: { strict: error, normal: warning, relaxed: info }
30
+
31
+ use_for: [business, technical, blog, legal, docs, academic, literature, speech]
32
+
33
+ group: structure
34
+ summary:
35
+ ja: 「```」で始めたまま閉じていないコードブロック(後ろがすべてコードになる)
36
+ en: A code block opened with "```" and never closed (everything after it shows as code)
37
+ example:
38
+ ja:
39
+ before: |
40
+ 手順は次のとおりです。
41
+
42
+ ```sh
43
+ npm install
44
+
45
+ ## 確認
46
+
47
+ 動くことを確かめます。
48
+ after: |
49
+ 手順は次のとおりです。
50
+
51
+ ```sh
52
+ npm install
53
+ ```
54
+
55
+ ## 確認
56
+
57
+ 動くことを確かめます。
58
+ en:
59
+ before: |
60
+ Install it first.
61
+
62
+ ```sh
63
+ npm install
64
+
65
+ ## Check
66
+
67
+ Make sure it runs.
68
+ after: |
69
+ Install it first.
70
+
71
+ ```sh
72
+ npm install
73
+ ```
74
+
75
+ ## Check
76
+
77
+ Make sure it runs.
78
+
79
+ not_flagged:
80
+ ja: 閉じたコードブロック、字下げで書いたコードブロック、引用の中のコードブロックは指しません。
81
+ en: A closed code block, an indented code block, and a code block in a quotation are not reported.
82
+ rewrite:
83
+ depth: light
84
+ ja:
85
+ direction: コードの終わりに閉じる行(「```」)を足してください。どこまでがコードかは、コマンドや出力の並びの終わりで決めます。コードの中身は変えません。
86
+ pairs:
87
+ - before: 「```sh」「npm install」「## 確認」
88
+ after: 「```sh」「npm install」「```」「## 確認」
89
+ - before: 「~~~」「SELECT 1;」のまま文書が終わる
90
+ after: 「~~~」「SELECT 1;」「~~~」
91
+ keep:
92
+ - コードの中身
93
+ - 始めの行の言語名
94
+ avoid:
95
+ - 後ろの本文までコードの中に入れる
96
+ en:
97
+ direction: Add a closing line ("```") where the code ends; the code ends where the commands or the output stop. Keep the code as it is.
98
+ pairs:
99
+ - before: '"```sh", "npm install", "## Check"'
100
+ after: '"```sh", "npm install", "```", "## Check"'
101
+ - before: 'the document ends after "~~~" and "SELECT 1;"'
102
+ after: '"~~~", "SELECT 1;", "~~~"'
103
+ keep:
104
+ - the code
105
+ - the language name on the opening line
106
+ avoid:
107
+ - putting the text after it inside the code block
@@ -0,0 +1,65 @@
1
+ id: uncomparable-graded
2
+ layer: L2
3
+ status: stable
4
+ how_to_find: phrase-match
5
+ word_list: uncomparable-graded
6
+ requires: [pos]
7
+ languages: [en]
8
+ severity: info
9
+
10
+ name:
11
+ ja: 比べられない形容詞に付けた程度
12
+ en: An uncomparable adjective given a degree
13
+
14
+ why:
15
+ ja: 英語の「unique」「unanimous」「impossible」は、そうであるかないかの二つしかない状態を言います。「very unique」「more unanimous」と程度を付けても何も足されず、読み手は書き手が語の意味を確かめていないと受け取ります。語の一覧は言語ごとの語彙表にあります。
16
+ en: '"Unique", "unanimous" and "impossible" name a state that holds or does not. "Very unique" or "more unanimous" adds nothing, and tells the reader the writer did not weigh the word. The phrases are listed in the lexicon.'
17
+
18
+ message:
19
+ ja: 「{matched}」は、程度の無い形容詞に程度を付けています
20
+ en: '"{matched}" grades an adjective that has no degrees'
21
+
22
+ how_to_fix:
23
+ ja: 程度の語を外すか、本当に言いたい程度の言える語に替えてください(very unique → unique、または unusual)。
24
+ en: Drop the grade, or use a word that has degrees ("very unique" → "unique", or "unusual").
25
+
26
+ levels: { strict: 1, normal: 1, relaxed: 2 }
27
+
28
+ use_for: [business, technical, blog, legal, docs, academic, literature, speech]
29
+ off_for:
30
+ literature: 'A narrator or a character may say "very unique"; the voice is the author''s choice.'
31
+
32
+ group: wording
33
+ summary:
34
+ ja: 英語で、「very unique」「more unanimous」のように、程度の無い形容詞に付けた程度
35
+ en: A degree given to an adjective that has none, such as "very unique" or "more unanimous"
36
+ example:
37
+ en:
38
+ before: |
39
+ The design is very unique.
40
+ after: |
41
+ The design is unusual.
42
+
43
+ not_flagged:
44
+ ja: 一覧にある組み合わせだけを見ます。「almost」「nearly」のように近さを言う語(almost unique、nearly impossible)は指しません。英語の文書だけで動き、文学のジャンルは対象にしません。
45
+ en: Only the pairs on chaff's list are checked. Words that say how close ("almost unique", "nearly impossible") are not reported. English documents only; literature is not checked.
46
+ level_meaning:
47
+ ja: 当てはまる言い回しが {limit} 箇所あれば指摘
48
+ en: reported once there are {limit}
49
+ sources: [proselint]
50
+ rewrite:
51
+ depth: light
52
+ en:
53
+ direction: Drop the grade before the adjective, or swap the adjective for one that has degrees when a degree is meant. Change nothing else in the sentence.
54
+ pairs:
55
+ - before: The design is very unique.
56
+ after: The design is unusual.
57
+ - before: The vote was more unanimous than last year.
58
+ after: The vote was unanimous this year.
59
+ - before: A fix before Friday is extremely impossible.
60
+ after: A fix before Friday is impossible.
61
+ keep:
62
+ - the claim the sentence makes
63
+ - the rest of the sentence
64
+ avoid:
65
+ - adding a new grade ("truly unique") in place of the old one
@@ -0,0 +1,73 @@
1
+ id: unrendered-emphasis
2
+ layer: L1
3
+ status: stable
4
+ how_to_find: unrendered-emphasis
5
+ requires: [markdown]
6
+ severity: warning
7
+
8
+ name:
9
+ ja: 太字にならずに見える「**」
10
+ en: Unrendered emphasis marks
11
+
12
+ why:
13
+ ja: 「**」や「__」は、Markdown が対にできたときだけ太字になり、対にできなければそのまま記号として表示されます。閉じ忘れ(「**重要」)のほか、日本語では「**「重要」**です」のように括弧や句読点の内側に記号を置き、外側に字が続くと、CommonMark の決まりで閉じられず、読み手には「**」が見えます。
14
+ en: '"**" and "__" turn into bold only when Markdown can pair them; otherwise they show as written. Besides one left open ("**important"), a mark with punctuation inside and a letter outside (Japanese "**「重要」**です") cannot close under CommonMark''s rules, and the reader sees the "**".'
15
+
16
+ message:
17
+ ja: 「{mark}」が太字にならず、そのまま表示されます
18
+ en: '"{mark}" is not turned into bold and shows as written'
19
+
20
+ how_to_fix:
21
+ ja: 閉じ忘れなら閉じる「**」を足してください。括弧や句読点の内側に置いた記号は、括弧の外に出すか(「**「重要」**」の外側に空白を置く)、括弧ごと太字にしないでください。
22
+ en: If it was left open, add the closing "**". If punctuation sits inside the mark, move the mark outside the punctuation, or put a space outside it.
23
+
24
+ placeholders:
25
+ mark:
26
+ ja: 記号
27
+ en: the mark
28
+
29
+ levels: { strict: error, normal: warning, relaxed: info }
30
+
31
+ use_for: [business, technical, blog, legal, docs, academic, literature, speech]
32
+
33
+ group: structure
34
+ summary:
35
+ ja: 対にならず、太字にならないまま記号として見える「**」「__」
36
+ en: '"**" or "__" that Markdown cannot pair and shows as written'
37
+ example:
38
+ ja:
39
+ before: 締め切りは**金曜日です。遅れないようにしてください。
40
+ after: 締め切りは**金曜日**です。遅れないようにしてください。
41
+ en:
42
+ before: The deadline is **Friday. Do not be late.
43
+ after: The deadline is **Friday**. Do not be late.
44
+
45
+ not_flagged:
46
+ ja: 語の中の記号(「2**10」「snake__case」)、前後が空白の記号、三つ以上並んだ記号(区切りや記入欄の「____」)、「__init__」のような名前、コードと引用の中の記号は指しません。
47
+ en: A mark inside a word ("2**10", "snake__case"), a mark with spaces on both sides, runs of three or more (dividers and blanks to fill, "____"), names such as "__init__", and marks in code or quotations are not reported.
48
+ rewrite:
49
+ depth: light
50
+ ja:
51
+ direction: 太字にしたい範囲を「**」で正しく囲んでください。閉じ忘れは閉じる記号を足し、括弧の内側に置いた記号は括弧の外に出します。言葉は変えません。
52
+ pairs:
53
+ - before: 締め切りは**金曜日です。
54
+ after: 締め切りは**金曜日**です。
55
+ - before: これは**「重要」**です。
56
+ after: これは「**重要**」です。
57
+ keep:
58
+ - 文の言葉
59
+ - 太字にしたい範囲
60
+ avoid:
61
+ - 太字をやめて記号だけ消すのか、閉じるのかを、文から読み取らずに決める
62
+ en:
63
+ direction: Wrap the words meant to be bold in a matching pair of "**". Add the missing closing mark, or move a mark outside the punctuation it sits inside. Keep the words.
64
+ pairs:
65
+ - before: The deadline is **Friday.
66
+ after: The deadline is **Friday**.
67
+ - before: Mark the task **done when it ships.
68
+ after: Mark the task **done** when it ships.
69
+ keep:
70
+ - the words
71
+ - the span meant to be bold
72
+ avoid:
73
+ - deciding whether to close or drop the mark without reading the sentence
@@ -0,0 +1,64 @@
1
+ id: which-that-consistency
2
+ layer: L3
3
+ status: stable
4
+ how_to_find: relative-pronoun-mix
5
+ requires: [pos]
6
+ languages: [en]
7
+ severity: info
8
+
9
+ name:
10
+ ja: 限定の関係節の which と that が揃っていない
11
+ en: Restrictive "which" and "that" mixed
12
+
13
+ why:
14
+ ja: 英語の限定の関係節(the file that contains the keys)は、that で書く人と which で書く人がいます。米国の手引きは that を勧め、英国の手引きはどちらも認めます。どちらが正しいかは決めません。一つの文書で混ざっていると、読み手は which の節が補足(読点のある非限定の節)なのかと迷います。読点を挟まない「名詞 + which / that + 動詞」だけを数え、少ないほうを指します。
15
+ en: 'A restrictive relative clause ("the file that contains the keys") opens with "that" for some writers and "which" for others. American guides prefer "that"; British ones accept both. chaff does not pick a side. Mixed in one document, a reader wonders whether a "which" clause is meant as an aside (the non-restrictive kind, set off by a comma). Only "noun + which/that + verb" with no comma between is counted, and the fewer form is pointed at.'
16
+
17
+ message:
18
+ ja: 限定の関係節を「{word}」で書いています(この文書はふつう「{usual}」)
19
+ en: 'This restrictive clause opens with "{word}"; the document mostly uses "{usual}"'
20
+
21
+ how_to_fix:
22
+ ja: 文書の多いほうに揃えてください。補足の節にするなら、前に読点を置いて which で書きます。
23
+ en: Match the rest of the document. If the clause is meant as an aside, set it off with a comma and use "which".
24
+
25
+ # 少ないほうが何箇所までなら「混在」と見るか。これを超えたら、文書が使い分けている。
26
+ levels: { strict: 4, normal: 2, relaxed: 1 }
27
+
28
+ use_for: [business, technical, blog, legal, docs, academic, literature, speech]
29
+ off_for:
30
+ literature: "Length, rhythm, repetition and register are the author's choices in literature, and dialogue mixes styles. Only what one work can hold itself to runs: consistent spacing and commas, and numbering without gaps."
31
+ speech: "A transcript keeps the speaker's words."
32
+
33
+ group: consistency
34
+ summary:
35
+ ja: 英語で、限定の関係節を which で書く所と that で書く所が混ざっている所
36
+ en: Restrictive clauses opened with "which" in some places and "that" in others
37
+
38
+ example:
39
+ en:
40
+ before: |
41
+ The job that builds the site runs nightly. The script that checks links runs hourly. The task that sends mail runs daily. The file which stores the keys is encrypted.
42
+ after: |
43
+ The job that builds the site runs nightly. The script that checks links runs hourly. The task that sends mail runs daily. The file that stores the keys is encrypted.
44
+
45
+ not_flagged:
46
+ ja: 読点のある非限定の節(the rule, which we added,)、前置詞の後ろの which(in which)、that の後ろに主語が来る節(the report that we wrote、the fact that it works)、多いほうが 3 箇所に満たない文書、少ないほうが水準の数を超える文書(使い分けている)は指しません。
47
+ en: 'A non-restrictive clause set off by a comma ("the rule, which we added,"), "which" after a preposition ("in which"), a "that" followed by its own subject ("the report that we wrote", "the fact that it works"), a document where the usual form appears fewer than 3 times, and one where the fewer form passes the level (used on purpose) are not reported.'
48
+ level_meaning:
49
+ ja: 少ないほうの書き方が {limit} 箇所以下のとき指摘
50
+ en: reported when the fewer form appears {limit} times or fewer
51
+
52
+ rewrite:
53
+ depth: light
54
+ en:
55
+ direction: Change the flagged "which" or "that" to the form the rest of the document uses. If the clause is an aside, add a comma before it and keep "which".
56
+ pairs:
57
+ - before: The file which stores the keys is encrypted.
58
+ after: The file that stores the keys is encrypted.
59
+ - before: The step which signs the build runs last.
60
+ after: The step that signs the build runs last.
61
+ keep:
62
+ - the clause itself and the rest of the sentence
63
+ avoid:
64
+ - changing a "which" clause set off by commas, which is an aside
@@ -32,7 +32,7 @@ choice, not a gap; turn it back on (`rules:` in `chaff.yaml`) only when the pers
32
32
  ```sh
33
33
  npx chaffjs --genre <genre> <file|dir|glob>... # human-readable, one block per finding (a folder or glob picks up .md / .markdown / .mdx; name a .txt file directly)
34
34
  npx chaffjs . --compact # two lines per finding: line:col severity message, then the rule id
35
- npx chaffjs <file> --experimental # also the experimental rules
35
+ npx chaffjs <file> --experimental # also the experimental rules (new ones, not yet measured)
36
36
  ```
37
37
 
38
38
  A run exits 1 when a finding is an `error`. It also exits 1 when it could not check anything: no file to
@@ -106,10 +106,10 @@ Use this section when asked to make a text sound less generated: 「AIっぽさ
106
106
 
107
107
  chaff marks the shapes common in generated text (group "Signs of generated text" in `npx chaffjs rules`: `ai-tell`,
108
108
  `contrast-framing`, `stock-transition`, `announcing-opener`, `colon-lead-in` (Japanese only), `assistant-residue`, and the signals
109
- `ai-generated-composite` reads). Most are experimental: run with `--experimental`. None of them says the text was
109
+ `ai-generated-composite` reads). They run by default outside legal, manual, literary and spoken genres. None of them says the text was
110
110
  generated. chaff never rewrites; the rewriting is yours.
111
111
 
112
- **Start with the plan.** Run `npx chaffjs fix-plan <file> --experimental` (with the genre's `--genre`; `--json` to
112
+ **Start with the plan.** Run `npx chaffjs fix-plan <file>` (with the genre's `--genre`; `--json` to
113
113
  read it as data). It prints, in the document's language:
114
114
 
115
115
  - the constraints: keep facts, numbers, conditions and names; add no fact; ask the writer instead of inventing a
@@ -140,7 +140,7 @@ repeats the body. The writer usually wants the structure changed, not only the s
140
140
 
141
141
  **Light** (only the flagged spots):
142
142
 
143
- 1. `npx chaffjs fix-plan <file> --experimental` (or with the genre's `--genre`).
143
+ 1. `npx chaffjs fix-plan <file>` (or with the genre's `--genre`).
144
144
  2. Rewrite only the flagged spots, each by its rule's direction in the plan. Keep the meaning, numbers, conditions and
145
145
  technical constraints.
146
146
  3. Run chaff again. At most two rewrite passes.
@@ -148,7 +148,7 @@ repeats the body. The writer usually wants the structure changed, not only the s
148
148
 
149
149
  **Bold** (section by section, outline kept):
150
150
 
151
- 1. Run chaff with `--experimental` and note the document-level signals: the `ai-generated-composite` inputs,
151
+ 1. Run chaff and note the document-level signals: the `ai-generated-composite` inputs,
152
152
  `bold-density`, `contrast-framing`, `stock-transition`, `sentence-rhythm`.
153
153
  2. Rewrite each section toward a human voice: less bold; one-line paragraphs and punchlines folded back into
154
154
  paragraphs; no "X ではありません。Y です" / "It's not X. It's Y" frames; lists turned back into sentences where the
@@ -204,7 +204,7 @@ repeats the body. The writer usually wants the structure changed, not only the s
204
204
  `chaff compare` catches an added number or name, but not added wording such as 「朝会で冗談が出るようになり」, so
205
205
  this one is yours to keep.
206
206
  5. **Check.**
207
- - `npx chaffjs <old> --experimental` and `npx chaffjs <new> --experimental`: the AI signals before and after.
207
+ - `npx chaffjs <old>` and `npx chaffjs <new>`: the AI signals before and after.
208
208
  - `npx chaffjs outline <old> <new>`: headings, average section length, text in lists, bold, and the structure score
209
209
  and each structure measure, before and after. A restructure shows up here, not only in rule counts.
210
210
  - `npx chaffjs compare <old> <new> --distinct --allow-dropped heading --allow-added heading`: the headings are the
@@ -249,7 +249,7 @@ output before and after.
249
249
  ## Structured documents
250
250
 
251
251
  - `npx chaffjs tree <file>` shows a contract or specification as a tree of addresses (`3.2` for 第3条第2項 or
252
- Section 3.2). `--experimental` adds the structure rules: references to missing provisions, numbering gaps,
252
+ Section 3.2). A check reads the same tree to find references to missing provisions, numbering gaps and
253
253
  terms defined twice.
254
254
  - `npx chaffjs cite <source> <quotes.json>` checks that quotations (`[{ "address", "quote" }]`) are really in
255
255
  the source; exit 1 if any is not. Use it to back every quotation you put in an answer or a summary.
package/src/cli-text.ts CHANGED
@@ -31,6 +31,8 @@ const USAGE_JA = `chaff — 文章の読みにくいところを見つけます
31
31
  chaff test <file|dir>... 意味を読む検査も動かす(API key が要ります)
32
32
  判定役は chaff.yaml の ai_backend で選びます
33
33
  chaff init chaff.yaml を作る(端末ならジャンルを尋ねる。--genre <ジャンル> でも選べる)
34
+ chaff init --plugin <名前> YAML だけのルールの束(chaff-plugin-<名前>/)を作る
35
+ chaff plugin-test [フォルダ] プラグインの各ルールを、そのルールの例にかけて確かめる
34
36
  chaff --version chaffjs と言語パッケージの版
35
37
  chaff eval <dir> 手元の文書で閾値を測り直す
36
38
  chaff explain <rule> そのルールの意図と根拠を読む
@@ -74,6 +76,8 @@ const USAGE_EN = `chaff — finds what makes writing hard to read. It never rewr
74
76
  chaff test <file|dir>... also run the checks that read meaning (needs an API key)
75
77
  the judge is chosen by ai_backend in chaff.yaml
76
78
  chaff init create chaff.yaml (asks for the genre at a terminal; --genre <genre> chooses it)
79
+ chaff init --plugin <name> create a YAML rule pack, chaff-plugin-<name>/
80
+ chaff plugin-test [folder] run each rule of a plugin on the rule's own example
77
81
  chaff --version the version of chaffjs and its language packages
78
82
  chaff eval <dir> re-measure the limits on your own documents
79
83
  chaff explain <rule> read what a rule is for and why
package/src/cli.ts CHANGED
@@ -13,8 +13,8 @@ import { runEval } from "./commands/eval.ts";
13
13
  import { runTest } from "./commands/test.ts";
14
14
  import { GENRES } from "./genre.ts";
15
15
  import { resolveGenre } from "./resolve-genre.ts";
16
- import { runInit } from "./init.ts";
17
- import { initGenre } from "./commands/init-ask.ts";
16
+ import { runInitCommand } from "./commands/init-command.ts";
17
+ import { runPluginTest } from "./commands/plugin-test.ts";
18
18
  import { targetsOf, withExperimental, withIncludes } from "./cli-args.ts";
19
19
  import { rulesOf } from "./custom/load.ts";
20
20
  import { renderCompact } from "./render/compact.ts";
@@ -282,19 +282,15 @@ const measureContext = (argv: readonly string[], config: Config): { config: Conf
282
282
 
283
283
  /** 分岐を数珠つなぎにせず表にする。足すときに main を太らせない。 */
284
284
  const HANDLERS: Readonly<Record<string, Handler>> = {
285
- init: async (argv, config) => {
286
- const ui = hostLanguage(config.language, process.env);
287
- const chosen = await initGenre(flag(argv, "--genre"), ui, process.cwd());
288
- if ("error" in chosen) console.error(chosen.error);
289
- else runInit(process.cwd(), chosen.genre, ui).forEach((line) => console.log(line));
290
- return "error" in chosen ? 1 : 0;
291
- },
285
+ init: (argv, config) => runInitCommand((name) => flag(argv, name), argv.includes("--plugin"), hostLanguage(config.language, process.env), process.cwd()),
292
286
  genres: (_argv, config) => showGenres(config),
293
287
  rules: showRules,
294
288
  explain: (argv, config) => explain(config, argv[1], flag(argv, "--genre")),
295
289
  eval: (argv, config) => runEval(positional(argv), argv, { ...measureContext(argv, config), flag }),
296
290
  ...Object.fromEntries(Object.entries(DOCUMENT_COMMANDS).map(([name, run]): [string, Handler] => [name, (argv, config) => run(argv, treeContext(config))])),
297
291
  test: (argv, config) => runTest(positional(argv), argv, { ...measureContext(argv, config), inspect }),
292
+ "plugin-test": (argv, config) =>
293
+ runPluginTest(positional(argv)[0], { ui: hostLanguage(config.language, process.env), check: async (...args) => (await inspect(...args)).checked }),
298
294
  "fix-plan": (argv, config) =>
299
295
  runFixPlan(fixPlanTargets(argv), argv, { ...treeContext(config), check: async (path) => (await inspectAll(config, argv)(path)).checked }),
300
296
  baseline: (argv, config) => runBaseline(positional(argv), argv, config),
@@ -0,0 +1,13 @@
1
+ import { runInit } from "../init.ts";
2
+ import type { UiLanguage } from "../ui.ts";
3
+ import { initGenre } from "./init-ask.ts";
4
+ import { runInitPlugin } from "./plugin-init.ts";
5
+
6
+ /** chaff init: chaff.yaml for a project, or with --plugin, a rule pack to start from. flag reads an option's value. */
7
+ export const runInitCommand = async (flag: (name: string) => string | undefined, plugin: boolean, ui: UiLanguage, dir: string): Promise<number> => {
8
+ if (plugin) return runInitPlugin(dir, flag("--plugin"), ui);
9
+ const chosen = await initGenre(flag("--genre"), ui, dir);
10
+ if ("error" in chosen) console.error(chosen.error);
11
+ else runInit(dir, chosen.genre, ui).forEach((line) => console.log(line));
12
+ return "error" in chosen ? 1 : 0;
13
+ };