chaffjs 0.34.0 → 0.36.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 (976) hide show
  1. package/README.ja.md +12 -0
  2. package/README.md +15 -0
  3. package/dist/announced-count.d.ts +2 -0
  4. package/dist/announced-count.d.ts.map +1 -1
  5. package/dist/announced-count.js +29 -7
  6. package/dist/announced-count.js.map +1 -1
  7. package/dist/capitals-passage.d.ts +3 -0
  8. package/dist/capitals-passage.d.ts.map +1 -0
  9. package/dist/capitals-passage.js +26 -0
  10. package/dist/capitals-passage.js.map +1 -0
  11. package/dist/chronology-rows.d.ts +9 -0
  12. package/dist/chronology-rows.d.ts.map +1 -0
  13. package/dist/chronology-rows.js +79 -0
  14. package/dist/chronology-rows.js.map +1 -0
  15. package/dist/coined-hyphen-name.d.ts +13 -0
  16. package/dist/coined-hyphen-name.d.ts.map +1 -0
  17. package/dist/coined-hyphen-name.js +21 -0
  18. package/dist/coined-hyphen-name.js.map +1 -0
  19. package/dist/company-name-run.d.ts +8 -0
  20. package/dist/company-name-run.d.ts.map +1 -0
  21. package/dist/company-name-run.js +30 -0
  22. package/dist/company-name-run.js.map +1 -0
  23. package/dist/company-names.d.ts +6 -1
  24. package/dist/company-names.d.ts.map +1 -1
  25. package/dist/company-names.js +22 -3
  26. package/dist/company-names.js.map +1 -1
  27. package/dist/compound-head.d.ts +7 -0
  28. package/dist/compound-head.d.ts.map +1 -0
  29. package/dist/compound-head.js +19 -0
  30. package/dist/compound-head.js.map +1 -0
  31. package/dist/date-format.d.ts +8 -3
  32. package/dist/date-format.d.ts.map +1 -1
  33. package/dist/date-format.js +36 -3
  34. package/dist/date-format.js.map +1 -1
  35. package/dist/derived/count-per-period.d.ts +23 -0
  36. package/dist/derived/count-per-period.d.ts.map +1 -0
  37. package/dist/derived/count-per-period.js +14 -0
  38. package/dist/derived/count-per-period.js.map +1 -0
  39. package/dist/detectors/acronym-context.d.ts +5 -1
  40. package/dist/detectors/acronym-context.d.ts.map +1 -1
  41. package/dist/detectors/acronym-context.js +32 -4
  42. package/dist/detectors/acronym-context.js.map +1 -1
  43. package/dist/detectors/acronym-definition.d.ts +13 -0
  44. package/dist/detectors/acronym-definition.d.ts.map +1 -0
  45. package/dist/detectors/acronym-definition.js +90 -0
  46. package/dist/detectors/acronym-definition.js.map +1 -0
  47. package/dist/detectors/acronym-expansion.d.ts +5 -1
  48. package/dist/detectors/acronym-expansion.d.ts.map +1 -1
  49. package/dist/detectors/acronym-expansion.js +35 -3
  50. package/dist/detectors/acronym-expansion.js.map +1 -1
  51. package/dist/detectors/acronym-known.d.ts +19 -0
  52. package/dist/detectors/acronym-known.d.ts.map +1 -0
  53. package/dist/detectors/acronym-known.js +32 -0
  54. package/dist/detectors/acronym-known.js.map +1 -0
  55. package/dist/detectors/acronym-link.d.ts +14 -0
  56. package/dist/detectors/acronym-link.d.ts.map +1 -0
  57. package/dist/detectors/acronym-link.js +32 -0
  58. package/dist/detectors/acronym-link.js.map +1 -0
  59. package/dist/detectors/acronym-lone.d.ts +13 -0
  60. package/dist/detectors/acronym-lone.d.ts.map +1 -0
  61. package/dist/detectors/acronym-lone.js +22 -0
  62. package/dist/detectors/acronym-lone.js.map +1 -0
  63. package/dist/detectors/acronym-name.d.ts +62 -0
  64. package/dist/detectors/acronym-name.d.ts.map +1 -0
  65. package/dist/detectors/acronym-name.js +94 -0
  66. package/dist/detectors/acronym-name.js.map +1 -0
  67. package/dist/detectors/addressee-edge.d.ts +13 -0
  68. package/dist/detectors/addressee-edge.d.ts.map +1 -0
  69. package/dist/detectors/addressee-edge.js +13 -0
  70. package/dist/detectors/addressee-edge.js.map +1 -0
  71. package/dist/detectors/announced-count.d.ts.map +1 -1
  72. package/dist/detectors/announced-count.js +1 -0
  73. package/dist/detectors/announced-count.js.map +1 -1
  74. package/dist/detectors/bare-comparative.d.ts +4 -0
  75. package/dist/detectors/bare-comparative.d.ts.map +1 -1
  76. package/dist/detectors/bare-comparative.js +28 -3
  77. package/dist/detectors/bare-comparative.js.map +1 -1
  78. package/dist/detectors/blank-structure.d.ts +7 -1
  79. package/dist/detectors/blank-structure.d.ts.map +1 -1
  80. package/dist/detectors/blank-structure.js +13 -8
  81. package/dist/detectors/blank-structure.js.map +1 -1
  82. package/dist/detectors/bracket-specified.d.ts +6 -0
  83. package/dist/detectors/bracket-specified.d.ts.map +1 -0
  84. package/dist/detectors/bracket-specified.js +23 -0
  85. package/dist/detectors/bracket-specified.js.map +1 -0
  86. package/dist/detectors/broken-link.d.ts +6 -0
  87. package/dist/detectors/broken-link.d.ts.map +1 -1
  88. package/dist/detectors/broken-link.js +23 -2
  89. package/dist/detectors/broken-link.js.map +1 -1
  90. package/dist/detectors/capitalised-term.d.ts +14 -2
  91. package/dist/detectors/capitalised-term.d.ts.map +1 -1
  92. package/dist/detectors/capitalised-term.js +115 -4
  93. package/dist/detectors/capitalised-term.js.map +1 -1
  94. package/dist/detectors/caps-caption.d.ts +12 -0
  95. package/dist/detectors/caps-caption.d.ts.map +1 -0
  96. package/dist/detectors/caps-caption.js +89 -0
  97. package/dist/detectors/caps-caption.js.map +1 -0
  98. package/dist/detectors/caps-phrase.d.ts +6 -0
  99. package/dist/detectors/caps-phrase.d.ts.map +1 -0
  100. package/dist/detectors/caps-phrase.js +16 -0
  101. package/dist/detectors/caps-phrase.js.map +1 -0
  102. package/dist/detectors/char-shape.d.ts +1 -0
  103. package/dist/detectors/char-shape.d.ts.map +1 -1
  104. package/dist/detectors/char-shape.js +72 -30
  105. package/dist/detectors/char-shape.js.map +1 -1
  106. package/dist/detectors/cited-title.d.ts +3 -2
  107. package/dist/detectors/cited-title.d.ts.map +1 -1
  108. package/dist/detectors/cited-title.js +14 -3
  109. package/dist/detectors/cited-title.js.map +1 -1
  110. package/dist/detectors/clause-shape.d.ts +1 -1
  111. package/dist/detectors/clause-shape.d.ts.map +1 -1
  112. package/dist/detectors/clause-shape.js +9 -4
  113. package/dist/detectors/clause-shape.js.map +1 -1
  114. package/dist/detectors/concrete-evidence.d.ts +13 -1
  115. package/dist/detectors/concrete-evidence.d.ts.map +1 -1
  116. package/dist/detectors/concrete-evidence.js +59 -0
  117. package/dist/detectors/concrete-evidence.js.map +1 -1
  118. package/dist/detectors/contraction-minority.d.ts +11 -0
  119. package/dist/detectors/contraction-minority.d.ts.map +1 -0
  120. package/dist/detectors/contraction-minority.js +10 -0
  121. package/dist/detectors/contraction-minority.js.map +1 -0
  122. package/dist/detectors/counter-edge.d.ts +7 -1
  123. package/dist/detectors/counter-edge.d.ts.map +1 -1
  124. package/dist/detectors/counter-edge.js +40 -2
  125. package/dist/detectors/counter-edge.js.map +1 -1
  126. package/dist/detectors/date-any-year.d.ts +12 -5
  127. package/dist/detectors/date-any-year.d.ts.map +1 -1
  128. package/dist/detectors/date-any-year.js +69 -12
  129. package/dist/detectors/date-any-year.js.map +1 -1
  130. package/dist/detectors/date-format.d.ts.map +1 -1
  131. package/dist/detectors/date-format.js +2 -1
  132. package/dist/detectors/date-format.js.map +1 -1
  133. package/dist/detectors/date-heading-year.d.ts +18 -0
  134. package/dist/detectors/date-heading-year.d.ts.map +1 -0
  135. package/dist/detectors/date-heading-year.js +38 -0
  136. package/dist/detectors/date-heading-year.js.map +1 -0
  137. package/dist/detectors/date-year.d.ts +19 -3
  138. package/dist/detectors/date-year.d.ts.map +1 -1
  139. package/dist/detectors/date-year.js +69 -8
  140. package/dist/detectors/date-year.js.map +1 -1
  141. package/dist/detectors/deadline-unit.d.ts +20 -0
  142. package/dist/detectors/deadline-unit.d.ts.map +1 -0
  143. package/dist/detectors/deadline-unit.js +19 -0
  144. package/dist/detectors/deadline-unit.js.map +1 -0
  145. package/dist/detectors/defined-term-form.d.ts.map +1 -1
  146. package/dist/detectors/defined-term-form.js +59 -12
  147. package/dist/detectors/defined-term-form.js.map +1 -1
  148. package/dist/detectors/definition-use.d.ts.map +1 -1
  149. package/dist/detectors/definition-use.js +6 -3
  150. package/dist/detectors/definition-use.js.map +1 -1
  151. package/dist/detectors/derived-numbers.d.ts.map +1 -1
  152. package/dist/detectors/derived-numbers.js +17 -4
  153. package/dist/detectors/derived-numbers.js.map +1 -1
  154. package/dist/detectors/doubled-across-aside.d.ts +9 -0
  155. package/dist/detectors/doubled-across-aside.d.ts.map +1 -0
  156. package/dist/detectors/doubled-across-aside.js +27 -0
  157. package/dist/detectors/doubled-across-aside.js.map +1 -0
  158. package/dist/detectors/doubled-punctuation.d.ts +3 -3
  159. package/dist/detectors/doubled-punctuation.d.ts.map +1 -1
  160. package/dist/detectors/doubled-punctuation.js +23 -4
  161. package/dist/detectors/doubled-punctuation.js.map +1 -1
  162. package/dist/detectors/doubled-word.d.ts.map +1 -1
  163. package/dist/detectors/doubled-word.js +2 -1
  164. package/dist/detectors/doubled-word.js.map +1 -1
  165. package/dist/detectors/due-date.d.ts.map +1 -1
  166. package/dist/detectors/due-date.js +6 -0
  167. package/dist/detectors/due-date.js.map +1 -1
  168. package/dist/detectors/ellipsis.d.ts.map +1 -1
  169. package/dist/detectors/ellipsis.js +13 -1
  170. package/dist/detectors/ellipsis.js.map +1 -1
  171. package/dist/detectors/email-letter.d.ts +31 -1
  172. package/dist/detectors/email-letter.d.ts.map +1 -1
  173. package/dist/detectors/email-letter.js +76 -14
  174. package/dist/detectors/email-letter.js.map +1 -1
  175. package/dist/detectors/en-shape.d.ts.map +1 -1
  176. package/dist/detectors/en-shape.js +5 -1
  177. package/dist/detectors/en-shape.js.map +1 -1
  178. package/dist/detectors/fact-consistency.d.ts.map +1 -1
  179. package/dist/detectors/fact-consistency.js +3 -2
  180. package/dist/detectors/fact-consistency.js.map +1 -1
  181. package/dist/detectors/field-label.d.ts +7 -0
  182. package/dist/detectors/field-label.d.ts.map +1 -0
  183. package/dist/detectors/field-label.js +23 -0
  184. package/dist/detectors/field-label.js.map +1 -0
  185. package/dist/detectors/footnote-mismatch.d.ts +6 -1
  186. package/dist/detectors/footnote-mismatch.d.ts.map +1 -1
  187. package/dist/detectors/footnote-mismatch.js +28 -7
  188. package/dist/detectors/footnote-mismatch.js.map +1 -1
  189. package/dist/detectors/graded-step.d.ts +20 -0
  190. package/dist/detectors/graded-step.d.ts.map +1 -0
  191. package/dist/detectors/graded-step.js +33 -0
  192. package/dist/detectors/graded-step.js.map +1 -0
  193. package/dist/detectors/gram-openers.d.ts +8 -0
  194. package/dist/detectors/gram-openers.d.ts.map +1 -0
  195. package/dist/detectors/gram-openers.js +16 -0
  196. package/dist/detectors/gram-openers.js.map +1 -0
  197. package/dist/detectors/gram-passages.d.ts +11 -0
  198. package/dist/detectors/gram-passages.d.ts.map +1 -0
  199. package/dist/detectors/gram-passages.js +26 -0
  200. package/dist/detectors/gram-passages.js.map +1 -0
  201. package/dist/detectors/gram-place.d.ts +3 -1
  202. package/dist/detectors/gram-place.d.ts.map +1 -1
  203. package/dist/detectors/gram-place.js +8 -0
  204. package/dist/detectors/gram-place.js.map +1 -1
  205. package/dist/detectors/gram-predicate.d.ts.map +1 -1
  206. package/dist/detectors/gram-predicate.js +37 -3
  207. package/dist/detectors/gram-predicate.js.map +1 -1
  208. package/dist/detectors/heading-echo.d.ts.map +1 -1
  209. package/dist/detectors/heading-echo.js +28 -2
  210. package/dist/detectors/heading-echo.js.map +1 -1
  211. package/dist/detectors/heading-end-mark.d.ts +8 -3
  212. package/dist/detectors/heading-end-mark.d.ts.map +1 -1
  213. package/dist/detectors/heading-end-mark.js +18 -8
  214. package/dist/detectors/heading-end-mark.js.map +1 -1
  215. package/dist/detectors/heading-names.d.ts +7 -0
  216. package/dist/detectors/heading-names.d.ts.map +1 -0
  217. package/dist/detectors/heading-names.js +24 -0
  218. package/dist/detectors/heading-names.js.map +1 -0
  219. package/dist/detectors/heading-numbering.d.ts.map +1 -1
  220. package/dist/detectors/heading-numbering.js +7 -2
  221. package/dist/detectors/heading-numbering.js.map +1 -1
  222. package/dist/detectors/ime-residue.d.ts +1 -1
  223. package/dist/detectors/ime-residue.d.ts.map +1 -1
  224. package/dist/detectors/ime-residue.js +4 -3
  225. package/dist/detectors/ime-residue.js.map +1 -1
  226. package/dist/detectors/inch-mark.d.ts +10 -0
  227. package/dist/detectors/inch-mark.d.ts.map +1 -0
  228. package/dist/detectors/inch-mark.js +48 -0
  229. package/dist/detectors/inch-mark.js.map +1 -0
  230. package/dist/detectors/kanji-compound-slip.d.ts +3 -0
  231. package/dist/detectors/kanji-compound-slip.d.ts.map +1 -0
  232. package/dist/detectors/kanji-compound-slip.js +50 -0
  233. package/dist/detectors/kanji-compound-slip.js.map +1 -0
  234. package/dist/detectors/kutoten-consistency.d.ts +10 -2
  235. package/dist/detectors/kutoten-consistency.d.ts.map +1 -1
  236. package/dist/detectors/kutoten-consistency.js +76 -12
  237. package/dist/detectors/kutoten-consistency.js.map +1 -1
  238. package/dist/detectors/lexicon.d.ts +0 -1
  239. package/dist/detectors/lexicon.d.ts.map +1 -1
  240. package/dist/detectors/lexicon.js +37 -25
  241. package/dist/detectors/lexicon.js.map +1 -1
  242. package/dist/detectors/link-shape.d.ts.map +1 -1
  243. package/dist/detectors/link-shape.js +9 -3
  244. package/dist/detectors/link-shape.js.map +1 -1
  245. package/dist/detectors/list-item-ending.d.ts +18 -0
  246. package/dist/detectors/list-item-ending.d.ts.map +1 -0
  247. package/dist/detectors/list-item-ending.js +35 -0
  248. package/dist/detectors/list-item-ending.js.map +1 -0
  249. package/dist/detectors/list-parallel.d.ts +18 -5
  250. package/dist/detectors/list-parallel.d.ts.map +1 -1
  251. package/dist/detectors/list-parallel.js +116 -36
  252. package/dist/detectors/list-parallel.js.map +1 -1
  253. package/dist/detectors/list-sentence.d.ts +4 -0
  254. package/dist/detectors/list-sentence.d.ts.map +1 -1
  255. package/dist/detectors/list-sentence.js +1 -1
  256. package/dist/detectors/list-sentence.js.map +1 -1
  257. package/dist/detectors/mark-shape.d.ts +15 -5
  258. package/dist/detectors/mark-shape.d.ts.map +1 -1
  259. package/dist/detectors/mark-shape.js +64 -10
  260. package/dist/detectors/mark-shape.js.map +1 -1
  261. package/dist/detectors/mentioned-phrase.d.ts +9 -0
  262. package/dist/detectors/mentioned-phrase.d.ts.map +1 -0
  263. package/dist/detectors/mentioned-phrase.js +25 -0
  264. package/dist/detectors/mentioned-phrase.js.map +1 -0
  265. package/dist/detectors/middle-dot.d.ts +2 -2
  266. package/dist/detectors/middle-dot.d.ts.map +1 -1
  267. package/dist/detectors/middle-dot.js +4 -2
  268. package/dist/detectors/middle-dot.js.map +1 -1
  269. package/dist/detectors/modal-conflict.d.ts.map +1 -1
  270. package/dist/detectors/modal-conflict.js +5 -2
  271. package/dist/detectors/modal-conflict.js.map +1 -1
  272. package/dist/detectors/name-variant-apart.d.ts +27 -0
  273. package/dist/detectors/name-variant-apart.d.ts.map +1 -0
  274. package/dist/detectors/name-variant-apart.js +51 -0
  275. package/dist/detectors/name-variant-apart.js.map +1 -0
  276. package/dist/detectors/name-variant.d.ts.map +1 -1
  277. package/dist/detectors/name-variant.js +18 -11
  278. package/dist/detectors/name-variant.js.map +1 -1
  279. package/dist/detectors/notice-paragraph.d.ts +9 -0
  280. package/dist/detectors/notice-paragraph.d.ts.map +1 -0
  281. package/dist/detectors/notice-paragraph.js +21 -0
  282. package/dist/detectors/notice-paragraph.js.map +1 -0
  283. package/dist/detectors/number-style.d.ts.map +1 -1
  284. package/dist/detectors/number-style.js +15 -2
  285. package/dist/detectors/number-style.js.map +1 -1
  286. package/dist/detectors/number-unit.d.ts.map +1 -1
  287. package/dist/detectors/number-unit.js +24 -1
  288. package/dist/detectors/number-unit.js.map +1 -1
  289. package/dist/detectors/numeral-opener.d.ts +6 -0
  290. package/dist/detectors/numeral-opener.d.ts.map +1 -1
  291. package/dist/detectors/numeral-opener.js +24 -1
  292. package/dist/detectors/numeral-opener.js.map +1 -1
  293. package/dist/detectors/numeral-word.d.ts +15 -0
  294. package/dist/detectors/numeral-word.d.ts.map +1 -0
  295. package/dist/detectors/numeral-word.js +26 -0
  296. package/dist/detectors/numeral-word.js.map +1 -0
  297. package/dist/detectors/obligation-without-deadline.d.ts +5 -1
  298. package/dist/detectors/obligation-without-deadline.d.ts.map +1 -1
  299. package/dist/detectors/obligation-without-deadline.js +44 -23
  300. package/dist/detectors/obligation-without-deadline.js.map +1 -1
  301. package/dist/detectors/open-end-class.d.ts +16 -0
  302. package/dist/detectors/open-end-class.d.ts.map +1 -0
  303. package/dist/detectors/open-end-class.js +65 -0
  304. package/dist/detectors/open-end-class.js.map +1 -0
  305. package/dist/detectors/open-end-condition.d.ts +7 -0
  306. package/dist/detectors/open-end-condition.d.ts.map +1 -0
  307. package/dist/detectors/open-end-condition.js +35 -0
  308. package/dist/detectors/open-end-condition.js.map +1 -0
  309. package/dist/detectors/open-end-names.d.ts +9 -3
  310. package/dist/detectors/open-end-names.d.ts.map +1 -1
  311. package/dist/detectors/open-end-names.js +5 -2
  312. package/dist/detectors/open-end-names.js.map +1 -1
  313. package/dist/detectors/open-end-question.d.ts +15 -0
  314. package/dist/detectors/open-end-question.d.ts.map +1 -0
  315. package/dist/detectors/open-end-question.js +37 -0
  316. package/dist/detectors/open-end-question.js.map +1 -0
  317. package/dist/detectors/open-end-scope.d.ts +16 -0
  318. package/dist/detectors/open-end-scope.d.ts.map +1 -0
  319. package/dist/detectors/open-end-scope.js +47 -0
  320. package/dist/detectors/open-end-scope.js.map +1 -0
  321. package/dist/detectors/opening-date.d.ts +10 -0
  322. package/dist/detectors/opening-date.d.ts.map +1 -0
  323. package/dist/detectors/opening-date.js +33 -0
  324. package/dist/detectors/opening-date.js.map +1 -0
  325. package/dist/detectors/ordinary-phrase.d.ts +20 -0
  326. package/dist/detectors/ordinary-phrase.d.ts.map +1 -0
  327. package/dist/detectors/ordinary-phrase.js +54 -0
  328. package/dist/detectors/ordinary-phrase.js.map +1 -0
  329. package/dist/detectors/organisation-run.d.ts +18 -0
  330. package/dist/detectors/organisation-run.d.ts.map +1 -0
  331. package/dist/detectors/organisation-run.js +80 -0
  332. package/dist/detectors/organisation-run.js.map +1 -0
  333. package/dist/detectors/orthographic-variant.d.ts.map +1 -1
  334. package/dist/detectors/orthographic-variant.js +65 -21
  335. package/dist/detectors/orthographic-variant.js.map +1 -1
  336. package/dist/detectors/orthography.d.ts.map +1 -1
  337. package/dist/detectors/orthography.js +6 -1
  338. package/dist/detectors/orthography.js.map +1 -1
  339. package/dist/detectors/outline-label.d.ts +14 -0
  340. package/dist/detectors/outline-label.d.ts.map +1 -0
  341. package/dist/detectors/outline-label.js +32 -0
  342. package/dist/detectors/outline-label.js.map +1 -0
  343. package/dist/detectors/oxford-comma.d.ts.map +1 -1
  344. package/dist/detectors/oxford-comma.js +38 -1
  345. package/dist/detectors/oxford-comma.js.map +1 -1
  346. package/dist/detectors/page-marker.d.ts +6 -0
  347. package/dist/detectors/page-marker.d.ts.map +1 -0
  348. package/dist/detectors/page-marker.js +19 -0
  349. package/dist/detectors/page-marker.js.map +1 -0
  350. package/dist/detectors/parallel-definition.d.ts +16 -0
  351. package/dist/detectors/parallel-definition.d.ts.map +1 -0
  352. package/dist/detectors/parallel-definition.js +51 -0
  353. package/dist/detectors/parallel-definition.js.map +1 -0
  354. package/dist/detectors/person-consistency.d.ts +2 -1
  355. package/dist/detectors/person-consistency.d.ts.map +1 -1
  356. package/dist/detectors/person-consistency.js +5 -3
  357. package/dist/detectors/person-consistency.js.map +1 -1
  358. package/dist/detectors/phrase-match.d.ts +2 -0
  359. package/dist/detectors/phrase-match.d.ts.map +1 -1
  360. package/dist/detectors/phrase-match.js +11 -4
  361. package/dist/detectors/phrase-match.js.map +1 -1
  362. package/dist/detectors/placeholder-text.d.ts.map +1 -1
  363. package/dist/detectors/placeholder-text.js +18 -3
  364. package/dist/detectors/placeholder-text.js.map +1 -1
  365. package/dist/detectors/placeholder.d.ts +3 -1
  366. package/dist/detectors/placeholder.d.ts.map +1 -1
  367. package/dist/detectors/placeholder.js +8 -3
  368. package/dist/detectors/placeholder.js.map +1 -1
  369. package/dist/detectors/postcode-end.d.ts +3 -0
  370. package/dist/detectors/postcode-end.d.ts.map +1 -0
  371. package/dist/detectors/postcode-end.js +15 -0
  372. package/dist/detectors/postcode-end.js.map +1 -0
  373. package/dist/detectors/prose-total-words.d.ts +5 -0
  374. package/dist/detectors/prose-total-words.d.ts.map +1 -0
  375. package/dist/detectors/prose-total-words.js +14 -0
  376. package/dist/detectors/prose-total-words.js.map +1 -0
  377. package/dist/detectors/reference-text.d.ts.map +1 -1
  378. package/dist/detectors/reference-text.js +1 -0
  379. package/dist/detectors/reference-text.js.map +1 -1
  380. package/dist/detectors/registry/kanji-compound-slip.d.ts +3 -0
  381. package/dist/detectors/registry/kanji-compound-slip.d.ts.map +1 -0
  382. package/dist/detectors/registry/kanji-compound-slip.js +3 -0
  383. package/dist/detectors/registry/kanji-compound-slip.js.map +1 -0
  384. package/dist/detectors/registry/phrase-in-use.d.ts +3 -0
  385. package/dist/detectors/registry/phrase-in-use.d.ts.map +1 -0
  386. package/dist/detectors/registry/phrase-in-use.js +3 -0
  387. package/dist/detectors/registry/phrase-in-use.js.map +1 -0
  388. package/dist/detectors/registry/unfilled-placeholder.d.ts.map +1 -1
  389. package/dist/detectors/registry/unfilled-placeholder.js +2 -2
  390. package/dist/detectors/registry/unfilled-placeholder.js.map +1 -1
  391. package/dist/detectors/registry/vague-density.js +1 -1
  392. package/dist/detectors/registry/vague-density.js.map +1 -1
  393. package/dist/detectors/request-owner.d.ts +6 -2
  394. package/dist/detectors/request-owner.d.ts.map +1 -1
  395. package/dist/detectors/request-owner.js +57 -7
  396. package/dist/detectors/request-owner.js.map +1 -1
  397. package/dist/detectors/requirement-smell.d.ts.map +1 -1
  398. package/dist/detectors/requirement-smell.js +39 -7
  399. package/dist/detectors/requirement-smell.js.map +1 -1
  400. package/dist/detectors/scaled-figure-unit.d.ts +28 -0
  401. package/dist/detectors/scaled-figure-unit.d.ts.map +1 -0
  402. package/dist/detectors/scaled-figure-unit.js +78 -0
  403. package/dist/detectors/scaled-figure-unit.js.map +1 -0
  404. package/dist/detectors/sentence-counts.d.ts +2 -0
  405. package/dist/detectors/sentence-counts.d.ts.map +1 -1
  406. package/dist/detectors/sentence-counts.js +18 -7
  407. package/dist/detectors/sentence-counts.js.map +1 -1
  408. package/dist/detectors/sentence-ending.d.ts +2 -0
  409. package/dist/detectors/sentence-ending.d.ts.map +1 -1
  410. package/dist/detectors/sentence-ending.js +10 -3
  411. package/dist/detectors/sentence-ending.js.map +1 -1
  412. package/dist/detectors/sentence-length.d.ts.map +1 -1
  413. package/dist/detectors/sentence-length.js +24 -16
  414. package/dist/detectors/sentence-length.js.map +1 -1
  415. package/dist/detectors/sentence-load.d.ts +4 -1
  416. package/dist/detectors/sentence-load.d.ts.map +1 -1
  417. package/dist/detectors/sentence-load.js +9 -2
  418. package/dist/detectors/sentence-load.js.map +1 -1
  419. package/dist/detectors/sentence-rhythm.d.ts.map +1 -1
  420. package/dist/detectors/sentence-rhythm.js +6 -3
  421. package/dist/detectors/sentence-rhythm.js.map +1 -1
  422. package/dist/detectors/series-label.d.ts +2 -1
  423. package/dist/detectors/series-label.d.ts.map +1 -1
  424. package/dist/detectors/series-label.js +10 -4
  425. package/dist/detectors/series-label.js.map +1 -1
  426. package/dist/detectors/signals.d.ts +4 -0
  427. package/dist/detectors/signals.d.ts.map +1 -1
  428. package/dist/detectors/signals.js +91 -52
  429. package/dist/detectors/signals.js.map +1 -1
  430. package/dist/detectors/structure-tree.d.ts.map +1 -1
  431. package/dist/detectors/structure-tree.js +21 -19
  432. package/dist/detectors/structure-tree.js.map +1 -1
  433. package/dist/detectors/structure.d.ts.map +1 -1
  434. package/dist/detectors/structure.js +2 -1
  435. package/dist/detectors/structure.js.map +1 -1
  436. package/dist/detectors/subject-name-line.d.ts +8 -0
  437. package/dist/detectors/subject-name-line.d.ts.map +1 -0
  438. package/dist/detectors/subject-name-line.js +53 -0
  439. package/dist/detectors/subject-name-line.js.map +1 -0
  440. package/dist/detectors/table-header.d.ts.map +1 -1
  441. package/dist/detectors/table-header.js +13 -1
  442. package/dist/detectors/table-header.js.map +1 -1
  443. package/dist/detectors/technical-docs.d.ts.map +1 -1
  444. package/dist/detectors/technical-docs.js +4 -1
  445. package/dist/detectors/technical-docs.js.map +1 -1
  446. package/dist/detectors/template-sections.d.ts +14 -0
  447. package/dist/detectors/template-sections.d.ts.map +1 -0
  448. package/dist/detectors/template-sections.js +25 -0
  449. package/dist/detectors/template-sections.js.map +1 -0
  450. package/dist/detectors/term-mention-sentence.d.ts +4 -0
  451. package/dist/detectors/term-mention-sentence.d.ts.map +1 -0
  452. package/dist/detectors/term-mention-sentence.js +28 -0
  453. package/dist/detectors/term-mention-sentence.js.map +1 -0
  454. package/dist/detectors/titled-run.d.ts +23 -0
  455. package/dist/detectors/titled-run.d.ts.map +1 -0
  456. package/dist/detectors/titled-run.js +39 -0
  457. package/dist/detectors/titled-run.js.map +1 -0
  458. package/dist/detectors/token-shape.d.ts.map +1 -1
  459. package/dist/detectors/token-shape.js +13 -5
  460. package/dist/detectors/token-shape.js.map +1 -1
  461. package/dist/detectors/unbalanced-bracket.d.ts.map +1 -1
  462. package/dist/detectors/unbalanced-bracket.js +4 -0
  463. package/dist/detectors/unbalanced-bracket.js.map +1 -1
  464. package/dist/detectors/undefined-term.d.ts.map +1 -1
  465. package/dist/detectors/undefined-term.js +8 -0
  466. package/dist/detectors/undefined-term.js.map +1 -1
  467. package/dist/detectors/unfilled-placeholder.d.ts +4 -0
  468. package/dist/detectors/unfilled-placeholder.d.ts.map +1 -0
  469. package/dist/detectors/unfilled-placeholder.js +9 -0
  470. package/dist/detectors/unfilled-placeholder.js.map +1 -0
  471. package/dist/detectors/vague-density.d.ts +8 -0
  472. package/dist/detectors/vague-density.d.ts.map +1 -0
  473. package/dist/detectors/vague-density.js +65 -0
  474. package/dist/detectors/vague-density.js.map +1 -0
  475. package/dist/document-paragraphs.d.ts +4 -0
  476. package/dist/document-paragraphs.d.ts.map +1 -0
  477. package/dist/document-paragraphs.js +24 -0
  478. package/dist/document-paragraphs.js.map +1 -0
  479. package/dist/document.d.ts.map +1 -1
  480. package/dist/document.js +2 -19
  481. package/dist/document.js.map +1 -1
  482. package/dist/facts/fact-scope.d.ts +10 -1
  483. package/dist/facts/fact-scope.d.ts.map +1 -1
  484. package/dist/facts/fact-scope.js +34 -3
  485. package/dist/facts/fact-scope.js.map +1 -1
  486. package/dist/facts/table-facts.d.ts +12 -2
  487. package/dist/facts/table-facts.d.ts.map +1 -1
  488. package/dist/facts/table-facts.js +22 -4
  489. package/dist/facts/table-facts.js.map +1 -1
  490. package/dist/figure-references.d.ts +3 -0
  491. package/dist/figure-references.d.ts.map +1 -1
  492. package/dist/figure-references.js +6 -2
  493. package/dist/figure-references.js.map +1 -1
  494. package/dist/format-template.d.ts +3 -0
  495. package/dist/format-template.d.ts.map +1 -0
  496. package/dist/format-template.js +13 -0
  497. package/dist/format-template.js.map +1 -0
  498. package/dist/formula-brackets.d.ts +7 -0
  499. package/dist/formula-brackets.d.ts.map +1 -0
  500. package/dist/formula-brackets.js +29 -0
  501. package/dist/formula-brackets.js.map +1 -0
  502. package/dist/grade-api.d.ts +9 -2
  503. package/dist/grade-api.d.ts.map +1 -1
  504. package/dist/grade-api.js +31 -15
  505. package/dist/grade-api.js.map +1 -1
  506. package/dist/heading-numbering.d.ts +5 -2
  507. package/dist/heading-numbering.d.ts.map +1 -1
  508. package/dist/heading-numbering.js +27 -6
  509. package/dist/heading-numbering.js.map +1 -1
  510. package/dist/html/html-markdown.d.ts.map +1 -1
  511. package/dist/html/html-markdown.js +2 -1
  512. package/dist/html/html-markdown.js.map +1 -1
  513. package/dist/html/html-site-chrome.d.ts +5 -0
  514. package/dist/html/html-site-chrome.d.ts.map +1 -0
  515. package/dist/html/html-site-chrome.js +33 -0
  516. package/dist/html/html-site-chrome.js.map +1 -0
  517. package/dist/joined-view.d.ts.map +1 -1
  518. package/dist/joined-view.js +1 -0
  519. package/dist/joined-view.js.map +1 -1
  520. package/dist/kanji-compound-slip.d.ts +32 -0
  521. package/dist/kanji-compound-slip.d.ts.map +1 -0
  522. package/dist/kanji-compound-slip.js +63 -0
  523. package/dist/kanji-compound-slip.js.map +1 -0
  524. package/dist/latin-company-form.d.ts +6 -0
  525. package/dist/latin-company-form.d.ts.map +1 -0
  526. package/dist/latin-company-form.js +32 -0
  527. package/dist/latin-company-form.js.map +1 -0
  528. package/dist/latin-word-boundary.d.ts +15 -0
  529. package/dist/latin-word-boundary.d.ts.map +1 -0
  530. package/dist/latin-word-boundary.js +40 -0
  531. package/dist/latin-word-boundary.js.map +1 -0
  532. package/dist/lexicon-genres.d.ts +2 -0
  533. package/dist/lexicon-genres.d.ts.map +1 -1
  534. package/dist/lexicon-genres.js +1 -1
  535. package/dist/lexicon-genres.js.map +1 -1
  536. package/dist/link-shape.d.ts +5 -0
  537. package/dist/link-shape.d.ts.map +1 -1
  538. package/dist/link-shape.js +18 -0
  539. package/dist/link-shape.js.map +1 -1
  540. package/dist/link-title.d.ts +4 -0
  541. package/dist/link-title.d.ts.map +1 -0
  542. package/dist/link-title.js +33 -0
  543. package/dist/link-title.js.map +1 -0
  544. package/dist/list-item-paragraphs.d.ts +15 -0
  545. package/dist/list-item-paragraphs.d.ts.map +1 -0
  546. package/dist/list-item-paragraphs.js +19 -0
  547. package/dist/list-item-paragraphs.js.map +1 -0
  548. package/dist/literal-quote.d.ts +12 -0
  549. package/dist/literal-quote.d.ts.map +1 -0
  550. package/dist/literal-quote.js +43 -0
  551. package/dist/literal-quote.js.map +1 -0
  552. package/dist/nado-closed-list.d.ts.map +1 -1
  553. package/dist/nado-closed-list.js +39 -5
  554. package/dist/nado-closed-list.js.map +1 -1
  555. package/dist/name-end-letter.d.ts +5 -0
  556. package/dist/name-end-letter.d.ts.map +1 -1
  557. package/dist/name-end-letter.js +8 -0
  558. package/dist/name-end-letter.js.map +1 -1
  559. package/dist/name-given-before.d.ts +15 -0
  560. package/dist/name-given-before.d.ts.map +1 -0
  561. package/dist/name-given-before.js +30 -0
  562. package/dist/name-given-before.js.map +1 -0
  563. package/dist/name-separator.d.ts +2 -2
  564. package/dist/name-separator.d.ts.map +1 -1
  565. package/dist/name-separator.js +79 -5
  566. package/dist/name-separator.js.map +1 -1
  567. package/dist/name-variants.d.ts +3 -1
  568. package/dist/name-variants.d.ts.map +1 -1
  569. package/dist/name-variants.js +8 -7
  570. package/dist/name-variants.js.map +1 -1
  571. package/dist/name-word-order.d.ts +9 -5
  572. package/dist/name-word-order.d.ts.map +1 -1
  573. package/dist/name-word-order.js +47 -15
  574. package/dist/name-word-order.js.map +1 -1
  575. package/dist/nominal-stem.d.ts +26 -0
  576. package/dist/nominal-stem.d.ts.map +1 -0
  577. package/dist/nominal-stem.js +70 -0
  578. package/dist/nominal-stem.js.map +1 -0
  579. package/dist/person-forms.d.ts +8 -0
  580. package/dist/person-forms.d.ts.map +1 -1
  581. package/dist/person-forms.js +12 -0
  582. package/dist/person-forms.js.map +1 -1
  583. package/dist/plugin.d.ts +5 -0
  584. package/dist/plugin.d.ts.map +1 -1
  585. package/dist/preamble-paragraphs.d.ts +3 -2
  586. package/dist/preamble-paragraphs.d.ts.map +1 -1
  587. package/dist/preamble-paragraphs.js +8 -2
  588. package/dist/preamble-paragraphs.js.map +1 -1
  589. package/dist/sentence-load.d.ts +2 -1
  590. package/dist/sentence-load.d.ts.map +1 -1
  591. package/dist/sentence-load.js +6 -2
  592. package/dist/sentence-load.js.map +1 -1
  593. package/dist/spacing-code.d.ts +1 -0
  594. package/dist/spacing-code.d.ts.map +1 -1
  595. package/dist/spacing-code.js +4 -1
  596. package/dist/spacing-code.js.map +1 -1
  597. package/dist/split-noun.d.ts +10 -0
  598. package/dist/split-noun.d.ts.map +1 -0
  599. package/dist/split-noun.js +50 -0
  600. package/dist/split-noun.js.map +1 -0
  601. package/dist/structure/attached-parts.d.ts +11 -0
  602. package/dist/structure/attached-parts.d.ts.map +1 -0
  603. package/dist/structure/attached-parts.js +31 -0
  604. package/dist/structure/attached-parts.js.map +1 -0
  605. package/dist/structure/build.d.ts.map +1 -1
  606. package/dist/structure/build.js +7 -4
  607. package/dist/structure/build.js.map +1 -1
  608. package/dist/structure/cited-document-section.d.ts +7 -0
  609. package/dist/structure/cited-document-section.d.ts.map +1 -0
  610. package/dist/structure/cited-document-section.js +33 -0
  611. package/dist/structure/cited-document-section.js.map +1 -0
  612. package/dist/structure/contents-lines.d.ts +7 -0
  613. package/dist/structure/contents-lines.d.ts.map +1 -0
  614. package/dist/structure/contents-lines.js +51 -0
  615. package/dist/structure/contents-lines.js.map +1 -0
  616. package/dist/structure/defining-names.d.ts +37 -0
  617. package/dist/structure/defining-names.d.ts.map +1 -0
  618. package/dist/structure/defining-names.js +122 -0
  619. package/dist/structure/defining-names.js.map +1 -0
  620. package/dist/structure/definition-use.d.ts +3 -2
  621. package/dist/structure/definition-use.d.ts.map +1 -1
  622. package/dist/structure/definition-use.js +99 -31
  623. package/dist/structure/definition-use.js.map +1 -1
  624. package/dist/structure/html-text-blocks.d.ts +8 -0
  625. package/dist/structure/html-text-blocks.d.ts.map +1 -0
  626. package/dist/structure/html-text-blocks.js +47 -0
  627. package/dist/structure/html-text-blocks.js.map +1 -0
  628. package/dist/structure/issues.d.ts +5 -2
  629. package/dist/structure/issues.d.ts.map +1 -1
  630. package/dist/structure/issues.js +24 -6
  631. package/dist/structure/issues.js.map +1 -1
  632. package/dist/structure/labelled-date-order.d.ts +4 -1
  633. package/dist/structure/labelled-date-order.d.ts.map +1 -1
  634. package/dist/structure/labelled-date-order.js +2 -2
  635. package/dist/structure/labelled-date-order.js.map +1 -1
  636. package/dist/structure/labelled-order.d.ts +3 -0
  637. package/dist/structure/labelled-order.d.ts.map +1 -1
  638. package/dist/structure/labelled-order.js +8 -3
  639. package/dist/structure/labelled-order.js.map +1 -1
  640. package/dist/structure/list-lead-in.d.ts +19 -0
  641. package/dist/structure/list-lead-in.d.ts.map +1 -0
  642. package/dist/structure/list-lead-in.js +85 -0
  643. package/dist/structure/list-lead-in.js.map +1 -0
  644. package/dist/structure/list-numbering.d.ts +20 -4
  645. package/dist/structure/list-numbering.d.ts.map +1 -1
  646. package/dist/structure/list-numbering.js +65 -9
  647. package/dist/structure/list-numbering.js.map +1 -1
  648. package/dist/structure/listed-paragraph.d.ts +16 -0
  649. package/dist/structure/listed-paragraph.d.ts.map +1 -0
  650. package/dist/structure/listed-paragraph.js +37 -0
  651. package/dist/structure/listed-paragraph.js.map +1 -0
  652. package/dist/structure/modal-conflict.d.ts +7 -2
  653. package/dist/structure/modal-conflict.d.ts.map +1 -1
  654. package/dist/structure/modal-conflict.js +36 -7
  655. package/dist/structure/modal-conflict.js.map +1 -1
  656. package/dist/structure/negated-act.d.ts +17 -0
  657. package/dist/structure/negated-act.d.ts.map +1 -0
  658. package/dist/structure/negated-act.js +32 -0
  659. package/dist/structure/negated-act.js.map +1 -0
  660. package/dist/structure/numbering.d.ts +5 -2
  661. package/dist/structure/numbering.d.ts.map +1 -1
  662. package/dist/structure/numbering.js +49 -12
  663. package/dist/structure/numbering.js.map +1 -1
  664. package/dist/structure/prose-total.d.ts +4 -0
  665. package/dist/structure/prose-total.d.ts.map +1 -1
  666. package/dist/structure/prose-total.js +16 -6
  667. package/dist/structure/prose-total.js.map +1 -1
  668. package/dist/structure/reference-text.d.ts +9 -1
  669. package/dist/structure/reference-text.d.ts.map +1 -1
  670. package/dist/structure/reference-text.js +21 -3
  671. package/dist/structure/reference-text.js.map +1 -1
  672. package/dist/structure/repeated-number.d.ts +24 -0
  673. package/dist/structure/repeated-number.d.ts.map +1 -0
  674. package/dist/structure/repeated-number.js +89 -0
  675. package/dist/structure/repeated-number.js.map +1 -0
  676. package/dist/structure/rounded-amount.d.ts +8 -0
  677. package/dist/structure/rounded-amount.d.ts.map +1 -0
  678. package/dist/structure/rounded-amount.js +48 -0
  679. package/dist/structure/rounded-amount.js.map +1 -0
  680. package/dist/structure/section-names.d.ts +12 -0
  681. package/dist/structure/section-names.d.ts.map +1 -0
  682. package/dist/structure/section-names.js +26 -0
  683. package/dist/structure/section-names.js.map +1 -0
  684. package/dist/structure/side-step.d.ts +8 -0
  685. package/dist/structure/side-step.d.ts.map +1 -0
  686. package/dist/structure/side-step.js +21 -0
  687. package/dist/structure/side-step.js.map +1 -0
  688. package/dist/structure/spanned-label-blank.d.ts +8 -0
  689. package/dist/structure/spanned-label-blank.d.ts.map +1 -0
  690. package/dist/structure/spanned-label-blank.js +37 -0
  691. package/dist/structure/spanned-label-blank.js.map +1 -0
  692. package/dist/structure/universal.d.ts +3 -1
  693. package/dist/structure/universal.d.ts.map +1 -1
  694. package/dist/structure/universal.js +9 -2
  695. package/dist/structure/universal.js.map +1 -1
  696. package/dist/structure/unspaced-heading.d.ts +10 -0
  697. package/dist/structure/unspaced-heading.d.ts.map +1 -0
  698. package/dist/structure/unspaced-heading.js +24 -0
  699. package/dist/structure/unspaced-heading.js.map +1 -0
  700. package/dist/structure/versioned-label.d.ts +16 -0
  701. package/dist/structure/versioned-label.d.ts.map +1 -0
  702. package/dist/structure/versioned-label.js +48 -0
  703. package/dist/structure/versioned-label.js.map +1 -0
  704. package/dist/structure/written-headings.d.ts +31 -0
  705. package/dist/structure/written-headings.d.ts.map +1 -0
  706. package/dist/structure/written-headings.js +119 -0
  707. package/dist/structure/written-headings.js.map +1 -0
  708. package/dist/structure/written-list-path.d.ts +10 -0
  709. package/dist/structure/written-list-path.d.ts.map +1 -0
  710. package/dist/structure/written-list-path.js +37 -0
  711. package/dist/structure/written-list-path.js.map +1 -0
  712. package/dist/structure/written-resolve.d.ts +12 -0
  713. package/dist/structure/written-resolve.d.ts.map +1 -0
  714. package/dist/structure/written-resolve.js +55 -0
  715. package/dist/structure/written-resolve.js.map +1 -0
  716. package/dist/title-line.d.ts +21 -0
  717. package/dist/title-line.d.ts.map +1 -0
  718. package/dist/title-line.js +27 -0
  719. package/dist/title-line.js.map +1 -0
  720. package/package.json +3 -3
  721. package/rules/all-caps-shouting.yaml +2 -2
  722. package/rules/announced-count-mismatch.yaml +2 -2
  723. package/rules/bare-url-mix.yaml +2 -2
  724. package/rules/bracket-nesting.yaml +2 -2
  725. package/rules/bracket-width-consistency.yaml +2 -2
  726. package/rules/broken-link.yaml +2 -2
  727. package/rules/cliche.yaml +4 -3
  728. package/rules/code-fence-language-mix.yaml +2 -2
  729. package/rules/comparative-without-baseline.yaml +2 -2
  730. package/rules/concrete-evidence-density.yaml +2 -2
  731. package/rules/contraction-consistency.yaml +13 -13
  732. package/rules/dangling-figure-reference.yaml +2 -2
  733. package/rules/dangling-reference.yaml +2 -2
  734. package/rules/date-without-year.yaml +10 -2
  735. package/rules/defined-name-repeated.yaml +2 -2
  736. package/rules/defined-term-form.yaml +2 -2
  737. package/rules/doubled-punctuation.yaml +4 -4
  738. package/rules/doubled-word.yaml +2 -2
  739. package/rules/duplicate-definition.yaml +2 -2
  740. package/rules/duration-mismatch.yaml +2 -2
  741. package/rules/email-greeting-closing.yaml +2 -2
  742. package/rules/email-subject-length.yaml +2 -2
  743. package/rules/empty-table-cell.yaml +2 -2
  744. package/rules/fact-conflict.yaml +2 -2
  745. package/rules/footnote-mismatch.yaml +2 -2
  746. package/rules/heading-echo.yaml +2 -2
  747. package/rules/heading-end-punctuation-mix.yaml +2 -2
  748. package/rules/heading-numbering-mix.yaml +2 -2
  749. package/rules/ime-residue.yaml +2 -2
  750. package/rules/kanji-compound-slip.yaml +67 -0
  751. package/rules/kutoten-consistency.yaml +4 -4
  752. package/rules/latin-spacing.yaml +4 -4
  753. package/rules/list-item-form-mix.yaml +2 -2
  754. package/rules/max-kanji-continuous.yaml +7 -3
  755. package/rules/max-sentence-length.yaml +3 -2
  756. package/rules/modal-conflict.yaml +1 -0
  757. package/rules/nado-closed-list.yaml +2 -2
  758. package/rules/name-variant.yaml +2 -2
  759. package/rules/ngram-repetition.yaml +2 -2
  760. package/rules/no-doubled-joshi.yaml +2 -2
  761. package/rules/no-mixed-desumasu.yaml +3 -3
  762. package/rules/no-nakaguro-parallel.yaml +2 -0
  763. package/rules/number-without-unit.yaml +9 -4
  764. package/rules/numbering-gap.yaml +7 -2
  765. package/rules/numeral-sentence-start.yaml +2 -2
  766. package/rules/obligation-without-deadline.yaml +2 -2
  767. package/rules/orthographic-variant.yaml +2 -2
  768. package/rules/oxford-comma-consistency.yaml +3 -3
  769. package/rules/preamble-length.yaml +2 -2
  770. package/rules/reference-title-mismatch.yaml +2 -2
  771. package/rules/repeated-sentence-ending.yaml +3 -2
  772. package/rules/request-without-deadline.yaml +2 -2
  773. package/rules/requirement-smell.yaml +3 -3
  774. package/rules/sentence-rhythm.yaml +2 -2
  775. package/rules/table-header-variant.yaml +2 -2
  776. package/rules/teki-overuse.yaml +3 -2
  777. package/rules/title-case-consistency.yaml +2 -2
  778. package/rules/total-mismatch.yaml +2 -2
  779. package/rules/translationese-density.yaml +2 -2
  780. package/rules/unbalanced-bracket.yaml +2 -2
  781. package/rules/undefined-acronym.yaml +15 -4
  782. package/rules/undefined-term.yaml +2 -2
  783. package/rules/unfilled-placeholder.yaml +4 -4
  784. package/rules/use-before-definition.yaml +2 -2
  785. package/rules/vague-word-density.yaml +2 -2
  786. package/skills/chaff/SKILL.md +7 -1
  787. package/src/announced-count.ts +35 -8
  788. package/src/capitals-passage.ts +31 -0
  789. package/src/chronology-rows.ts +86 -0
  790. package/src/coined-hyphen-name.ts +27 -0
  791. package/src/company-name-run.ts +37 -0
  792. package/src/company-names.ts +24 -3
  793. package/src/compound-head.ts +25 -0
  794. package/src/date-format.ts +43 -4
  795. package/src/derived/count-per-period.ts +28 -0
  796. package/src/detectors/acronym-context.ts +34 -6
  797. package/src/detectors/acronym-definition.ts +123 -0
  798. package/src/detectors/acronym-expansion.ts +47 -6
  799. package/src/detectors/acronym-known.ts +40 -0
  800. package/src/detectors/acronym-link.ts +37 -0
  801. package/src/detectors/acronym-lone.ts +26 -0
  802. package/src/detectors/acronym-name.ts +140 -0
  803. package/src/detectors/addressee-edge.ts +16 -0
  804. package/src/detectors/announced-count.ts +1 -0
  805. package/src/detectors/bare-comparative.ts +44 -3
  806. package/src/detectors/blank-structure.ts +21 -10
  807. package/src/detectors/bracket-specified.ts +25 -0
  808. package/src/detectors/broken-link.ts +26 -2
  809. package/src/detectors/capitalised-term.ts +154 -4
  810. package/src/detectors/caps-caption.ts +103 -0
  811. package/src/detectors/caps-phrase.ts +17 -0
  812. package/src/detectors/char-shape.ts +99 -26
  813. package/src/detectors/cited-title.ts +15 -3
  814. package/src/detectors/clause-shape.ts +14 -4
  815. package/src/detectors/concrete-evidence.ts +77 -1
  816. package/src/detectors/contraction-minority.ts +11 -0
  817. package/src/detectors/counter-edge.ts +40 -2
  818. package/src/detectors/date-any-year.ts +79 -12
  819. package/src/detectors/date-format.ts +2 -1
  820. package/src/detectors/date-heading-year.ts +55 -0
  821. package/src/detectors/date-year.ts +107 -14
  822. package/src/detectors/deadline-unit.ts +40 -0
  823. package/src/detectors/defined-term-form.ts +58 -17
  824. package/src/detectors/definition-use.ts +7 -3
  825. package/src/detectors/derived-numbers.ts +19 -4
  826. package/src/detectors/doubled-across-aside.ts +36 -0
  827. package/src/detectors/doubled-punctuation.ts +28 -7
  828. package/src/detectors/doubled-word.ts +2 -1
  829. package/src/detectors/due-date.ts +10 -1
  830. package/src/detectors/ellipsis.ts +16 -1
  831. package/src/detectors/email-letter.ts +97 -21
  832. package/src/detectors/en-shape.ts +5 -1
  833. package/src/detectors/fact-consistency.ts +3 -2
  834. package/src/detectors/field-label.ts +25 -0
  835. package/src/detectors/footnote-mismatch.ts +39 -7
  836. package/src/detectors/graded-step.ts +52 -0
  837. package/src/detectors/gram-openers.ts +21 -0
  838. package/src/detectors/gram-passages.ts +36 -0
  839. package/src/detectors/gram-place.ts +10 -1
  840. package/src/detectors/gram-predicate.ts +43 -3
  841. package/src/detectors/heading-echo.ts +31 -3
  842. package/src/detectors/heading-end-mark.ts +23 -10
  843. package/src/detectors/heading-names.ts +31 -0
  844. package/src/detectors/heading-numbering.ts +7 -2
  845. package/src/detectors/ime-residue.ts +4 -3
  846. package/src/detectors/inch-mark.ts +49 -0
  847. package/src/detectors/kanji-compound-slip.ts +61 -0
  848. package/src/detectors/kutoten-consistency.ts +93 -14
  849. package/src/detectors/lexicon.ts +44 -24
  850. package/src/detectors/link-shape.ts +10 -3
  851. package/src/detectors/list-item-ending.ts +51 -0
  852. package/src/detectors/list-parallel.ts +158 -33
  853. package/src/detectors/list-sentence.ts +5 -1
  854. package/src/detectors/mark-shape.ts +70 -10
  855. package/src/detectors/mentioned-phrase.ts +38 -0
  856. package/src/detectors/middle-dot.ts +7 -2
  857. package/src/detectors/modal-conflict.ts +5 -2
  858. package/src/detectors/name-variant-apart.ts +63 -0
  859. package/src/detectors/name-variant.ts +30 -12
  860. package/src/detectors/notice-paragraph.ts +33 -0
  861. package/src/detectors/number-style.ts +14 -2
  862. package/src/detectors/number-unit.ts +28 -1
  863. package/src/detectors/numeral-opener.ts +27 -1
  864. package/src/detectors/numeral-word.ts +33 -0
  865. package/src/detectors/obligation-without-deadline.ts +29 -4
  866. package/src/detectors/open-end-class.ts +78 -0
  867. package/src/detectors/open-end-condition.ts +40 -0
  868. package/src/detectors/open-end-names.ts +9 -3
  869. package/src/detectors/open-end-question.ts +50 -0
  870. package/src/detectors/open-end-scope.ts +62 -0
  871. package/src/detectors/opening-date.ts +47 -0
  872. package/src/detectors/ordinary-phrase.ts +62 -0
  873. package/src/detectors/organisation-run.ts +97 -0
  874. package/src/detectors/orthographic-variant.ts +103 -27
  875. package/src/detectors/orthography.ts +10 -1
  876. package/src/detectors/outline-label.ts +48 -0
  877. package/src/detectors/oxford-comma.ts +40 -1
  878. package/src/detectors/page-marker.ts +26 -0
  879. package/src/detectors/parallel-definition.ts +64 -0
  880. package/src/detectors/person-consistency.ts +5 -3
  881. package/src/detectors/phrase-match.ts +16 -5
  882. package/src/detectors/placeholder-text.ts +18 -3
  883. package/src/detectors/placeholder.ts +10 -3
  884. package/src/detectors/postcode-end.ts +16 -0
  885. package/src/detectors/prose-total-words.ts +18 -0
  886. package/src/detectors/reference-text.ts +1 -0
  887. package/src/detectors/registry/kanji-compound-slip.ts +4 -0
  888. package/src/detectors/registry/phrase-in-use.ts +4 -0
  889. package/src/detectors/registry/unfilled-placeholder.ts +2 -2
  890. package/src/detectors/registry/vague-density.ts +1 -1
  891. package/src/detectors/request-owner.ts +71 -8
  892. package/src/detectors/requirement-smell.ts +53 -7
  893. package/src/detectors/scaled-figure-unit.ts +103 -0
  894. package/src/detectors/sentence-counts.ts +24 -8
  895. package/src/detectors/sentence-ending.ts +12 -3
  896. package/src/detectors/sentence-length.ts +14 -6
  897. package/src/detectors/sentence-load.ts +9 -2
  898. package/src/detectors/sentence-rhythm.ts +8 -4
  899. package/src/detectors/series-label.ts +13 -4
  900. package/src/detectors/signals.ts +105 -55
  901. package/src/detectors/structure-tree.ts +22 -20
  902. package/src/detectors/structure.ts +2 -1
  903. package/src/detectors/subject-name-line.ts +66 -0
  904. package/src/detectors/table-header.ts +15 -1
  905. package/src/detectors/technical-docs.ts +5 -1
  906. package/src/detectors/template-sections.ts +37 -0
  907. package/src/detectors/term-mention-sentence.ts +31 -0
  908. package/src/detectors/titled-run.ts +48 -0
  909. package/src/detectors/token-shape.ts +14 -5
  910. package/src/detectors/unbalanced-bracket.ts +3 -0
  911. package/src/detectors/undefined-term.ts +8 -0
  912. package/src/detectors/unfilled-placeholder.ts +10 -0
  913. package/src/detectors/vague-density.ts +84 -0
  914. package/src/document-paragraphs.ts +27 -0
  915. package/src/document.ts +3 -23
  916. package/src/facts/fact-scope.ts +53 -4
  917. package/src/facts/table-facts.ts +43 -6
  918. package/src/figure-references.ts +7 -2
  919. package/src/format-template.ts +15 -0
  920. package/src/formula-brackets.ts +36 -0
  921. package/src/grade-api.ts +38 -16
  922. package/src/heading-numbering.ts +35 -8
  923. package/src/html/html-markdown.ts +2 -1
  924. package/src/html/html-site-chrome.ts +47 -0
  925. package/src/joined-view.ts +1 -0
  926. package/src/kanji-compound-slip.ts +98 -0
  927. package/src/latin-company-form.ts +38 -0
  928. package/src/latin-word-boundary.ts +46 -0
  929. package/src/lexicon-genres.ts +1 -1
  930. package/src/link-shape.ts +19 -0
  931. package/src/link-title.ts +38 -0
  932. package/src/list-item-paragraphs.ts +22 -0
  933. package/src/literal-quote.ts +55 -0
  934. package/src/nado-closed-list.ts +48 -5
  935. package/src/name-end-letter.ts +9 -0
  936. package/src/name-given-before.ts +40 -0
  937. package/src/name-separator.ts +91 -5
  938. package/src/name-variants.ts +21 -11
  939. package/src/name-word-order.ts +62 -17
  940. package/src/nominal-stem.ts +93 -0
  941. package/src/person-forms.ts +15 -0
  942. package/src/plugin.ts +5 -0
  943. package/src/preamble-paragraphs.ts +13 -3
  944. package/src/sentence-load.ts +7 -2
  945. package/src/spacing-code.ts +5 -1
  946. package/src/split-noun.ts +63 -0
  947. package/src/structure/attached-parts.ts +32 -0
  948. package/src/structure/build.ts +7 -4
  949. package/src/structure/cited-document-section.ts +42 -0
  950. package/src/structure/contents-lines.ts +63 -0
  951. package/src/structure/defining-names.ts +155 -0
  952. package/src/structure/definition-use.ts +116 -25
  953. package/src/structure/html-text-blocks.ts +45 -0
  954. package/src/structure/issues.ts +26 -7
  955. package/src/structure/labelled-date-order.ts +5 -2
  956. package/src/structure/labelled-order.ts +12 -3
  957. package/src/structure/list-lead-in.ts +94 -0
  958. package/src/structure/list-numbering.ts +100 -11
  959. package/src/structure/listed-paragraph.ts +45 -0
  960. package/src/structure/modal-conflict.ts +42 -7
  961. package/src/structure/negated-act.ts +49 -0
  962. package/src/structure/numbering.ts +70 -26
  963. package/src/structure/prose-total.ts +20 -6
  964. package/src/structure/reference-text.ts +25 -3
  965. package/src/structure/repeated-number.ts +110 -0
  966. package/src/structure/rounded-amount.ts +55 -0
  967. package/src/structure/section-names.ts +32 -0
  968. package/src/structure/side-step.ts +21 -0
  969. package/src/structure/spanned-label-blank.ts +39 -0
  970. package/src/structure/universal.ts +11 -2
  971. package/src/structure/unspaced-heading.ts +27 -0
  972. package/src/structure/versioned-label.ts +52 -0
  973. package/src/structure/written-headings.ts +137 -0
  974. package/src/structure/written-list-path.ts +46 -0
  975. package/src/structure/written-resolve.ts +64 -0
  976. package/src/title-line.ts +52 -0
@@ -0,0 +1,47 @@
1
+ // The date in a document's opening lines: a line that is only a date, or a labelled one, under the title ("January 17,
2
+ // 2024" below a centred heading in plain-text minutes, where the indented title block is no paragraph). Pure.
3
+ import type { Span } from "../plugin.ts";
4
+ import { dateStampIndexes, stampCandidates } from "../date-stamp.ts";
5
+
6
+ /** How many non-blank lines after the front matter make the title block. */
7
+ const OPENING_LINES = 5;
8
+ /** How many lines from the top are read at most, blank ones and front matter included. */
9
+ const LINE_REACH = 64;
10
+ const FRONT_MATTER_FENCE = "---";
11
+
12
+ export type DatedSpan = Span & { readonly value: string };
13
+
14
+ type Line = Span & { readonly text: string };
15
+
16
+ const firstLines = (source: string): Line[] =>
17
+ source.split("\n", LINE_REACH).reduce<Line[]>((lines, text) => {
18
+ const start = (lines.at(-1)?.end ?? -1) + 1;
19
+ lines.push({ start, end: start + text.length, text });
20
+ return lines;
21
+ }, []);
22
+
23
+ /** The lines after a Markdown front matter block ("---" … "---" at the very top), or all of them. */
24
+ const afterFrontMatter = (lines: readonly Line[]): readonly Line[] => {
25
+ if (lines[0]?.text.trim() !== FRONT_MATTER_FENCE) return lines;
26
+ const close = lines.findIndex((line, index) => index > 0 && line.text.trim() === FRONT_MATTER_FENCE);
27
+ return close === -1 ? lines : lines.slice(close + 1);
28
+ };
29
+
30
+ const openingLines = (source: string): Line[] =>
31
+ afterFrontMatter(firstLines(source))
32
+ .filter((line) => line.text.trim() !== "")
33
+ .slice(0, OPENING_LINES);
34
+
35
+ const firstDateIn = (dates: readonly DatedSpan[], line: Span | undefined): string | undefined =>
36
+ line === undefined ? undefined : dates.find((date) => date.start >= line.start && date.end <= line.end)?.value;
37
+
38
+ /**
39
+ * The first date of the first opening line that is a date stamp, as the tree reads it ("2024-01-17"). A label on a line of
40
+ * its own ("Date:") takes the date on the line after it.
41
+ */
42
+ export const openingDateOf = (source: string, dates: readonly DatedSpan[], labels: readonly string[]): string | undefined => {
43
+ const lines = openingLines(source);
44
+ const stamps = dateStampIndexes(stampCandidates(source, lines, dates), labels);
45
+ const at = lines.findIndex((_, index) => stamps.has(index));
46
+ return at === -1 ? undefined : (firstDateIn(dates, lines[at]) ?? firstDateIn(dates, lines[at + 1]));
47
+ };
@@ -0,0 +1,62 @@
1
+ // Where a lower-case word that a defined term shares is the ordinary word in a phrase of its own, not the term, and where
2
+ // a quoted term is named rather than used. Pure: the tokens, the source and the lexicons' words are passed in.
3
+ import type { Token } from "../plugin.ts";
4
+
5
+ /** Words that narrow a noun into a kind of its own (a common parent, a limited liability company). */
6
+ const NARROWING = new Set(["ADJ", "NOUN"]);
7
+ const LOWER_START = /^\p{Ll}/u;
8
+ /** How far back from an opening quote the words that name it as a term are looked for. */
9
+ const CUE_LOOK_BACK = 40;
10
+ const LETTER = /\p{L}/u;
11
+ const LATIN = /\p{Script=Latin}/u;
12
+
13
+ /**
14
+ * An adjective or a noun of the same Latin-script phrase right before the use narrows it into a phrase of its own (the
15
+ * common parent, a limited liability company), unless it is a word that points at the defined thing (the other party).
16
+ */
17
+ export const isNarrowedUse = (tokens: readonly Token[], at: number, pointers: readonly string[]): boolean => {
18
+ const before = tokens[at - 1];
19
+ if (before === undefined || !NARROWING.has(before.pos) || !LATIN.test(before.surface)) return false;
20
+ return !pointers.some((pointer) => pointer.toLowerCase() === before.surface.toLowerCase());
21
+ };
22
+
23
+ /**
24
+ * The use heads a phrase that names a kind of thing with "of" and a bare noun (certificates of deposit, letters of credit);
25
+ * "of" followed by an article, a pronoun or a name (the certificate of the Company) is the defined thing again.
26
+ * last is the index of the use's last token.
27
+ */
28
+ export const headsKindPhrase = (tokens: readonly Token[], last: number): boolean => {
29
+ const of = tokens[last + 1];
30
+ const noun = tokens[last + 2];
31
+ return of !== undefined && noun !== undefined && of.surface.toLowerCase() === "of" && noun.pos === "NOUN" && LOWER_START.test(noun.surface);
32
+ };
33
+
34
+ /** Every position of part inside whole, overlapping ones too. */
35
+ const positionsOf = (whole: string, part: string): number[] =>
36
+ Array.from({ length: whole.length }, (_, index) => index).filter((index) => part !== "" && whole.startsWith(part, index));
37
+
38
+ /** The use sits inside another defined term written out in any case (certificate of merger, where Certificate of Merger is defined). */
39
+ export const insideLongerTerm = (source: string, offset: number, term: string, defined: readonly string[]): boolean =>
40
+ defined.some((longer) => {
41
+ if (longer.length <= term.length) return false;
42
+ const lowerLonger = longer.toLowerCase();
43
+ return positionsOf(lowerLonger, term.toLowerCase()).some((at) => {
44
+ const start = offset - at;
45
+ return start >= 0 && source.slice(start, start + longer.length).toLowerCase() === lowerLonger;
46
+ });
47
+ });
48
+
49
+ /**
50
+ * A quoted term that the words before its opening quote name as a term (the definition of "Material Adverse Effect",
51
+ * the term "Affiliate"): the term is mentioned, not used again. opening is the offset of the opening quote.
52
+ */
53
+ export const isNamedAsTerm = (source: string, opening: number, cues: readonly string[]): boolean => {
54
+ const before = source
55
+ .slice(Math.max(0, opening - CUE_LOOK_BACK), opening)
56
+ .trimEnd()
57
+ .toLowerCase();
58
+ return cues.some((cue) => {
59
+ const lower = cue.toLowerCase();
60
+ return lower !== "" && before.endsWith(lower) && !LETTER.test(before.charAt(before.length - lower.length - 1));
61
+ });
62
+ };
@@ -0,0 +1,97 @@
1
+ import type { Token } from "../plugin.ts";
2
+
3
+ /**
4
+ * 組織の名前の前に立つ形(語彙表 organisation-form)、そのうち名前の後ろにも立つ法人格(closingForms。株式会社、監査法人)と、
5
+ * 組織や単位の名前を閉じる語(organisation-unit)。
6
+ */
7
+ export type OrganisationWords = { readonly forms: readonly string[]; readonly closingForms: readonly string[]; readonly units: readonly string[] };
8
+
9
+ /** 区切りの前に要る字数。1 字なら、普通の語の一部(外部・本部・課題)と見分けられない。 */
10
+ const MIN_BODY_LENGTH = 2;
11
+ const KANJI = /[一-鿿]/u;
12
+
13
+ const surfaceOf = (tokens: readonly Token[]): string => tokens.map((token) => token.surface).join("");
14
+ const isNumber = (token: Token): boolean => token.features?.["NumType"] === "Card";
15
+ const isProperPiece = (token: Token): boolean => token.pos === "PROPN" || token.features?.["NameType"] === "GeoUnit";
16
+
17
+ /** covering の語が、隙間なく続いて並ぶときだけ、その語の並び。改行などで割れていれば読まない。 */
18
+ const contiguous = (tokens: readonly Token[], covering: readonly number[]): Token[] | undefined => {
19
+ const run = covering.flatMap((index) => tokens.slice(index, index + 1));
20
+ const joined = run.every((token, at) => at === 0 || run[at - 1]?.span.end === token.span.start);
21
+ return run.length === covering.length && joined ? run : undefined;
22
+ };
23
+
24
+ /**
25
+ * 連なりのすぐ後ろの語が組織の語そのもの(幼稚園運営企画グループのグループ)なら、それも足した語の並び。
26
+ * 漢字でない組織の語は漢字の連なりの外にあるが、名前はそこで閉じる。
27
+ */
28
+ const withClosingUnit = (tokens: readonly Token[], covering: readonly number[], units: readonly string[]): number[] => {
29
+ const next = (covering.at(-1) ?? -1) + 1;
30
+ const [last, closing] = [tokens[next - 1], tokens[next]];
31
+ const closes =
32
+ covering.length > 0 &&
33
+ last !== undefined &&
34
+ closing !== undefined &&
35
+ last.span.end === closing.span.start &&
36
+ !KANJI.test(closing.surface) &&
37
+ units.includes(closing.surface);
38
+ return closes ? [...covering, next] : [...covering];
39
+ };
40
+
41
+ /** 頭の、語の切れ目で終わる組織の形(国立研究開発法人)の語数。無ければ 0。 */
42
+ const formLength = (run: readonly Token[], forms: ReadonlySet<string>): number =>
43
+ run.reduce((found, _, at) => (forms.has(surfaceOf(run.slice(0, at + 1))) ? at + 1 : found), 0);
44
+
45
+ /** 頭の、固有名詞と地名の単位だけの並び(紀美野町、下神野地区、気象庁)の語数。固有名詞が無ければ 0。 */
46
+ const properLength = (run: readonly Token[]): number => {
47
+ const length = run.findIndex((token) => !isProperPiece(token));
48
+ const stretch = length === -1 ? run.length : length;
49
+ return run.slice(0, stretch).some((token) => token.pos === "PROPN") ? stretch : 0;
50
+ };
51
+
52
+ /** 1 つの区切り(総務課、産業技術総合研究所)か。組織の語で閉じ、その前に 2 字以上の語があり、数を含まない。 */
53
+ const isSegment = (part: readonly Token[], units: readonly string[]): boolean => {
54
+ const text = [...surfaceOf(part)];
55
+ const closing = units.filter((unit) => text.join("").endsWith(unit));
56
+ return !part.some(isNumber) && closing.some((unit) => text.length - [...unit].length >= MIN_BODY_LENGTH);
57
+ };
58
+
59
+ /**
60
+ * run を区切りだけに割ったときの区切りの数の最大。割れなければ 0。
61
+ * 後ろから、各位置から終わりまでを割れる数を一度ずつ決める(長い連なりでも語数の二乗で済む)。
62
+ */
63
+ const segmentCount = (run: readonly Token[], units: readonly string[]): number => {
64
+ const counts = run.reduceRight<number[]>((after, _, start) => {
65
+ const best = run.slice(start).reduce((most, __, offset) => {
66
+ const end = start + offset + 1;
67
+ const rest = after[end - start - 1] ?? 0;
68
+ const closesRun = end === run.length;
69
+ return isSegment(run.slice(start, end), units) && (closesRun || rest > 0) ? Math.max(most, 1 + rest) : most;
70
+ }, 0);
71
+ return [best, ...after];
72
+ }, []);
73
+ return counts[0] ?? 0;
74
+ };
75
+
76
+ /**
77
+ * 法人格で閉じ、その前に 2 字以上の名前がある(東日本自動車販売株式会社、青葉監査法人)。数を含む連なり(2024年株式会社、第三東京販売株式会社)は名前と読まない。
78
+ * 呼び出し側は、名前に固有名詞か地名があることも求める。法令の語(株式交換完全親株式会社)は法人格で閉じても名前ではない。
79
+ */
80
+ const endsInForm = (text: string, closingForms: readonly string[]): boolean =>
81
+ !/[0-90-9]/u.test(text) && closingForms.some((form) => text.endsWith(form) && [...text].length - [...form].length >= MIN_BODY_LENGTH);
82
+
83
+ /**
84
+ * 漢字の連なりの語(covering: tokens の添字)が 1 つの組織の名前か。名前は書き手が変えられない。
85
+ * 法人格か地名・固有名詞で始まって組織の語で閉じるもの(国立研究開発法人産業技術総合研究所、紀美野町青少年育成町民会議)、
86
+ * または組織の語で閉じる区切りが 2 つ以上続くもの(国土交通省鉄道局総務課)。
87
+ * 組織の語で閉じない連なり(情報処理推進機構認定試験、総務課長)や、頭に名前の無い 1 区切り(個人情報保護法施行規則改正案検討会)は名前ではない。
88
+ */
89
+ export const isOrganisationRun = (tokens: readonly Token[], covering: readonly number[], words: OrganisationWords): boolean => {
90
+ const run = contiguous(tokens, withClosingUnit(tokens, covering, words.units));
91
+ if (run === undefined || run.length === 0) return false;
92
+ if (endsInForm(surfaceOf(run), words.closingForms) && run.some(isProperPiece) && !run.some(isNumber)) return true;
93
+ const form = formLength(run, new Set(words.forms));
94
+ const head = form > 0 ? form : properLength(run);
95
+ const segments = segmentCount(run.slice(head), words.units);
96
+ return head > 0 ? segments >= 1 : segments >= 2;
97
+ };
@@ -1,14 +1,22 @@
1
- import type { Detector, Finding, ProseDocument, Sentence, TableCell, Token } from "../plugin.ts";
1
+ import type { Detector, Finding, ProseDocument, Sentence, Span, TableCell, Token } from "../plugin.ts";
2
+ import { externalLinkTitleSpans } from "../link-title.ts";
2
3
  import { groupBy, oddSpellings, type KeyedWord, type OddSpelling } from "../spelling-variants.ts";
3
4
  import { dropsOkurigana, kanjiKeyAmong, katakanaKey, lemmaReading } from "../kana-spelling.ts";
4
5
  import { isKatakanaWord, stemOf } from "../long-vowel.ts";
6
+ import { withNounsAfterParticles } from "../nominal-stem.ts";
5
7
  import { QUOTATION_MARKS, isWithinAny, quotedSpans } from "../quoted-span.ts";
6
8
  import { nameSpans, touchesAny } from "../team-names.ts";
7
9
  import { furiganaSpans } from "../furigana.ts";
10
+ import { withCutNounsJoined } from "../split-noun.ts";
11
+ import { japaneseCompanyNameSpans } from "../company-name-run.ts";
8
12
  import { acronymsIn, isCapitalsNotSpelling } from "../capitals-with-small.ts";
9
13
  import { isPartOfAddress } from "./address-word.ts";
14
+ import { isInCapitalsPassage } from "../capitals-passage.ts";
15
+ import { withoutCoinedNames } from "../coined-hyphen-name.ts";
10
16
  import { wholeWordRuns, type WholeWordRun } from "../whole-word-runs.ts";
11
17
  import { entriesForGenre } from "../lexicon-genres.ts";
18
+ import { asNounWhereNominal, documentNounKeys } from "../nominal-stem.ts";
19
+ import { isCompoundHead } from "../compound-head.ts";
12
20
 
13
21
  /**
14
22
  * A word found in the document: where it is, which sentence it is in, its key and spelling, how it is written when that differs, and
@@ -39,24 +47,48 @@ const DISTINCT = "orthographic-variant-distinct";
39
47
  const FUKUSHI = "hiragana-fukushi";
40
48
  /** Lexicon: idioms written as noun, particle and verb (気をつける). The verb there is compared apart from the verb on its own. */
41
49
  const IDIOM = "orthographic-variant-idiom";
50
+ /** Lexicon: verbs whose て-form opening a sentence before a comma is a conjunction (あわせて、). */
51
+ const CONJUNCTION = "orthographic-variant-conjunction";
42
52
  /** Lexicon: words the tokenizer cuts in one spelling and not the other (お客様, お客 and さま). Each is read whole, keyed by its group. */
43
53
  const WHOLE_WORD = "orthographic-variant-whole-word";
54
+ /** Lexicon: suffixes written onto a word that do not make a compound of it (割当て等, 引受け後): the word keeps its okurigana there. */
55
+ const PHRASE_SUFFIX = "orthographic-variant-phrase-suffix";
44
56
 
45
57
  const patternsOf = (doc: ProseDocument, id: string, genre: string | undefined): string[] =>
46
58
  entriesForGenre(doc.lexicons[id] ?? [], genre).map((entry) => entry.pattern);
47
59
 
48
60
  /**
49
- * Whether a stretch of the sentence is outside a quotation, the team's names and a reading in brackets (HTTP(えいちてぃーてぃーぴー)):
50
- * the first two keep their own spelling, and a reading is not a spelling at all.
61
+ * The team's names, the company forms (株式会社, ㈱) a registered company name is written next to, and the links that quote an
62
+ * outside page's title (link-title.ts), placed in the source.
51
63
  */
52
- const isOpenIn = (sentence: Sentence, names: readonly string[]): IsOpen => {
53
- const closed = [...quotedSpans(sentence.text, QUOTATION_MARKS), ...furiganaSpans(sentence.text)];
54
- const named = nameSpans(sentence.text, names);
64
+ type Names = { readonly team: readonly string[]; readonly companyForms: readonly string[]; readonly linkTitles: readonly Span[] };
65
+
66
+ /** Spans placed in the source, placed in a sentence's text instead. */
67
+ const inSentence = (sentence: Sentence, spans: readonly Span[]): Span[] =>
68
+ spans.map((span) => ({ start: span.start - sentence.span.start, end: span.end - sentence.span.start }));
69
+
70
+ /**
71
+ * Whether a stretch of the sentence is outside a quotation, the team's names, a company's name (関東珪曹硝子㈱) and a reading in
72
+ * brackets (HTTP(えいちてぃーてぃーぴー)): the first three keep their own spelling, and a reading is not a spelling at all.
73
+ */
74
+ const isOpenIn = (sentence: Sentence, names: Names): IsOpen => {
75
+ const closed = [
76
+ ...quotedSpans(sentence.text, QUOTATION_MARKS),
77
+ ...furiganaSpans(sentence.text),
78
+ ...japaneseCompanyNameSpans(sentence.text, names.companyForms),
79
+ ...inSentence(sentence, names.linkTitles),
80
+ ];
81
+ const named = nameSpans(sentence.text, names.team);
55
82
  return (start, end) => !isWithinAny(closed, { start, end }) && !touchesAny(named, start, end);
56
83
  };
57
84
 
58
- /** A word and the two words before it, in its sentence. */
59
- type InContext = { readonly token: Token; readonly previous: Token | undefined; readonly before: Token | undefined };
85
+ /** A word, the two words before it and the two after it, in its sentence. */
86
+ type InContext = {
87
+ readonly token: Token;
88
+ readonly previous: Token | undefined;
89
+ readonly before: Token | undefined;
90
+ readonly following?: readonly Token[];
91
+ };
60
92
 
61
93
  /** A verb's て-form the tokenizer read as a conjunction (追って at the head of a sentence): a kanji stem and て or で. Connectives (そして, それで) are kana. */
62
94
  const TE_FORM_CONJUNCTION = /^\p{Script=Han}.*[てで]$/u;
@@ -94,13 +126,32 @@ const isKanaSuffix = ({ token, previous }: InContext): boolean =>
94
126
  const isIdiomVerb = ({ token, previous, before }: InContext, idioms: ReadonlySet<string>): boolean =>
95
127
  token.pos === "VERB" && previous?.pos === "ADP" && before !== undefined && idioms.has(`${before.surface}${previous.surface}${token.lemma ?? token.surface}`);
96
128
 
129
+ const TE = new Set(["て", "で"]);
130
+ const COMMA = new Set(["、", ",", ","]);
131
+
132
+ /**
133
+ * A listed verb's て-form that opens its sentence and is followed by a comma (あわせて、…): a conjunction ("in addition"), which
134
+ * many guides write in kana while the verb (日程を合わせる) keeps its kanji.
135
+ */
136
+ const isConjunctionUse = ({ token, previous, following }: InContext, conjunctions: ReadonlySet<string>): boolean =>
137
+ token.pos === "VERB" &&
138
+ conjunctions.has(token.lemma ?? "") &&
139
+ (previous === undefined || previous.pos === "PUNCT") &&
140
+ TE.has(following?.[0]?.surface ?? "") &&
141
+ COMMA.has(following?.[1]?.surface ?? "");
142
+
143
+ /** The lexicons that set a verb's use apart: idioms (気をつける) and conjunctions (あわせて、). */
144
+ type Uses = { readonly idioms: ReadonlySet<string>; readonly conjunctions: ReadonlySet<string> };
145
+
97
146
  /**
98
147
  * A helper verb or a dependent noun (見て下さい, その事) is written kana by many guides while the full word keeps its kanji (資料を下さい).
99
148
  * The two uses are compared apart, so a document that follows that convention is consistent. A suffix (業務用, 全員ぶん) is a third use:
100
- * it is not the dependent noun of the same reading (このように). The verb of an idiom (気をつける) is a fourth.
149
+ * it is not the dependent noun of the same reading (このように). The verb of an idiom (気をつける) is a fourth, and a
150
+ * て-form used as a conjunction (あわせて、) a fifth.
101
151
  */
102
- const useOf = (word: InContext, idioms: ReadonlySet<string>): string => {
152
+ const useOf = (word: InContext, { idioms, conjunctions }: Uses): string => {
103
153
  if (isIdiomVerb(word, idioms)) return "idiom";
154
+ if (isConjunctionUse(word, conjunctions)) return "conjunction";
104
155
  if (isKanaSuffix(word)) return "suffix";
105
156
  if (!isHelper(word)) return "free";
106
157
  return word.token.pos === "NOUN" && word.token.features?.["NounType"] !== "Dependent" ? "suffix" : "bound";
@@ -121,15 +172,24 @@ const isCutFromKatakana = ({ token, previous }: InContext): boolean =>
121
172
  const isCopulaReadAsVerb = ({ token, previous }: InContext): boolean =>
122
173
  token.pos === "VERB" && token.surface === "で" && previous !== undefined && previous.pos !== "ADP";
123
174
 
124
- type Skips = { readonly skip: ReadonlySet<string>; readonly idioms: ReadonlySet<string>; readonly wholeWords: ReadonlyMap<string, string> };
175
+ type Skips = {
176
+ readonly skip: ReadonlySet<string>;
177
+ readonly idioms: ReadonlySet<string>;
178
+ readonly conjunctions: ReadonlySet<string>;
179
+ readonly wholeWords: ReadonlyMap<string, string>;
180
+ readonly phraseSuffixes: ReadonlySet<string>;
181
+ /** The document's nouns, as documentNounKeys keys them. */
182
+ readonly nouns: ReadonlySet<string>;
183
+ };
125
184
 
126
- const readingKeyOf = (word: InContext, { skip, idioms }: Skips): string | undefined => {
185
+ const readingKeyOf = (word: InContext, skips: Skips): string | undefined => {
186
+ const { skip } = skips;
127
187
  const { token } = word;
128
188
  const lemma = token.lemma;
129
189
  if (!CONTENT.has(token.pos) || token.reading === undefined || lemma === undefined || !JAPANESE_WORD.test(lemma) || skip.has(lemma)) return undefined;
130
190
  const reading = lemmaReading(token.surface, lemma, token.reading);
131
191
  if (reading === undefined || [...reading].length < MIN_READING || skip.has(reading) || isCutFromKatakana(word) || isCopulaReadAsVerb(word)) return undefined;
132
- return `${token.pos}|${useOf(word, idioms)}|${reading}`;
192
+ return `${token.pos}|${useOf(word, skips)}|${reading}`;
133
193
  };
134
194
 
135
195
  /**
@@ -150,19 +210,20 @@ const wholeWordOf = (
150
210
 
151
211
  /** Japanese words keyed by part of speech, use and the reading of the dictionary form, spelled as the dictionary form. */
152
212
  const readingWords = (sentence: Sentence, isOpen: IsOpen, skips: Skips): Placed[] => {
153
- const tokens = sentence.tokens ?? [];
213
+ const tokens = withNounsAfterParticles(sentence.tokens ?? []);
154
214
  const runs = wholeWordRuns(tokens, skips.wholeWords);
155
215
  const inRun = new Set(runs.flatMap(({ first, last }) => Array.from({ length: last - first + 1 }, (_, extra) => first + extra)));
156
216
  const whole = runs.flatMap((run) => wholeWordOf(sentence, tokens, run, isOpen, skips.wholeWords));
157
217
  return [
158
218
  ...whole,
159
- ...tokens.flatMap((token, at): Placed[] => {
219
+ ...tokens.flatMap((written, at): Placed[] => {
160
220
  if (inRun.has(at)) return [];
161
- const key = readingKeyOf({ token, previous: tokens[at - 1], before: tokens[at - 2] }, skips);
221
+ const next = tokens[at + 1];
222
+ const token = asNounWhereNominal(written, next, skips.phraseSuffixes, skips.nouns);
223
+ const key = readingKeyOf({ token, previous: tokens[at - 1], before: tokens[at - 2], following: tokens.slice(at + 1, at + 3) }, skips);
162
224
  const local = token.span.start - sentence.span.start;
163
225
  if (key === undefined || token.lemma === undefined || !isOpen(local, local + token.surface.length)) return [];
164
- const next = tokens[at + 1];
165
- const compoundHead = token.pos === "NOUN" && next?.pos === "NOUN" && isTouching(token, next);
226
+ const compoundHead = isCompoundHead(token, tokens, at, skips.phraseSuffixes);
166
227
  return [{ key, spelling: token.lemma, sentence, offset: token.span.start, compoundHead }];
167
228
  }),
168
229
  ];
@@ -260,7 +321,7 @@ const latinWords = (sentence: Sentence, isOpen: IsOpen, skip: ReadonlySet<string
260
321
  const plain = word.toLowerCase().replaceAll("-", "");
261
322
  const end = match.index + word.length;
262
323
  if (plain.length < MIN_LATIN_KEY || !LOWER.test(word) || isCapitalsNotSpelling(word, acronyms) || skip.has(word.toLowerCase())) return [];
263
- if (isPartOfAddress(sentence.text, match.index, end) || !isOpen(match.index, end)) return [];
324
+ if (isPartOfAddress(sentence.text, match.index, end) || !isOpen(match.index, end) || isInCapitalsPassage(sentence.text, match.index, end)) return [];
264
325
  return [{ key: `latin|${plain}`, spelling: latinSpelling(word), shown: word, sentence, offset: sentence.span.start + match.index }];
265
326
  });
266
327
  };
@@ -289,7 +350,7 @@ const LINK_CHROME = /\]\([^)]*\)|\]\[[^\]]*\]|\[/gu;
289
350
  const withoutLinkChrome = (text: string): string => text.replaceAll(LINK_CHROME, (chrome) => " ".repeat(chrome.length));
290
351
 
291
352
  /** A body cell of a table read as a sentence of its own: the prose covers tables, so a cell's words (片栗粉 in a list of ingredients) are not in the sentences. Header rows stay out. */
292
- const cellPlace = (cell: TableCell, names: readonly string[]): Place => {
353
+ const cellPlace = (cell: TableCell, names: Names): Place => {
293
354
  const text = withoutLinkChrome(cell.text);
294
355
  const sentence: Sentence = { span: { start: cell.start, end: cell.end }, text, tokens: cell.tokens ?? [] };
295
356
  return { sentence, isOpen: isOpenIn(sentence, names), readsLatin: !DATA_KEY_CELL.test(text.trim()) };
@@ -301,20 +362,35 @@ const cellPlace = (cell: TableCell, names: readonly string[]): Place => {
301
362
  * document writes less is pointed at. No way is called right; limit is the largest share, in percent, the minority may have.
302
363
  */
303
364
  export const orthographicVariant: Detector = (doc, options): Finding[] => {
304
- const skips: Skips = {
305
- skip: new Set([...patternsOf(doc, DISTINCT, options.genre), ...patternsOf(doc, FUKUSHI, options.genre)]),
306
- idioms: new Set(patternsOf(doc, IDIOM, options.genre)),
307
- wholeWords: new Map((doc.lexicons[WHOLE_WORD] ?? []).map((entry) => [entry.pattern, entry.group ?? entry.pattern])),
365
+ const names: Names = {
366
+ team: doc.names ?? [],
367
+ companyForms: (doc.lexicons["company-form"] ?? []).map((entry) => entry.pattern),
368
+ linkTitles: externalLinkTitleSpans(doc.source, doc.links),
308
369
  };
309
- const names = doc.names ?? [];
310
370
  const placed: Place[] = [
311
371
  ...doc.sentences.map((sentence) => ({ sentence, isOpen: isOpenIn(sentence, names), readsLatin: true })),
312
372
  ...(doc.tableCells?.() ?? []).map((cell) => cellPlace(cell, names)),
313
373
  ];
314
- const reading = byKanji(placed.flatMap(({ sentence, isOpen }) => readingWords(sentence, isOpen, skips)));
374
+ const phraseSuffixes = new Set(patternsOf(doc, PHRASE_SUFFIX, options.genre));
375
+ const skips: Skips = {
376
+ skip: new Set([...patternsOf(doc, DISTINCT, options.genre), ...patternsOf(doc, FUKUSHI, options.genre)]),
377
+ idioms: new Set(patternsOf(doc, IDIOM, options.genre)),
378
+ conjunctions: new Set(patternsOf(doc, CONJUNCTION, options.genre)),
379
+ wholeWords: new Map((doc.lexicons[WHOLE_WORD] ?? []).map((entry) => [entry.pattern, entry.group ?? entry.pattern])),
380
+ phraseSuffixes,
381
+ nouns: documentNounKeys(
382
+ placed.map(({ sentence }) => sentence.tokens ?? []),
383
+ phraseSuffixes,
384
+ ),
385
+ };
386
+ const reading = byKanji(placed.flatMap(({ sentence, isOpen }) => readingWords(withCutNounsJoined(sentence, skips.nouns), isOpen, skips)));
315
387
  const katakana = placed.flatMap(({ sentence, isOpen }) => katakanaWords(sentence, isOpen));
316
388
  const runs = placed.flatMap(({ sentence, isOpen }) => katakanaRunWords(sentence, isOpen));
317
- const latin = placed.flatMap(({ sentence, isOpen, readsLatin }) => (readsLatin ? latinWords(sentence, isOpen, skips.skip) : []));
389
+ const dictionary = doc.dictionary?.();
390
+ const latin = withoutCoinedNames(
391
+ placed.flatMap(({ sentence, isOpen, readsLatin }) => (readsLatin ? latinWords(sentence, isOpen, skips.skip) : [])),
392
+ (word) => dictionary?.has(word) ?? true,
393
+ );
318
394
  const odd = [reading, katakana, latin].flatMap((words) => oddSpellings(words, options.limit));
319
395
  const oddRuns = oddSpellings(runs, options.limit).filter(({ word }) => !odd.some((other) => coversOffset(word, other.word.offset)));
320
396
  const all = [...reading, ...katakana, ...runs, ...latin];
@@ -8,6 +8,7 @@ import { digitRunAround, endsWithDivisionLabel, isNumberName, sequenceLabelStart
8
8
  import { isSpacedLocationPart, type FloorWords } from "../location-part.ts";
9
9
  import { isFieldSeparator, isNameSeparator, type OrganizationWords } from "../name-separator.ts";
10
10
  import { addressSpans, clockTimeSpans, identifierSpans, isInsideSpan } from "../spacing-code.ts";
11
+ import { isBoundSuffix, isJoinerSpace } from "../latin-word-boundary.ts";
11
12
 
12
13
  /** 書いた形の出現に、動詞の活用した形(行う → 行います)を足したもの。同じ位置は一度だけ。 */
13
14
  const avoidedStarts = (sentence: Sentence, entry: LexiconEntry, use: string): number[] => {
@@ -55,6 +56,8 @@ type NumberContext = NameContext & {
55
56
  readonly itemNumbers: ReadonlySet<string>;
56
57
  readonly floors: FloorWords;
57
58
  readonly organizations: OrganizationWords;
59
+ /** 日本語の句をつなぐ英語の語(or、vs.)と、英字の語に付ける接尾の語(版、化)。 */
60
+ readonly latinWords: { readonly joiners: ReadonlySet<string>; readonly boundSuffixes: ReadonlySet<string> };
58
61
  };
59
62
 
60
63
  /** 文頭の項目の番号の後ろと見る境目の位置の上限。番号は短く文の頭にあるので、これより後ろの境目は番号の後ろではない。長い文で文頭からの切り出しを繰り返さない。 */
@@ -105,7 +108,12 @@ const isCounted = (sentence: Sentence, boundary: Boundary, context: NumberContex
105
108
  if (followsItemNumber(sentence.text, boundary, context.itemNumbers) || besideSpan(codes.identifiers, boundary)) return false;
106
109
  if (boundary.kind !== "after-digit" && endsWithDivisionLabel(sentence.text.slice(0, boundary.offset), context.divisions)) return false;
107
110
  if (boundary.kind === "letter")
108
- return !besideSpan(codes.addresses, boundary) && !isNameSeparator(sentence.text, boundary, sentence.tokens, sentence.span.start, context.organizations);
111
+ return (
112
+ !besideSpan(codes.addresses, boundary) &&
113
+ !isNameSeparator(sentence.text, boundary, sentence.tokens, sentence.span.start, context.organizations) &&
114
+ !isJoinerSpace(sentence.text, boundary, context.latinWords.joiners) &&
115
+ !isBoundSuffix(sentence.text, boundary, sentence.tokens, sentence.span.start, context.latinWords.boundSuffixes)
116
+ );
109
117
  if (isInsideSpan(codes.clockTimes, digitBeside(boundary))) return false;
110
118
  const run = digitRunAround(sentence.text, digitBeside(boundary));
111
119
  if (run === undefined) return true;
@@ -180,6 +188,7 @@ export const latinSpacing: Detector = (doc, options): Finding[] => {
180
188
  itemNumbers: numberedItems(patternList(doc, "item-number"), doc.prose ?? doc.source),
181
189
  floors: { units: patternsOf(doc, "floor-unit"), levels: patternsOf(doc, "floor-level") },
182
190
  organizations: { units: patternsOf(doc, "organization-unit"), forms: patternList(doc, "company-form") },
191
+ latinWords: { joiners: patternsOf(doc, "latin-joiner"), boundSuffixes: patternsOf(doc, "latin-bound-suffix") },
183
192
  };
184
193
  const located: Located[] = doc.sentences.flatMap((sentence) => {
185
194
  const quoted = quotedSpans(sentence.text);
@@ -0,0 +1,48 @@
1
+ import { escapeRegExp } from "../orthography.ts";
2
+
3
+ /**
4
+ * 行頭の、文字で振った見出しの番号(議事録の Z. の次の AA.、AB. … BZ.)。表計算の列名と同じく A〜Z の次は AA と進む。
5
+ * 略語ではない。行頭で . か ) が続き、その前か後の番号も同じ文書の行頭にあるときだけ番号と読む。1 か所だけの
6
+ * 行頭の大文字(IT. の説明、FAQ) の行)は略語のまま数える。そう読めた番号を区切りの名前の後ろで指す所(See Attachment AA)も
7
+ * 番号。区切りの名前は言語パッケージの語彙表から読む。
8
+ */
9
+
10
+ type Span = { readonly start: number; readonly end: number };
11
+
12
+ const LABEL = /^[ \t]*(?<label>[A-Z]{1,3})[.)](?=[ \t]|$)/gmu;
13
+ const ALPHABET = 26;
14
+ const CODE_BEFORE_A = 64;
15
+
16
+ /** A=1、Z=26、AA=27、AZ=52、BA=53。 */
17
+ const positionOf = (label: string): number => [...label].reduce((total, letter) => total * ALPHABET + (letter.charCodeAt(0) - CODE_BEFORE_A), 0);
18
+
19
+ type Label = { readonly text: string; readonly position: number; readonly span: Span };
20
+
21
+ const labelsOf = (source: string): Label[] =>
22
+ [...source.matchAll(LABEL)].map((match) => {
23
+ const text = match.groups?.["label"] ?? "";
24
+ const start = match.index + match[0].indexOf(text);
25
+ return { text, position: positionOf(text), span: { start, end: start + text.length } };
26
+ });
27
+
28
+ const lineLabels = (source: string): Label[] => {
29
+ const labels = labelsOf(source);
30
+ const positions = new Set(labels.map((label) => label.position));
31
+ return labels.filter(({ position }) => positions.has(position - 1) || positions.has(position + 1));
32
+ };
33
+
34
+ const referenceSpans = (source: string, labels: readonly Label[], divisions: readonly string[]): Span[] => {
35
+ const texts = [...new Set(labels.map((label) => label.text))];
36
+ if (texts.length === 0 || divisions.length === 0) return [];
37
+ const pattern = new RegExp(String.raw`(?<![A-Za-z0-9_])(?:${divisions.map(escapeRegExp).join("|")})\s+(?<label>${texts.join("|")})(?![A-Za-z0-9_&])`, "gu");
38
+ return [...source.matchAll(pattern)].map((match) => {
39
+ const end = match.index + match[0].length;
40
+ return { start: end - (match.groups?.["label"] ?? "").length, end };
41
+ });
42
+ };
43
+
44
+ /** 文書の中の、隣の番号と並んだ文字の番号と、それを区切りの名前の後ろで指す所の範囲。位置は文書の頭からの文字数。 */
45
+ export const outlineLabelSpans = (source: string, divisions: readonly string[]): Span[] => {
46
+ const labels = lineLabels(source);
47
+ return [...labels.map((label) => label.span), ...referenceSpans(source, labels, divisions)];
48
+ };
@@ -45,6 +45,7 @@ import {
45
45
  type View,
46
46
  } from "./list-view.ts";
47
47
  import { lowerBound, type TokenRange } from "./token-column.ts";
48
+ import { followsPostcode } from "./postcode-end.ts";
48
49
 
49
50
  const EMPTY: TokenRange = { start: 0, end: 0 };
50
51
 
@@ -55,10 +56,35 @@ const commaBefore = (scope: ItemScope, at: number): boolean => scope.sentence.to
55
56
  * 節の最初の項目が前置詞・接続詞・副詞・to・過去分詞で始まり、次の項目と頭の形が違えば外す。
56
57
  * Quickly, quietly and carefully は残る。For managers, engineers and designers, も外れるが、前置詞のあとの名詞を
57
58
  * 項目と読むと、Over this period, the subcommittees and the full committee ... を並びと誤る。こちらのほうが多い。
59
+ * 順番の語(First,)のあとにもう一つ導入の句が続く(First, outside a block, …)ときは、順番の語を外してから確かめる。
58
60
  */
59
61
  const LEAD_POS = new Set(["ADP", "SCONJ", "ADV", "PART"]);
60
62
 
63
+ const isSequenceWord = (scope: ItemScope, token: Token | undefined): boolean => scope.sentence.words.sequence?.has(token?.surface.toLowerCase() ?? "") ?? false;
64
+
65
+ const SENTENCE_MARKS = new Set(["PUNCT", "SYM"]);
66
+
67
+ /**
68
+ * 順番の語と読点(First, / Next,)で始まる最初の項目から、その語を外した並び。解析器は First を形容詞と読み、読点で項目を切らないことがある。
69
+ * 文頭の語だけ。文の途中の first は項目のことがある(We support first, fallback, and legacy modes)。
70
+ * 次の項目も順番の語なら、順番の語の並び(first, second and third)なので外さない。
71
+ */
72
+ const withoutSequenceWord = (view: View): View | undefined => {
73
+ const { scope } = view.list;
74
+ const [first, second] = [firstOf(view), secondOf(view)];
75
+ if (first === undefined || second === undefined) return undefined;
76
+ const at = firstAt(scope, "open", first.item);
77
+ const { tokens } = scope.sentence;
78
+ const opensSentence = tokens.slice(0, at).every((token) => SENTENCE_MARKS.has(token.pos));
79
+ if (!opensSentence || !isSequenceWord(scope, tokens[at]) || tokens[at + 1]?.surface !== "," || isSequenceWord(scope, openingOf(scope, second.item)))
80
+ return undefined;
81
+ const rest = { start: at + 2, end: first.item.end };
82
+ return hasContent(scope, rest) ? { ...withoutFirst(view), pre: rest } : withoutFirst(view);
83
+ };
84
+
61
85
  const withoutLead = (view: View): View => {
86
+ const afterSequence = withoutSequenceWord(view);
87
+ if (afterSequence !== undefined) return withoutLead(afterSequence);
62
88
  const { scope } = view.list;
63
89
  const [first, second] = [firstOf(view), secondOf(view)];
64
90
  const opening = first === undefined ? undefined : openingOf(scope, first.item);
@@ -225,6 +251,15 @@ const itemsAgree = (scope: ItemScope, view: View, afterItem: TokenRange, shape:
225
251
  return clausesAgree && (!VERBAL.has(shape) || every(view, "hasVerb"));
226
252
  };
227
253
 
254
+ /** 否定で始まる項目(not cleaner)。 */
255
+ const CONTRAST = new Set(["not", "never"]);
256
+
257
+ /**
258
+ * and / or の前の項目が否定で始まれば、読点の前と対比している(more correct, not cleaner or more elegant)。
259
+ * and / or が結ぶのは否定の中の 2 つで、読点の前の項目と並ぶ 3 つではない。
260
+ */
261
+ const opensContrast = (scope: ItemScope, item: TokenRange): boolean => CONTRAST.has(openingOf(scope, item)?.surface.toLowerCase() ?? "");
262
+
228
263
  /**
229
264
  * 読点で区切った項目が and / or の前に 2 つ以上あり、最後の項目と and の後ろが同じ形のときだけ並列。
230
265
  * 導入の読点(After the review, the team fixed the bug and shipped it.)や、節をつなぐ読点
@@ -237,6 +272,7 @@ const listAt = (list: ItemList, at: number): boolean | undefined => {
237
272
  const items = fromParticiplePhrase(fromExample(afterClosedList(withoutLead(wholeList(list)))), afterItem);
238
273
  if (listContinues(scope, afterItem) || isAppositive(scope, at, items, afterItem) || insideLastItem(scope, at, items, afterItem)) return undefined;
239
274
  const last = lastOf(items);
275
+ if (last !== undefined && opensContrast(scope, last.item)) return undefined;
240
276
  const shape = last === undefined ? undefined : shapeOf(scope, last.item);
241
277
  if (sizeOf(items) < 2 || shape === undefined || shape !== shapeOf(scope, afterItem)) return undefined;
242
278
  return itemsAgree(scope, items, afterItem, shape) ? commaBefore(scope, at) : undefined;
@@ -254,7 +290,8 @@ export const listVerdicts = (tokens: readonly Token[], words: ListWords, source:
254
290
  const readItems = listReader(sentence);
255
291
  return tokens.flatMap((token, at) => {
256
292
  if (!isJudgedConjunction(token, at)) return [];
257
- return [sentence.inCitedTitle(at) ? undefined : listAt(readItems(at), at)];
293
+ // 郵便番号で終わる住所のあとの and / or は、住所の行を区切る読点のあと。並びの読点ではない。
294
+ return [sentence.inCitedTitle(at) || followsPostcode(source, token.span.start) ? undefined : listAt(readItems(at), at)];
258
295
  });
259
296
  };
260
297
 
@@ -275,6 +312,8 @@ export const oxfordComma: Detector = (doc, options): Finding[] => {
275
312
  example: doc.lexicons["example-marker"] ?? [],
276
313
  pair: patternsOf(doc.lexicons["pair-opener"]),
277
314
  region: doc.lexicons["place-region"] ?? [],
315
+ titleCue: (doc.lexicons["title-cue"] ?? []).map((entry) => entry.pattern),
316
+ sequence: patternsOf(doc.lexicons["sequence-opener"]),
278
317
  };
279
318
  const judged = doc.sentences.flatMap((sentence) => {
280
319
  const oxford = oxfordIn(sentence.tokens ?? [], words, doc.source);
@@ -0,0 +1,26 @@
1
+ import { escapeRegExp } from "../orthography.ts";
2
+ import type { LengthUnit } from "../plugin.ts";
3
+
4
+ /**
5
+ * Page markers a converted print edition leaves inside a sentence ("( printed page 52044)", "[[Page 52044]]", 「-12-」).
6
+ * They are the page break, not the writer's words. The shapes come from the lexicon: "#" stands for the page number and a
7
+ * space for any run of spaces, none included. A marker touching a digit is part of a number (an address, 1-2-3).
8
+ */
9
+ const NUMBER = "#";
10
+
11
+ const TEMPLATE_PARTS: Readonly<Record<string, string>> = { [NUMBER]: String.raw`\p{Nd}+`, " ": String.raw`\s*` };
12
+
13
+ const templatePattern = (template: string): string => [...template].map((char) => TEMPLATE_PARTS[char] ?? escapeRegExp(char)).join("");
14
+
15
+ /** One pattern for every page marker the lexicon names, or undefined when it names none. */
16
+ export const pageMarkerPattern = (templates: readonly string[]): RegExp | undefined =>
17
+ templates.length === 0 ? undefined : new RegExp(String.raw`(?<!\p{Nd})(?:${templates.map(templatePattern).join("|")})(?!\p{Nd})`, "gu");
18
+
19
+ const sizeOf = (marker: string, unit: LengthUnit): number =>
20
+ unit === "word" ? marker.split(/\s+/u).filter((word) => word.length > 0).length : marker.replace(/\s+/gu, "").length;
21
+
22
+ /** How much of a sentence its page markers take up, in the document's unit: their words, or their characters without spaces. */
23
+ export const pageMarkerSize = (text: string, pattern: RegExp | undefined, unit: LengthUnit): number => {
24
+ if (pattern === undefined) return 0;
25
+ return [...text.matchAll(pattern)].map((match) => match[0]).reduce((size, marker) => size + sizeOf(marker, unit), 0);
26
+ };