chaffjs 0.28.0 → 0.29.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/ai-score/of-document.d.ts.map +1 -1
- package/dist/ai-score/of-document.js +23 -14
- package/dist/ai-score/of-document.js.map +1 -1
- package/dist/ai-score/render.d.ts.map +1 -1
- package/dist/ai-score/render.js +13 -4
- package/dist/ai-score/render.js.map +1 -1
- package/dist/ai-score/score.d.ts +16 -1
- package/dist/ai-score/score.d.ts.map +1 -1
- package/dist/ai-score/score.js +15 -3
- package/dist/ai-score/score.js.map +1 -1
- package/dist/ai-score/signals.d.ts +2 -4
- package/dist/ai-score/signals.d.ts.map +1 -1
- package/dist/ai-score/signals.js +11 -2
- package/dist/ai-score/signals.js.map +1 -1
- package/dist/ai-score/text.d.ts +2 -0
- package/dist/ai-score/text.d.ts.map +1 -1
- package/dist/ai-score/text.js +4 -2
- package/dist/ai-score/text.js.map +1 -1
- package/dist/announced-count.d.ts +2 -0
- package/dist/announced-count.d.ts.map +1 -1
- package/dist/announced-count.js +14 -7
- package/dist/announced-count.js.map +1 -1
- package/dist/check-source.d.ts +3 -1
- package/dist/check-source.d.ts.map +1 -1
- package/dist/check-source.js +3 -1
- package/dist/check-source.js.map +1 -1
- package/dist/cli-text.d.ts.map +1 -1
- package/dist/cli-text.js +38 -16
- package/dist/cli-text.js.map +1 -1
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +2 -1
- package/dist/cli.js.map +1 -1
- package/dist/commands/cite-claims.d.ts +36 -0
- package/dist/commands/cite-claims.d.ts.map +1 -0
- package/dist/commands/cite-claims.js +81 -0
- package/dist/commands/cite-claims.js.map +1 -0
- package/dist/commands/cite-page.d.ts +14 -0
- package/dist/commands/cite-page.d.ts.map +1 -0
- package/dist/commands/cite-page.js +47 -0
- package/dist/commands/cite-page.js.map +1 -0
- package/dist/commands/cite-scaffold.d.ts +16 -0
- package/dist/commands/cite-scaffold.d.ts.map +1 -0
- package/dist/commands/cite-scaffold.js +21 -0
- package/dist/commands/cite-scaffold.js.map +1 -0
- package/dist/commands/cite.d.ts +3 -12
- package/dist/commands/cite.d.ts.map +1 -1
- package/dist/commands/cite.js +110 -51
- package/dist/commands/cite.js.map +1 -1
- package/dist/company-names.d.ts +34 -0
- package/dist/company-names.d.ts.map +1 -0
- package/dist/company-names.js +158 -0
- package/dist/company-names.js.map +1 -0
- package/dist/default-values.d.ts +17 -0
- package/dist/default-values.d.ts.map +1 -0
- package/dist/default-values.js +134 -0
- package/dist/default-values.js.map +1 -0
- package/dist/deprecated-use.d.ts +17 -0
- package/dist/deprecated-use.d.ts.map +1 -0
- package/dist/deprecated-use.js +95 -0
- package/dist/deprecated-use.js.map +1 -0
- package/dist/derived/stays.d.ts +43 -0
- package/dist/derived/stays.d.ts.map +1 -0
- package/dist/derived/stays.js +105 -0
- package/dist/derived/stays.js.map +1 -0
- package/dist/detectors/acronym-context.d.ts +2 -2
- package/dist/detectors/acronym-context.d.ts.map +1 -1
- package/dist/detectors/acronym-context.js +6 -0
- package/dist/detectors/acronym-context.js.map +1 -1
- package/dist/detectors/address-word.d.ts +3 -0
- package/dist/detectors/address-word.d.ts.map +1 -0
- package/dist/detectors/address-word.js +7 -0
- package/dist/detectors/address-word.js.map +1 -0
- package/dist/detectors/agreement-slip.d.ts.map +1 -1
- package/dist/detectors/agreement-slip.js +4 -1
- package/dist/detectors/agreement-slip.js.map +1 -1
- package/dist/detectors/ai-phrasing.d.ts +0 -4
- package/dist/detectors/ai-phrasing.d.ts.map +1 -1
- package/dist/detectors/ai-phrasing.js +5 -1
- package/dist/detectors/ai-phrasing.js.map +1 -1
- package/dist/detectors/amount-range.d.ts +3 -0
- package/dist/detectors/amount-range.d.ts.map +1 -0
- package/dist/detectors/amount-range.js +38 -0
- package/dist/detectors/amount-range.js.map +1 -0
- package/dist/detectors/amount-scale.d.ts +6 -1
- package/dist/detectors/amount-scale.d.ts.map +1 -1
- package/dist/detectors/amount-scale.js +33 -9
- package/dist/detectors/amount-scale.js.map +1 -1
- package/dist/detectors/announced-count.d.ts +1 -1
- package/dist/detectors/announced-count.d.ts.map +1 -1
- package/dist/detectors/announced-count.js +18 -3
- package/dist/detectors/announced-count.js.map +1 -1
- package/dist/detectors/bare-comparative.d.ts.map +1 -1
- package/dist/detectors/bare-comparative.js +4 -1
- package/dist/detectors/bare-comparative.js.map +1 -1
- package/dist/detectors/block-quotation.d.ts +13 -0
- package/dist/detectors/block-quotation.d.ts.map +1 -0
- package/dist/detectors/block-quotation.js +86 -0
- package/dist/detectors/block-quotation.js.map +1 -0
- package/dist/detectors/bracket-label.d.ts +10 -0
- package/dist/detectors/bracket-label.d.ts.map +1 -0
- package/dist/detectors/bracket-label.js +51 -0
- package/dist/detectors/bracket-label.js.map +1 -0
- package/dist/detectors/citation-entry.d.ts +5 -0
- package/dist/detectors/citation-entry.d.ts.map +1 -1
- package/dist/detectors/citation-entry.js +19 -5
- package/dist/detectors/citation-entry.js.map +1 -1
- package/dist/detectors/code-before.d.ts +6 -0
- package/dist/detectors/code-before.d.ts.map +1 -0
- package/dist/detectors/code-before.js +15 -0
- package/dist/detectors/code-before.js.map +1 -0
- package/dist/detectors/connective-hierarchy.d.ts +11 -1
- package/dist/detectors/connective-hierarchy.d.ts.map +1 -1
- package/dist/detectors/connective-hierarchy.js +26 -6
- package/dist/detectors/connective-hierarchy.js.map +1 -1
- package/dist/detectors/currency-notation.d.ts.map +1 -1
- package/dist/detectors/currency-notation.js +2 -1
- package/dist/detectors/currency-notation.js.map +1 -1
- package/dist/detectors/date-outside-period.d.ts +4 -0
- package/dist/detectors/date-outside-period.d.ts.map +1 -0
- package/dist/detectors/date-outside-period.js +34 -0
- package/dist/detectors/date-outside-period.js.map +1 -0
- package/dist/detectors/default-values.d.ts +3 -0
- package/dist/detectors/default-values.d.ts.map +1 -0
- package/dist/detectors/default-values.js +14 -0
- package/dist/detectors/default-values.js.map +1 -0
- package/dist/detectors/defined-term-form.d.ts +6 -2
- package/dist/detectors/defined-term-form.d.ts.map +1 -1
- package/dist/detectors/defined-term-form.js +72 -12
- package/dist/detectors/defined-term-form.js.map +1 -1
- package/dist/detectors/definition-use.d.ts.map +1 -1
- package/dist/detectors/definition-use.js +8 -1
- package/dist/detectors/definition-use.js.map +1 -1
- package/dist/detectors/deprecated-use.d.ts +3 -0
- package/dist/detectors/deprecated-use.d.ts.map +1 -0
- package/dist/detectors/deprecated-use.js +14 -0
- package/dist/detectors/deprecated-use.js.map +1 -0
- package/dist/detectors/derived-numbers.d.ts +1 -1
- package/dist/detectors/derived-numbers.d.ts.map +1 -1
- package/dist/detectors/derived-numbers.js +70 -15
- package/dist/detectors/derived-numbers.js.map +1 -1
- package/dist/detectors/document-shape.d.ts +1 -0
- package/dist/detectors/document-shape.d.ts.map +1 -1
- package/dist/detectors/document-shape.js +4 -1
- package/dist/detectors/document-shape.js.map +1 -1
- package/dist/detectors/due-date.d.ts +3 -0
- package/dist/detectors/due-date.d.ts.map +1 -0
- package/dist/detectors/due-date.js +38 -0
- package/dist/detectors/due-date.js.map +1 -0
- package/dist/detectors/en-shape.d.ts.map +1 -1
- package/dist/detectors/en-shape.js +17 -9
- package/dist/detectors/en-shape.js.map +1 -1
- package/dist/detectors/fact-consistency.d.ts.map +1 -1
- package/dist/detectors/fact-consistency.js +76 -2
- package/dist/detectors/fact-consistency.js.map +1 -1
- package/dist/detectors/heading-echo.d.ts.map +1 -1
- package/dist/detectors/heading-echo.js +10 -1
- package/dist/detectors/heading-echo.js.map +1 -1
- package/dist/detectors/kana-function-word.d.ts +12 -0
- package/dist/detectors/kana-function-word.d.ts.map +1 -0
- package/dist/detectors/kana-function-word.js +59 -0
- package/dist/detectors/kana-function-word.js.map +1 -0
- package/dist/detectors/line-amount.d.ts +3 -0
- package/dist/detectors/line-amount.d.ts.map +1 -0
- package/dist/detectors/line-amount.js +22 -0
- package/dist/detectors/line-amount.js.map +1 -0
- package/dist/detectors/location-pointer.d.ts +6 -0
- package/dist/detectors/location-pointer.d.ts.map +1 -0
- package/dist/detectors/location-pointer.js +22 -0
- package/dist/detectors/location-pointer.js.map +1 -0
- package/dist/detectors/mark-shape.d.ts.map +1 -1
- package/dist/detectors/mark-shape.js +13 -1
- package/dist/detectors/mark-shape.js.map +1 -1
- package/dist/detectors/nado-closed-list.d.ts +3 -0
- package/dist/detectors/nado-closed-list.d.ts.map +1 -0
- package/dist/detectors/nado-closed-list.js +21 -0
- package/dist/detectors/nado-closed-list.js.map +1 -0
- package/dist/detectors/name-variant.d.ts.map +1 -1
- package/dist/detectors/name-variant.js +82 -8
- package/dist/detectors/name-variant.js.map +1 -1
- package/dist/detectors/next-word.d.ts.map +1 -1
- package/dist/detectors/next-word.js +41 -8
- package/dist/detectors/next-word.js.map +1 -1
- package/dist/detectors/number-word-figure.d.ts +5 -0
- package/dist/detectors/number-word-figure.d.ts.map +1 -0
- package/dist/detectors/number-word-figure.js +32 -0
- package/dist/detectors/number-word-figure.js.map +1 -0
- package/dist/detectors/obligation-without-deadline.d.ts +39 -0
- package/dist/detectors/obligation-without-deadline.d.ts.map +1 -0
- package/dist/detectors/obligation-without-deadline.js +148 -0
- package/dist/detectors/obligation-without-deadline.js.map +1 -0
- package/dist/detectors/open-end-names.d.ts +23 -0
- package/dist/detectors/open-end-names.d.ts.map +1 -0
- package/dist/detectors/open-end-names.js +95 -0
- package/dist/detectors/open-end-names.js.map +1 -0
- package/dist/detectors/ordinal-run-gaps.d.ts +8 -0
- package/dist/detectors/ordinal-run-gaps.d.ts.map +1 -0
- package/dist/detectors/ordinal-run-gaps.js +80 -0
- package/dist/detectors/ordinal-run-gaps.js.map +1 -0
- package/dist/detectors/orthographic-variant.d.ts.map +1 -1
- package/dist/detectors/orthographic-variant.js +26 -9
- package/dist/detectors/orthographic-variant.js.map +1 -1
- package/dist/detectors/orthography.d.ts.map +1 -1
- package/dist/detectors/orthography.js +5 -0
- package/dist/detectors/orthography.js.map +1 -1
- package/dist/detectors/parameter-table.d.ts +3 -0
- package/dist/detectors/parameter-table.d.ts.map +1 -0
- package/dist/detectors/parameter-table.js +16 -0
- package/dist/detectors/parameter-table.js.map +1 -0
- package/dist/detectors/phone-number-variant.d.ts +3 -0
- package/dist/detectors/phone-number-variant.d.ts.map +1 -0
- package/dist/detectors/phone-number-variant.js +18 -0
- package/dist/detectors/phone-number-variant.js.map +1 -0
- package/dist/detectors/prerequisite-order.d.ts +3 -0
- package/dist/detectors/prerequisite-order.d.ts.map +1 -0
- package/dist/detectors/prerequisite-order.js +30 -0
- package/dist/detectors/prerequisite-order.js.map +1 -0
- package/dist/detectors/quote-unnamed-speaker.d.ts +3 -0
- package/dist/detectors/quote-unnamed-speaker.d.ts.map +1 -0
- package/dist/detectors/quote-unnamed-speaker.js +18 -0
- package/dist/detectors/quote-unnamed-speaker.js.map +1 -0
- package/dist/detectors/quote-without-source.d.ts +12 -2
- package/dist/detectors/quote-without-source.d.ts.map +1 -1
- package/dist/detectors/quote-without-source.js +45 -11
- package/dist/detectors/quote-without-source.js.map +1 -1
- package/dist/detectors/registry/amount-range.d.ts +3 -0
- package/dist/detectors/registry/amount-range.d.ts.map +1 -0
- package/dist/detectors/registry/amount-range.js +3 -0
- package/dist/detectors/registry/amount-range.js.map +1 -0
- package/dist/detectors/registry/arrival-before-departure.d.ts +3 -0
- package/dist/detectors/registry/arrival-before-departure.d.ts.map +1 -0
- package/dist/detectors/registry/arrival-before-departure.js +3 -0
- package/dist/detectors/registry/arrival-before-departure.js.map +1 -0
- package/dist/detectors/registry/date-outside-period.d.ts +3 -0
- package/dist/detectors/registry/date-outside-period.d.ts.map +1 -0
- package/dist/detectors/registry/date-outside-period.js +3 -0
- package/dist/detectors/registry/date-outside-period.js.map +1 -0
- package/dist/detectors/registry/default-values.d.ts +3 -0
- package/dist/detectors/registry/default-values.d.ts.map +1 -0
- package/dist/detectors/registry/default-values.js +3 -0
- package/dist/detectors/registry/default-values.js.map +1 -0
- package/dist/detectors/registry/deprecated-use.d.ts +3 -0
- package/dist/detectors/registry/deprecated-use.d.ts.map +1 -0
- package/dist/detectors/registry/deprecated-use.js +3 -0
- package/dist/detectors/registry/deprecated-use.js.map +1 -0
- package/dist/detectors/registry/due-date.d.ts +3 -0
- package/dist/detectors/registry/due-date.d.ts.map +1 -0
- package/dist/detectors/registry/due-date.js +3 -0
- package/dist/detectors/registry/due-date.js.map +1 -0
- package/dist/detectors/registry/kana-function-word.d.ts +3 -0
- package/dist/detectors/registry/kana-function-word.d.ts.map +1 -0
- package/dist/detectors/registry/kana-function-word.js +3 -0
- package/dist/detectors/registry/kana-function-word.js.map +1 -0
- package/dist/detectors/registry/line-amount.d.ts +3 -0
- package/dist/detectors/registry/line-amount.d.ts.map +1 -0
- package/dist/detectors/registry/line-amount.js +3 -0
- package/dist/detectors/registry/line-amount.js.map +1 -0
- package/dist/detectors/registry/nado-closed-list.d.ts +3 -0
- package/dist/detectors/registry/nado-closed-list.d.ts.map +1 -0
- package/dist/detectors/registry/nado-closed-list.js +3 -0
- package/dist/detectors/registry/nado-closed-list.js.map +1 -0
- package/dist/detectors/registry/number-word-figure.d.ts +3 -0
- package/dist/detectors/registry/number-word-figure.d.ts.map +1 -0
- package/dist/detectors/registry/number-word-figure.js +3 -0
- package/dist/detectors/registry/number-word-figure.js.map +1 -0
- package/dist/detectors/registry/obligation-without-deadline.d.ts +3 -0
- package/dist/detectors/registry/obligation-without-deadline.d.ts.map +1 -0
- package/dist/detectors/registry/obligation-without-deadline.js +3 -0
- package/dist/detectors/registry/obligation-without-deadline.js.map +1 -0
- package/dist/detectors/registry/parameter-table.d.ts +3 -0
- package/dist/detectors/registry/parameter-table.d.ts.map +1 -0
- package/dist/detectors/registry/parameter-table.js +3 -0
- package/dist/detectors/registry/parameter-table.js.map +1 -0
- package/dist/detectors/registry/phone-number-variant.d.ts +3 -0
- package/dist/detectors/registry/phone-number-variant.d.ts.map +1 -0
- package/dist/detectors/registry/phone-number-variant.js +3 -0
- package/dist/detectors/registry/phone-number-variant.js.map +1 -0
- package/dist/detectors/registry/prerequisite-order.d.ts +3 -0
- package/dist/detectors/registry/prerequisite-order.d.ts.map +1 -0
- package/dist/detectors/registry/prerequisite-order.js +3 -0
- package/dist/detectors/registry/prerequisite-order.js.map +1 -0
- package/dist/detectors/registry/quote-unnamed-speaker.d.ts +3 -0
- package/dist/detectors/registry/quote-unnamed-speaker.d.ts.map +1 -0
- package/dist/detectors/registry/quote-unnamed-speaker.js +3 -0
- package/dist/detectors/registry/quote-unnamed-speaker.js.map +1 -0
- package/dist/detectors/registry/tax-amount.d.ts +3 -0
- package/dist/detectors/registry/tax-amount.d.ts.map +1 -0
- package/dist/detectors/registry/tax-amount.js +3 -0
- package/dist/detectors/registry/tax-amount.js.map +1 -0
- package/dist/detectors/registry/time-order.d.ts +3 -0
- package/dist/detectors/registry/time-order.d.ts.map +1 -0
- package/dist/detectors/registry/time-order.js +3 -0
- package/dist/detectors/registry/time-order.js.map +1 -0
- package/dist/detectors/registry/ui-label.d.ts +3 -0
- package/dist/detectors/registry/ui-label.d.ts.map +1 -0
- package/dist/detectors/registry/ui-label.js +3 -0
- package/dist/detectors/registry/ui-label.js.map +1 -0
- package/dist/detectors/registry/undefined-call.d.ts +3 -0
- package/dist/detectors/registry/undefined-call.d.ts.map +1 -0
- package/dist/detectors/registry/undefined-call.js +3 -0
- package/dist/detectors/registry/undefined-call.js.map +1 -0
- package/dist/detectors/registry/undefined-term.d.ts +3 -0
- package/dist/detectors/registry/undefined-term.d.ts.map +1 -0
- package/dist/detectors/registry/undefined-term.js +3 -0
- package/dist/detectors/registry/undefined-term.js.map +1 -0
- package/dist/detectors/registry/version-order.d.ts +3 -0
- package/dist/detectors/registry/version-order.d.ts.map +1 -0
- package/dist/detectors/registry/version-order.js +3 -0
- package/dist/detectors/registry/version-order.js.map +1 -0
- package/dist/detectors/registry/warning-action.d.ts +3 -0
- package/dist/detectors/registry/warning-action.d.ts.map +1 -0
- package/dist/detectors/registry/warning-action.js +3 -0
- package/dist/detectors/registry/warning-action.js.map +1 -0
- package/dist/detectors/requirement-smell.d.ts.map +1 -1
- package/dist/detectors/requirement-smell.js +25 -8
- package/dist/detectors/requirement-smell.js.map +1 -1
- package/dist/detectors/structure-tree.d.ts +12 -4
- package/dist/detectors/structure-tree.d.ts.map +1 -1
- package/dist/detectors/structure-tree.js +31 -14
- package/dist/detectors/structure-tree.js.map +1 -1
- package/dist/detectors/superlative-scope.d.ts.map +1 -1
- package/dist/detectors/superlative-scope.js +11 -1
- package/dist/detectors/superlative-scope.js.map +1 -1
- package/dist/detectors/tax-amount.d.ts +3 -0
- package/dist/detectors/tax-amount.d.ts.map +1 -0
- package/dist/detectors/tax-amount.js +19 -0
- package/dist/detectors/tax-amount.js.map +1 -0
- package/dist/detectors/technical-docs.d.ts.map +1 -1
- package/dist/detectors/technical-docs.js +5 -1
- package/dist/detectors/technical-docs.js.map +1 -1
- package/dist/detectors/term-extension.d.ts +14 -0
- package/dist/detectors/term-extension.d.ts.map +1 -0
- package/dist/detectors/term-extension.js +67 -0
- package/dist/detectors/term-extension.js.map +1 -0
- package/dist/detectors/time-order.d.ts +4 -0
- package/dist/detectors/time-order.d.ts.map +1 -0
- package/dist/detectors/time-order.js +32 -0
- package/dist/detectors/time-order.js.map +1 -0
- package/dist/detectors/ui-label.d.ts +3 -0
- package/dist/detectors/ui-label.d.ts.map +1 -0
- package/dist/detectors/ui-label.js +16 -0
- package/dist/detectors/ui-label.js.map +1 -0
- package/dist/detectors/unbalanced-bracket.d.ts.map +1 -1
- package/dist/detectors/unbalanced-bracket.js +8 -13
- package/dist/detectors/unbalanced-bracket.js.map +1 -1
- package/dist/detectors/undefined-call.d.ts +3 -0
- package/dist/detectors/undefined-call.d.ts.map +1 -0
- package/dist/detectors/undefined-call.js +18 -0
- package/dist/detectors/undefined-call.js.map +1 -0
- package/dist/detectors/undefined-term.d.ts +22 -0
- package/dist/detectors/undefined-term.d.ts.map +1 -0
- package/dist/detectors/undefined-term.js +85 -0
- package/dist/detectors/undefined-term.js.map +1 -0
- package/dist/detectors/unknown-word.d.ts +1 -1
- package/dist/detectors/unknown-word.js +3 -3
- package/dist/detectors/unknown-word.js.map +1 -1
- package/dist/detectors/vague-deadline.d.ts +4 -0
- package/dist/detectors/vague-deadline.d.ts.map +1 -1
- package/dist/detectors/vague-deadline.js +3 -3
- package/dist/detectors/vague-deadline.js.map +1 -1
- package/dist/detectors/version-mismatch.d.ts.map +1 -1
- package/dist/detectors/version-mismatch.js +18 -1
- package/dist/detectors/version-mismatch.js.map +1 -1
- package/dist/detectors/version-order.d.ts +3 -0
- package/dist/detectors/version-order.d.ts.map +1 -0
- package/dist/detectors/version-order.js +43 -0
- package/dist/detectors/version-order.js.map +1 -0
- package/dist/detectors/warning-action.d.ts +3 -0
- package/dist/detectors/warning-action.d.ts.map +1 -0
- package/dist/detectors/warning-action.js +48 -0
- package/dist/detectors/warning-action.js.map +1 -0
- package/dist/facts/condition-pairs.d.ts +51 -0
- package/dist/facts/condition-pairs.d.ts.map +1 -0
- package/dist/facts/condition-pairs.js +203 -0
- package/dist/facts/condition-pairs.js.map +1 -0
- package/dist/facts/event-dates.d.ts +26 -0
- package/dist/facts/event-dates.d.ts.map +1 -0
- package/dist/facts/event-dates.js +38 -0
- package/dist/facts/event-dates.js.map +1 -0
- package/dist/facts/fact-scope.d.ts +2 -0
- package/dist/facts/fact-scope.d.ts.map +1 -1
- package/dist/facts/fact-scope.js +5 -0
- package/dist/facts/fact-scope.js.map +1 -1
- package/dist/facts/labelled-facts.d.ts +2 -0
- package/dist/facts/labelled-facts.d.ts.map +1 -1
- package/dist/facts/labelled-facts.js +9 -1
- package/dist/facts/labelled-facts.js.map +1 -1
- package/dist/facts/table-facts.d.ts +16 -0
- package/dist/facts/table-facts.d.ts.map +1 -1
- package/dist/facts/table-facts.js +2 -2
- package/dist/facts/table-facts.js.map +1 -1
- package/dist/grade/ai-score.d.ts +1 -1
- package/dist/grade/ai-score.d.ts.map +1 -1
- package/dist/grade/text.js +2 -2
- package/dist/grade/text.js.map +1 -1
- package/dist/heading-numbering.js +2 -2
- package/dist/heading-numbering.js.map +1 -1
- package/dist/html/fetch-page.d.ts +20 -0
- package/dist/html/fetch-page.d.ts.map +1 -0
- package/dist/html/fetch-page.js +51 -0
- package/dist/html/fetch-page.js.map +1 -0
- package/dist/html/fetched-text.d.ts +5 -0
- package/dist/html/fetched-text.d.ts.map +1 -0
- package/dist/html/fetched-text.js +25 -0
- package/dist/html/fetched-text.js.map +1 -0
- package/dist/html/html-content-block.d.ts +6 -0
- package/dist/html/html-content-block.d.ts.map +1 -0
- package/dist/html/html-content-block.js +86 -0
- package/dist/html/html-content-block.js.map +1 -0
- package/dist/html/html-elements.d.ts +41 -0
- package/dist/html/html-elements.d.ts.map +1 -0
- package/dist/html/html-elements.js +91 -0
- package/dist/html/html-elements.js.map +1 -0
- package/dist/html/html-footnote-marks.d.ts +2 -0
- package/dist/html/html-footnote-marks.d.ts.map +1 -0
- package/dist/html/html-footnote-marks.js +15 -0
- package/dist/html/html-footnote-marks.js.map +1 -0
- package/dist/html/html-heading-links.d.ts +6 -0
- package/dist/html/html-heading-links.d.ts.map +1 -0
- package/dist/html/html-heading-links.js +71 -0
- package/dist/html/html-heading-links.js.map +1 -0
- package/dist/html/html-lost-tags.d.ts +3 -0
- package/dist/html/html-lost-tags.d.ts.map +1 -0
- package/dist/html/html-lost-tags.js +11 -0
- package/dist/html/html-lost-tags.js.map +1 -0
- package/dist/html/html-markdown.d.ts +2 -0
- package/dist/html/html-markdown.d.ts.map +1 -0
- package/dist/html/html-markdown.js +347 -0
- package/dist/html/html-markdown.js.map +1 -0
- package/dist/html/html-preformatted.d.ts +17 -0
- package/dist/html/html-preformatted.d.ts.map +1 -0
- package/dist/html/html-preformatted.js +82 -0
- package/dist/html/html-preformatted.js.map +1 -0
- package/dist/html/html-reader-only.d.ts +6 -0
- package/dist/html/html-reader-only.d.ts.map +1 -0
- package/dist/html/html-reader-only.js +63 -0
- package/dist/html/html-reader-only.js.map +1 -0
- package/dist/html/html-run-in-headings.d.ts +2 -0
- package/dist/html/html-run-in-headings.d.ts.map +1 -0
- package/dist/html/html-run-in-headings.js +36 -0
- package/dist/html/html-run-in-headings.js.map +1 -0
- package/dist/html/html-tables.d.ts +3 -0
- package/dist/html/html-tables.d.ts.map +1 -0
- package/dist/html/html-tables.js +58 -0
- package/dist/html/html-tables.js.map +1 -0
- package/dist/html/html-widgets.d.ts +3 -0
- package/dist/html/html-widgets.d.ts.map +1 -0
- package/dist/html/html-widgets.js +71 -0
- package/dist/html/html-widgets.js.map +1 -0
- package/dist/html/markup-text.d.ts +5 -0
- package/dist/html/markup-text.d.ts.map +1 -0
- package/dist/html/markup-text.js +32 -0
- package/dist/html/markup-text.js.map +1 -0
- package/dist/html/page-document.d.ts +9 -0
- package/dist/html/page-document.d.ts.map +1 -0
- package/dist/html/page-document.js +19 -0
- package/dist/html/page-document.js.map +1 -0
- package/dist/inline-count.d.ts +19 -0
- package/dist/inline-count.d.ts.map +1 -0
- package/dist/inline-count.js +109 -0
- package/dist/inline-count.js.map +1 -0
- package/dist/kana-spelling.d.ts +5 -0
- package/dist/kana-spelling.d.ts.map +1 -1
- package/dist/kana-spelling.js +5 -0
- package/dist/kana-spelling.js.map +1 -1
- package/dist/location-part.d.ts +13 -0
- package/dist/location-part.d.ts.map +1 -0
- package/dist/location-part.js +24 -0
- package/dist/location-part.js.map +1 -0
- package/dist/nado-closed-list.d.ts +20 -0
- package/dist/nado-closed-list.d.ts.map +1 -0
- package/dist/nado-closed-list.js +72 -0
- package/dist/nado-closed-list.js.map +1 -0
- package/dist/name-cue.d.ts +17 -0
- package/dist/name-cue.d.ts.map +1 -0
- package/dist/name-cue.js +29 -0
- package/dist/name-cue.js.map +1 -0
- package/dist/name-variants.d.ts +23 -1
- package/dist/name-variants.d.ts.map +1 -1
- package/dist/name-variants.js +39 -8
- package/dist/name-variants.js.map +1 -1
- package/dist/paragraph-runs.d.ts +6 -1
- package/dist/paragraph-runs.d.ts.map +1 -1
- package/dist/paragraph-runs.js +9 -2
- package/dist/paragraph-runs.js.map +1 -1
- package/dist/parameter-table.d.ts +19 -0
- package/dist/parameter-table.d.ts.map +1 -0
- package/dist/parameter-table.js +191 -0
- package/dist/parameter-table.js.map +1 -0
- package/dist/phone-numbers.d.ts +23 -0
- package/dist/phone-numbers.d.ts.map +1 -0
- package/dist/phone-numbers.js +83 -0
- package/dist/phone-numbers.js.map +1 -0
- package/dist/place-names.d.ts +55 -0
- package/dist/place-names.d.ts.map +1 -0
- package/dist/place-names.js +196 -0
- package/dist/place-names.js.map +1 -0
- package/dist/plugin.d.ts +4 -0
- package/dist/plugin.d.ts.map +1 -1
- package/dist/prerequisite-order.d.ts +16 -0
- package/dist/prerequisite-order.d.ts.map +1 -0
- package/dist/prerequisite-order.js +29 -0
- package/dist/prerequisite-order.js.map +1 -0
- package/dist/profile/parse.d.ts.map +1 -1
- package/dist/profile/parse.js +10 -1
- package/dist/profile/parse.js.map +1 -1
- package/dist/reasons.d.ts +2 -0
- package/dist/reasons.d.ts.map +1 -1
- package/dist/reasons.js +2 -0
- package/dist/reasons.js.map +1 -1
- package/dist/render/rules-json.d.ts.map +1 -1
- package/dist/render/rules-json.js +4 -0
- package/dist/render/rules-json.js.map +1 -1
- package/dist/render/rules-table.d.ts.map +1 -1
- package/dist/render/rules-table.js +6 -2
- package/dist/render/rules-table.js.map +1 -1
- package/dist/rule-genres.d.ts +5 -2
- package/dist/rule-genres.d.ts.map +1 -1
- package/dist/rule-genres.js +2 -0
- package/dist/rule-genres.js.map +1 -1
- package/dist/rule-load.d.ts.map +1 -1
- package/dist/rule-load.js +2 -1
- package/dist/rule-load.js.map +1 -1
- package/dist/run.d.ts.map +1 -1
- package/dist/run.js +5 -1
- package/dist/run.js.map +1 -1
- package/dist/spelling.d.ts +2 -0
- package/dist/spelling.d.ts.map +1 -1
- package/dist/spelling.js +6 -0
- package/dist/spelling.js.map +1 -1
- package/dist/structure/action-due.d.ts +21 -0
- package/dist/structure/action-due.d.ts.map +1 -0
- package/dist/structure/action-due.js +126 -0
- package/dist/structure/action-due.js.map +1 -0
- package/dist/structure/amount-range.d.ts +30 -0
- package/dist/structure/amount-range.d.ts.map +1 -0
- package/dist/structure/amount-range.js +153 -0
- package/dist/structure/amount-range.js.map +1 -0
- package/dist/structure/amount-scale.d.ts +6 -0
- package/dist/structure/amount-scale.d.ts.map +1 -1
- package/dist/structure/amount-scale.js +13 -0
- package/dist/structure/amount-scale.js.map +1 -1
- package/dist/structure/cite.d.ts +5 -2
- package/dist/structure/cite.d.ts.map +1 -1
- package/dist/structure/cite.js +20 -1
- package/dist/structure/cite.js.map +1 -1
- package/dist/structure/counted-amounts.d.ts +12 -0
- package/dist/structure/counted-amounts.d.ts.map +1 -0
- package/dist/structure/counted-amounts.js +30 -0
- package/dist/structure/counted-amounts.js.map +1 -0
- package/dist/structure/date-order.d.ts +24 -3
- package/dist/structure/date-order.d.ts.map +1 -1
- package/dist/structure/date-order.js +49 -17
- package/dist/structure/date-order.js.map +1 -1
- package/dist/structure/date-outside-period.d.ts +27 -0
- package/dist/structure/date-outside-period.d.ts.map +1 -0
- package/dist/structure/date-outside-period.js +86 -0
- package/dist/structure/date-outside-period.js.map +1 -0
- package/dist/structure/definition-use.d.ts +5 -2
- package/dist/structure/definition-use.d.ts.map +1 -1
- package/dist/structure/definition-use.js +11 -3
- package/dist/structure/definition-use.js.map +1 -1
- package/dist/structure/due-date.d.ts +19 -0
- package/dist/structure/due-date.d.ts.map +1 -0
- package/dist/structure/due-date.js +30 -0
- package/dist/structure/due-date.js.map +1 -0
- package/dist/structure/heading-runs.d.ts +9 -0
- package/dist/structure/heading-runs.d.ts.map +1 -0
- package/dist/structure/heading-runs.js +23 -0
- package/dist/structure/heading-runs.js.map +1 -0
- package/dist/structure/install-pin.d.ts +46 -0
- package/dist/structure/install-pin.d.ts.map +1 -0
- package/dist/structure/install-pin.js +85 -0
- package/dist/structure/install-pin.js.map +1 -0
- package/dist/structure/leg-times.d.ts +34 -0
- package/dist/structure/leg-times.d.ts.map +1 -0
- package/dist/structure/leg-times.js +135 -0
- package/dist/structure/leg-times.js.map +1 -0
- package/dist/structure/line-amount-unit.d.ts +24 -0
- package/dist/structure/line-amount-unit.d.ts.map +1 -0
- package/dist/structure/line-amount-unit.js +24 -0
- package/dist/structure/line-amount-unit.js.map +1 -0
- package/dist/structure/line-amount.d.ts +40 -0
- package/dist/structure/line-amount.d.ts.map +1 -0
- package/dist/structure/line-amount.js +118 -0
- package/dist/structure/line-amount.js.map +1 -0
- package/dist/structure/number-word-figure.d.ts +37 -0
- package/dist/structure/number-word-figure.d.ts.map +1 -0
- package/dist/structure/number-word-figure.js +151 -0
- package/dist/structure/number-word-figure.js.map +1 -0
- package/dist/structure/numbering.d.ts +1 -0
- package/dist/structure/numbering.d.ts.map +1 -1
- package/dist/structure/numbering.js +3 -0
- package/dist/structure/numbering.js.map +1 -1
- package/dist/structure/ordinal-runs.d.ts +45 -0
- package/dist/structure/ordinal-runs.d.ts.map +1 -0
- package/dist/structure/ordinal-runs.js +78 -0
- package/dist/structure/ordinal-runs.js.map +1 -0
- package/dist/structure/percent-sum-prose.d.ts +1 -1
- package/dist/structure/percent-sum-prose.d.ts.map +1 -1
- package/dist/structure/percent-sum-prose.js +45 -3
- package/dist/structure/percent-sum-prose.js.map +1 -1
- package/dist/structure/percent-sum.d.ts +8 -0
- package/dist/structure/percent-sum.d.ts.map +1 -1
- package/dist/structure/percent-sum.js +8 -1
- package/dist/structure/percent-sum.js.map +1 -1
- package/dist/structure/release-list.d.ts +9 -0
- package/dist/structure/release-list.d.ts.map +1 -0
- package/dist/structure/release-list.js +46 -0
- package/dist/structure/release-list.js.map +1 -0
- package/dist/structure/share-column.d.ts +7 -0
- package/dist/structure/share-column.d.ts.map +1 -0
- package/dist/structure/share-column.js +22 -0
- package/dist/structure/share-column.js.map +1 -0
- package/dist/structure/stated-period.d.ts +31 -0
- package/dist/structure/stated-period.d.ts.map +1 -0
- package/dist/structure/stated-period.js +127 -0
- package/dist/structure/stated-period.js.map +1 -0
- package/dist/structure/tax.d.ts +25 -0
- package/dist/structure/tax.d.ts.map +1 -0
- package/dist/structure/tax.js +86 -0
- package/dist/structure/tax.js.map +1 -0
- package/dist/structure/time-marks.d.ts +58 -0
- package/dist/structure/time-marks.d.ts.map +1 -0
- package/dist/structure/time-marks.js +74 -0
- package/dist/structure/time-marks.js.map +1 -0
- package/dist/structure/time-order.d.ts +21 -0
- package/dist/structure/time-order.d.ts.map +1 -0
- package/dist/structure/time-order.js +108 -0
- package/dist/structure/time-order.js.map +1 -0
- package/dist/structure/title-lines.d.ts +8 -0
- package/dist/structure/title-lines.d.ts.map +1 -0
- package/dist/structure/title-lines.js +27 -0
- package/dist/structure/title-lines.js.map +1 -0
- package/dist/structure/total.d.ts.map +1 -1
- package/dist/structure/total.js +3 -1
- package/dist/structure/total.js.map +1 -1
- package/dist/structure/version-mismatch.d.ts +1 -5
- package/dist/structure/version-mismatch.d.ts.map +1 -1
- package/dist/structure/version-mismatch.js +65 -12
- package/dist/structure/version-mismatch.js.map +1 -1
- package/dist/structure/version-order.d.ts +23 -0
- package/dist/structure/version-order.d.ts.map +1 -0
- package/dist/structure/version-order.js +67 -0
- package/dist/structure/version-order.js.map +1 -0
- package/dist/table-text.d.ts +9 -0
- package/dist/table-text.d.ts.map +1 -0
- package/dist/table-text.js +36 -0
- package/dist/table-text.js.map +1 -0
- package/dist/ui-labels.d.ts +16 -0
- package/dist/ui-labels.d.ts.map +1 -0
- package/dist/ui-labels.js +42 -0
- package/dist/ui-labels.js.map +1 -0
- package/dist/undefined-call.d.ts +13 -0
- package/dist/undefined-call.d.ts.map +1 -0
- package/dist/undefined-call.js +55 -0
- package/dist/undefined-call.js.map +1 -0
- package/dist/unnamed-speaker.d.ts +23 -0
- package/dist/unnamed-speaker.d.ts.map +1 -0
- package/dist/unnamed-speaker.js +176 -0
- package/dist/unnamed-speaker.js.map +1 -0
- package/dist/warning-action.d.ts +22 -0
- package/dist/warning-action.d.ts.map +1 -0
- package/dist/warning-action.js +58 -0
- package/dist/warning-action.js.map +1 -0
- package/genres.yaml +2 -0
- package/package.json +4 -3
- package/profiles/statute.yaml +8 -0
- package/rules/agreement-slip.yaml +2 -2
- package/rules/amount-range-reversed.yaml +52 -0
- package/rules/amount-scale-consistency.yaml +4 -4
- package/rules/announced-count-mismatch.yaml +9 -4
- package/rules/arrival-before-departure.yaml +48 -0
- package/rules/connective-hierarchy.yaml +3 -3
- package/rules/currency-notation-consistency.yaml +2 -2
- package/rules/date-order.yaml +9 -4
- package/rules/date-outside-period.yaml +64 -0
- package/rules/default-value-mismatch.yaml +79 -0
- package/rules/defined-term-form.yaml +9 -7
- package/rules/deprecated-option-used.yaml +78 -0
- package/rules/doubled-nado.yaml +28 -12
- package/rules/due-before-issue.yaml +68 -0
- package/rules/duplicate-definition.yaml +2 -2
- package/rules/duration-mismatch.yaml +12 -4
- package/rules/heading-echo.yaml +2 -2
- package/rules/hyphen-as-dash.yaml +2 -2
- package/rules/kana-function-word.yaml +58 -0
- package/rules/latin-spacing.yaml +6 -5
- package/rules/line-amount-mismatch.yaml +58 -0
- package/rules/nado-closed-list.yaml +77 -0
- package/rules/name-variant.yaml +14 -2
- package/rules/number-word-figure-mismatch.yaml +76 -0
- package/rules/numbering-gap.yaml +2 -2
- package/rules/obligation-without-deadline.yaml +95 -0
- package/rules/one-sentence-paragraph-run.yaml +2 -3
- package/rules/parameter-table-mismatch.yaml +90 -0
- package/rules/percent-sum-mismatch.yaml +2 -2
- package/rules/phone-number-variant.yaml +68 -0
- package/rules/prerequisite-after-step.yaml +78 -0
- package/rules/quote-unnamed-speaker.yaml +67 -0
- package/rules/quote-without-source.yaml +6 -6
- package/rules/requirement-smell.yaml +3 -3
- package/rules/sentence-initial-conjunction-run.yaml +13 -7
- package/rules/summary-fact-mismatch.yaml +4 -4
- package/rules/tax-mismatch.yaml +71 -0
- package/rules/time-order.yaml +65 -0
- package/rules/title-length.yaml +2 -2
- package/rules/ui-label-variant.yaml +70 -0
- package/rules/unbalanced-bracket.yaml +4 -4
- package/rules/uncomparable-graded.yaml +29 -10
- package/rules/undefined-function-call.yaml +77 -0
- package/rules/undefined-term.yaml +72 -0
- package/rules/unknown-word.yaml +2 -2
- package/rules/unqualified-superlative.yaml +2 -2
- package/rules/use-before-definition.yaml +2 -2
- package/rules/version-mismatch.yaml +12 -4
- package/rules/version-order.yaml +85 -0
- package/rules/very-adjective.yaml +31 -13
- package/rules/warning-without-action.yaml +64 -0
- package/rules/wordy-phrase.yaml +27 -9
- package/src/ai-score/of-document.ts +19 -9
- package/src/ai-score/render.ts +24 -4
- package/src/ai-score/score.ts +24 -3
- package/src/ai-score/signals.ts +12 -2
- package/src/ai-score/text.ts +7 -2
- package/src/announced-count.ts +19 -12
- package/src/check-source.ts +11 -2
- package/src/cli-text.ts +38 -16
- package/src/cli.ts +2 -1
- package/src/commands/cite-claims.ts +103 -0
- package/src/commands/cite-page.ts +61 -0
- package/src/commands/cite-scaffold.ts +27 -0
- package/src/commands/cite.ts +127 -58
- package/src/company-names.ts +202 -0
- package/src/default-values.ts +158 -0
- package/src/deprecated-use.ts +122 -0
- package/src/derived/stays.ts +145 -0
- package/src/detectors/acronym-context.ts +10 -2
- package/src/detectors/address-word.ts +9 -0
- package/src/detectors/agreement-slip.ts +7 -1
- package/src/detectors/ai-phrasing.ts +6 -1
- package/src/detectors/amount-range.ts +54 -0
- package/src/detectors/amount-scale.ts +50 -17
- package/src/detectors/announced-count.ts +29 -11
- package/src/detectors/bare-comparative.ts +7 -2
- package/src/detectors/block-quotation.ts +95 -0
- package/src/detectors/bracket-label.ts +58 -0
- package/src/detectors/citation-entry.ts +20 -5
- package/src/detectors/code-before.ts +14 -0
- package/src/detectors/connective-hierarchy.ts +39 -11
- package/src/detectors/currency-notation.ts +2 -1
- package/src/detectors/date-outside-period.ts +38 -0
- package/src/detectors/default-values.ts +17 -0
- package/src/detectors/defined-term-form.ts +84 -15
- package/src/detectors/definition-use.ts +10 -2
- package/src/detectors/deprecated-use.ts +17 -0
- package/src/detectors/derived-numbers.ts +106 -15
- package/src/detectors/document-shape.ts +6 -1
- package/src/detectors/due-date.ts +47 -0
- package/src/detectors/en-shape.ts +27 -11
- package/src/detectors/fact-consistency.ts +95 -3
- package/src/detectors/heading-echo.ts +11 -1
- package/src/detectors/kana-function-word.ts +71 -0
- package/src/detectors/line-amount.ts +33 -0
- package/src/detectors/location-pointer.ts +30 -0
- package/src/detectors/mark-shape.ts +18 -1
- package/src/detectors/nado-closed-list.ts +25 -0
- package/src/detectors/name-variant.ts +106 -13
- package/src/detectors/next-word.ts +56 -9
- package/src/detectors/number-word-figure.ts +43 -0
- package/src/detectors/obligation-without-deadline.ts +192 -0
- package/src/detectors/open-end-names.ts +140 -0
- package/src/detectors/ordinal-run-gaps.ts +101 -0
- package/src/detectors/orthographic-variant.ts +39 -14
- package/src/detectors/orthography.ts +6 -1
- package/src/detectors/parameter-table.ts +17 -0
- package/src/detectors/phone-number-variant.ts +18 -0
- package/src/detectors/prerequisite-order.ts +35 -0
- package/src/detectors/quote-unnamed-speaker.ts +19 -0
- package/src/detectors/quote-without-source.ts +57 -10
- package/src/detectors/registry/amount-range.ts +4 -0
- package/src/detectors/registry/arrival-before-departure.ts +4 -0
- package/src/detectors/registry/date-outside-period.ts +4 -0
- package/src/detectors/registry/default-values.ts +4 -0
- package/src/detectors/registry/deprecated-use.ts +4 -0
- package/src/detectors/registry/due-date.ts +4 -0
- package/src/detectors/registry/kana-function-word.ts +4 -0
- package/src/detectors/registry/line-amount.ts +4 -0
- package/src/detectors/registry/nado-closed-list.ts +4 -0
- package/src/detectors/registry/number-word-figure.ts +4 -0
- package/src/detectors/registry/obligation-without-deadline.ts +4 -0
- package/src/detectors/registry/parameter-table.ts +4 -0
- package/src/detectors/registry/phone-number-variant.ts +4 -0
- package/src/detectors/registry/prerequisite-order.ts +4 -0
- package/src/detectors/registry/quote-unnamed-speaker.ts +4 -0
- package/src/detectors/registry/tax-amount.ts +4 -0
- package/src/detectors/registry/time-order.ts +4 -0
- package/src/detectors/registry/ui-label.ts +4 -0
- package/src/detectors/registry/undefined-call.ts +4 -0
- package/src/detectors/registry/undefined-term.ts +4 -0
- package/src/detectors/registry/version-order.ts +4 -0
- package/src/detectors/registry/warning-action.ts +4 -0
- package/src/detectors/requirement-smell.ts +29 -9
- package/src/detectors/structure-tree.ts +43 -21
- package/src/detectors/superlative-scope.ts +13 -1
- package/src/detectors/tax-amount.ts +25 -0
- package/src/detectors/technical-docs.ts +7 -1
- package/src/detectors/term-extension.ts +67 -0
- package/src/detectors/time-order.ts +49 -0
- package/src/detectors/ui-label.ts +17 -0
- package/src/detectors/unbalanced-bracket.ts +7 -14
- package/src/detectors/undefined-call.ts +19 -0
- package/src/detectors/undefined-term.ts +103 -0
- package/src/detectors/unknown-word.ts +3 -3
- package/src/detectors/vague-deadline.ts +3 -3
- package/src/detectors/version-mismatch.ts +26 -5
- package/src/detectors/version-order.ts +50 -0
- package/src/detectors/warning-action.ts +49 -0
- package/src/facts/condition-pairs.ts +289 -0
- package/src/facts/event-dates.ts +63 -0
- package/src/facts/fact-scope.ts +6 -0
- package/src/facts/labelled-facts.ts +13 -1
- package/src/facts/table-facts.ts +3 -3
- package/src/grade/ai-score.ts +1 -1
- package/src/grade/text.ts +2 -2
- package/src/heading-numbering.ts +2 -2
- package/src/html/fetch-page.ts +64 -0
- package/src/html/fetched-text.ts +32 -0
- package/src/html/html-content-block.ts +107 -0
- package/src/html/html-elements.ts +127 -0
- package/src/html/html-footnote-marks.ts +20 -0
- package/src/html/html-heading-links.ts +93 -0
- package/src/html/html-lost-tags.ts +14 -0
- package/src/html/html-markdown.ts +481 -0
- package/src/html/html-preformatted.ts +110 -0
- package/src/html/html-reader-only.ts +82 -0
- package/src/html/html-run-in-headings.ts +43 -0
- package/src/html/html-tables.ts +76 -0
- package/src/html/html-widgets.ts +114 -0
- package/src/html/markup-text.ts +35 -0
- package/src/html/page-document.ts +22 -0
- package/src/inline-count.ts +146 -0
- package/src/kana-spelling.ts +7 -0
- package/src/location-part.ts +30 -0
- package/src/nado-closed-list.ts +106 -0
- package/src/name-cue.ts +35 -0
- package/src/name-variants.ts +57 -11
- package/src/paragraph-runs.ts +12 -2
- package/src/parameter-table.ts +208 -0
- package/src/phone-numbers.ts +98 -0
- package/src/place-names.ts +248 -0
- package/src/plugin.ts +4 -0
- package/src/prerequisite-order.ts +39 -0
- package/src/profile/parse.ts +10 -1
- package/src/reasons.ts +4 -0
- package/src/render/rules-json.ts +4 -0
- package/src/render/rules-table.ts +6 -3
- package/src/rule-genres.ts +5 -2
- package/src/rule-load.ts +3 -2
- package/src/run.ts +3 -1
- package/src/spelling.ts +8 -0
- package/src/structure/action-due.ts +179 -0
- package/src/structure/amount-range.ts +219 -0
- package/src/structure/amount-scale.ts +18 -0
- package/src/structure/cite.ts +21 -2
- package/src/structure/counted-amounts.ts +42 -0
- package/src/structure/date-order.ts +72 -22
- package/src/structure/date-outside-period.ts +127 -0
- package/src/structure/definition-use.ts +24 -3
- package/src/structure/due-date.ts +46 -0
- package/src/structure/heading-runs.ts +24 -0
- package/src/structure/install-pin.ts +115 -0
- package/src/structure/leg-times.ts +198 -0
- package/src/structure/line-amount-unit.ts +35 -0
- package/src/structure/line-amount.ts +162 -0
- package/src/structure/number-word-figure.ts +199 -0
- package/src/structure/numbering.ts +3 -0
- package/src/structure/ordinal-runs.ts +107 -0
- package/src/structure/percent-sum-prose.ts +46 -3
- package/src/structure/percent-sum.ts +16 -2
- package/src/structure/release-list.ts +69 -0
- package/src/structure/share-column.ts +25 -0
- package/src/structure/stated-period.ts +161 -0
- package/src/structure/tax.ts +114 -0
- package/src/structure/time-marks.ts +127 -0
- package/src/structure/time-order.ts +140 -0
- package/src/structure/title-lines.ts +33 -0
- package/src/structure/total.ts +5 -1
- package/src/structure/version-mismatch.ts +67 -13
- package/src/structure/version-order.ts +84 -0
- package/src/table-text.ts +39 -0
- package/src/ui-labels.ts +55 -0
- package/src/undefined-call.ts +65 -0
- package/src/unnamed-speaker.ts +224 -0
- package/src/warning-action.ts +73 -0
- package/styles/koyobun.yaml +7 -4
|
@@ -0,0 +1,162 @@
|
|
|
1
|
+
import type { StructureIssue } from "./issues.ts";
|
|
2
|
+
import { linesOf, type Line } from "./lines.ts";
|
|
3
|
+
import { CELL_SEPARATOR } from "./bare-numbers.ts";
|
|
4
|
+
import { TABLE_RULE } from "./runs.ts";
|
|
5
|
+
import { roundedMatches } from "./tax.ts";
|
|
6
|
+
import { perUnitPrice, quantityUnit, unitsAgree, type UnitWord } from "./line-amount-unit.ts";
|
|
7
|
+
|
|
8
|
+
/**
|
|
9
|
+
* 明細の表で、数量 × 単価が金額と合わない行。見出しの行から数量・単価・金額の列を語(quantity-column、unit-price-column、
|
|
10
|
+
* line-amount-column)で見つけ、本体の行ごとに数量の升の頭の数と単価の升の数を掛け、金額の升の数と比べる。
|
|
11
|
+
* 単価と金額は、数の前後に書いた印($、円、万円)が同じときだけ比べる。端数は切り捨て・四捨五入・切り上げのどれでもよい。
|
|
12
|
+
* 単価が何かあたり($100/hour、月額、Rate の列)なら、数量がその単位か単位の無い数のときだけ比べる。Pure.
|
|
13
|
+
*/
|
|
14
|
+
export type LineAmountWords = {
|
|
15
|
+
readonly quantity: readonly string[];
|
|
16
|
+
readonly unitPrice: readonly string[];
|
|
17
|
+
readonly amount: readonly string[];
|
|
18
|
+
/** Unit words of a quantity (rate-unit). */
|
|
19
|
+
readonly units: readonly UnitWord[];
|
|
20
|
+
/** Marks saying a price is per a unit (per-unit-mark). */
|
|
21
|
+
readonly perUnitMarks: readonly UnitWord[];
|
|
22
|
+
/** Column headings that say the unit of their column (Hours, Rate). */
|
|
23
|
+
readonly headerUnits: readonly UnitWord[];
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
type Cell = { readonly start: number; readonly text: string };
|
|
27
|
+
|
|
28
|
+
/** A number with what is written before and after it in one cell: "$1,500.00" is $ 1500 "", "15万円" is "" 15 万円. */
|
|
29
|
+
type CellNumber = {
|
|
30
|
+
readonly before: string;
|
|
31
|
+
readonly value: number;
|
|
32
|
+
readonly after: string;
|
|
33
|
+
readonly offset: number;
|
|
34
|
+
readonly written: string;
|
|
35
|
+
readonly grouped: boolean;
|
|
36
|
+
readonly decimals: number;
|
|
37
|
+
};
|
|
38
|
+
|
|
39
|
+
const CENTS = 100;
|
|
40
|
+
const ONE_NUMBER = /^([^\d]*?)(\d{1,3}(?:,\d{3})+|\d+)(\.\d+)?([^\d]*)$/u;
|
|
41
|
+
const LEADING_NUMBER = /^(\d{1,3}(?:,\d{3})+|\d+)(\.\d+)?(?![\d,])/u;
|
|
42
|
+
const NEGATIVE = /[-−▲△((]/u;
|
|
43
|
+
|
|
44
|
+
const cellsOf = (line: Line): Cell[] => {
|
|
45
|
+
const bounds = [-1, ...[...line.text.matchAll(CELL_SEPARATOR)].map((match) => match.index), line.text.length];
|
|
46
|
+
const cells = bounds.slice(1).map((end, index) => {
|
|
47
|
+
const from = (bounds[index] ?? 0) + 1;
|
|
48
|
+
return { start: line.start + from, text: line.text.slice(from, end) };
|
|
49
|
+
});
|
|
50
|
+
const trimmed = line.text.trim();
|
|
51
|
+
return cells.slice(trimmed.startsWith("|") ? 1 : 0, trimmed.endsWith("|") ? cells.length - 1 : cells.length);
|
|
52
|
+
};
|
|
53
|
+
|
|
54
|
+
const plain = (text: string): string => text.normalize("NFKC").replace(/[*_`]/gu, "").trim();
|
|
55
|
+
|
|
56
|
+
/** The one number of a price cell with its marks, undefined when the cell holds none, more, or a negative one. */
|
|
57
|
+
export const cellNumber = (cell: Cell): CellNumber | undefined => {
|
|
58
|
+
const text = plain(cell.text);
|
|
59
|
+
const match = ONE_NUMBER.exec(text);
|
|
60
|
+
if (match === null) return undefined;
|
|
61
|
+
const [, before = "", whole = "", fraction = "", after = ""] = match;
|
|
62
|
+
if (NEGATIVE.test(before) || NEGATIVE.test(after)) return undefined;
|
|
63
|
+
return {
|
|
64
|
+
before: before.trim(),
|
|
65
|
+
value: Number(`${whole.replaceAll(",", "")}${fraction}`),
|
|
66
|
+
after: after.trim(),
|
|
67
|
+
offset: cell.start + (cell.text.length - cell.text.trimStart().length),
|
|
68
|
+
written: text,
|
|
69
|
+
grouped: whole.includes(","),
|
|
70
|
+
decimals: Math.max(0, fraction.length - 1),
|
|
71
|
+
};
|
|
72
|
+
};
|
|
73
|
+
|
|
74
|
+
/** The number a quantity cell starts with ("4", "3人日", "2.5 hours"), undefined when it does not, or holds another ("2 x 3"). */
|
|
75
|
+
export const quantityOf = (cell: Cell): number | undefined => {
|
|
76
|
+
const text = plain(cell.text);
|
|
77
|
+
const match = LEADING_NUMBER.exec(text);
|
|
78
|
+
if (match === null || /\d/u.test(text.slice(match[0].length))) return undefined;
|
|
79
|
+
return Number(`${(match[1] ?? "").replaceAll(",", "")}${match[2] ?? ""}`);
|
|
80
|
+
};
|
|
81
|
+
|
|
82
|
+
/** What a quantity cell writes after its number ("days" in "2 days"). */
|
|
83
|
+
const quantityWord = (cell: Cell): string => plain(cell.text).replace(LEADING_NUMBER, "").trim();
|
|
84
|
+
|
|
85
|
+
const columnNamed = (header: readonly Cell[], names: readonly string[]): number => {
|
|
86
|
+
const wanted = names.map((name) => name.toLowerCase());
|
|
87
|
+
return header.findIndex((cell) => wanted.includes(plain(cell.text).toLowerCase()));
|
|
88
|
+
};
|
|
89
|
+
|
|
90
|
+
type Columns = { readonly quantity: number; readonly unitPrice: number; readonly amount: number };
|
|
91
|
+
|
|
92
|
+
/** A table's columns, and the units its quantity and price headings say (undefined when they say none). */
|
|
93
|
+
type Table = { readonly columns: Columns; readonly quantityUnit: string | undefined; readonly priceUnit: string | undefined };
|
|
94
|
+
|
|
95
|
+
const headerUnit = (cell: Cell | undefined, words: LineAmountWords): string | undefined =>
|
|
96
|
+
cell === undefined ? undefined : words.headerUnits.find((word) => word.pattern.toLowerCase() === plain(cell.text).toLowerCase())?.unit;
|
|
97
|
+
|
|
98
|
+
const tableOf = (header: readonly Cell[], words: LineAmountWords): Table | undefined => {
|
|
99
|
+
const columns = { quantity: columnNamed(header, words.quantity), unitPrice: columnNamed(header, words.unitPrice), amount: columnNamed(header, words.amount) };
|
|
100
|
+
if (Object.values(columns).some((index) => index < 0) || new Set(Object.values(columns)).size < 3) return undefined;
|
|
101
|
+
return { columns, quantityUnit: headerUnit(header[columns.quantity], words), priceUnit: headerUnit(header[columns.unitPrice], words) };
|
|
102
|
+
};
|
|
103
|
+
|
|
104
|
+
/** The unit the quantity cell counts: its own word, else its heading's ("Hours"). */
|
|
105
|
+
const rowQuantityUnit = (cell: Cell, table: Table, words: LineAmountWords): string | undefined => {
|
|
106
|
+
const unit = quantityUnit(quantityWord(cell), words.units);
|
|
107
|
+
return unit === "" && table.quantityUnit !== undefined ? table.quantityUnit : unit;
|
|
108
|
+
};
|
|
109
|
+
|
|
110
|
+
/** quantity × price, written the way the amount cell writes its number (grouping, decimals, marks). */
|
|
111
|
+
const shownExpected = (amount: CellNumber, exactCents: number): string => {
|
|
112
|
+
const exact = exactCents / CENTS;
|
|
113
|
+
const decimals = Number.isInteger(Math.round(exact * CENTS) / CENTS) && amount.decimals === 0 ? 0 : Math.max(amount.decimals, 2);
|
|
114
|
+
const number = exact.toLocaleString("en-US", { minimumFractionDigits: decimals, maximumFractionDigits: decimals, useGrouping: amount.grouped });
|
|
115
|
+
return `${amount.before}${number}${amount.after}`;
|
|
116
|
+
};
|
|
117
|
+
|
|
118
|
+
/** Another cell than the item name with a number in it (a discount, a tax rate): the amount may not be quantity × price alone. */
|
|
119
|
+
const hasOtherNumber = (cells: readonly Cell[], columns: Columns): boolean =>
|
|
120
|
+
cells.some((cell, index) => index > 0 && !Object.values(columns).includes(index) && /\d/u.test(plain(cell.text)));
|
|
121
|
+
|
|
122
|
+
const rowIssue = (row: Line, table: Table, words: LineAmountWords): StructureIssue[] => {
|
|
123
|
+
const { columns } = table;
|
|
124
|
+
const cells = cellsOf(row);
|
|
125
|
+
if (hasOtherNumber(cells, columns)) return [];
|
|
126
|
+
const quantityCell = cells[columns.quantity];
|
|
127
|
+
const priceCell = cells[columns.unitPrice];
|
|
128
|
+
const amountCell = cells[columns.amount];
|
|
129
|
+
if (quantityCell === undefined || priceCell === undefined || amountCell === undefined) return [];
|
|
130
|
+
const quantity = quantityOf(quantityCell);
|
|
131
|
+
const price = cellNumber(priceCell);
|
|
132
|
+
const amount = cellNumber(amountCell);
|
|
133
|
+
if (quantity === undefined || price === undefined || amount === undefined) return [];
|
|
134
|
+
const perUnit = perUnitPrice(price.before, price.after, words.perUnitMarks);
|
|
135
|
+
const marks = perUnit ?? price;
|
|
136
|
+
if (marks.before !== amount.before || marks.after !== amount.after) return [];
|
|
137
|
+
if (!unitsAgree(rowQuantityUnit(quantityCell, table, words), perUnit?.unit ?? table.priceUnit)) return [];
|
|
138
|
+
const exactCents = quantity * price.value * CENTS;
|
|
139
|
+
if (roundedMatches(Math.round(amount.value * CENTS), exactCents, amount.decimals === 0)) return [];
|
|
140
|
+
return [
|
|
141
|
+
{
|
|
142
|
+
offset: amount.offset,
|
|
143
|
+
values: { written: amount.written, quantity: plain(quantityCell.text), price: price.written, expected: shownExpected(amount, exactCents) },
|
|
144
|
+
},
|
|
145
|
+
];
|
|
146
|
+
};
|
|
147
|
+
|
|
148
|
+
/** Each table: its header row and its body rows. */
|
|
149
|
+
const tablesOf = (lines: readonly Line[]): { header: Line; rows: Line[] }[] =>
|
|
150
|
+
lines.flatMap((line, index) => {
|
|
151
|
+
const header = lines[index - 1];
|
|
152
|
+
if (!TABLE_RULE.test(line.text) || header === undefined || !header.text.includes("|")) return [];
|
|
153
|
+
const after = lines.slice(index + 1);
|
|
154
|
+
const end = after.findIndex((row) => !row.text.includes("|"));
|
|
155
|
+
return [{ header, rows: end === -1 ? after : after.slice(0, end) }];
|
|
156
|
+
});
|
|
157
|
+
|
|
158
|
+
export const lineAmountMismatches = (source: string, words: LineAmountWords): StructureIssue[] =>
|
|
159
|
+
tablesOf(linesOf(source)).flatMap(({ header, rows }) => {
|
|
160
|
+
const table = tableOf(cellsOf(header), words);
|
|
161
|
+
return table === undefined ? [] : rows.flatMap((row) => rowIssue(row, table, words));
|
|
162
|
+
});
|
|
@@ -0,0 +1,199 @@
|
|
|
1
|
+
// number-word-figure-mismatch: the reading half. A number written in words and then in figures in brackets ("six (7)
|
|
2
|
+
// months", 「金参拾万円(30,000円)」) is read on both sides; the words come from the lexicon number-word, the marks that may
|
|
3
|
+
// stand around the figure from currency-notation and amount-multiplier.
|
|
4
|
+
|
|
5
|
+
export type NumberWordKind = "digit" | "place" | "scale" | "joiner" | "lead" | "unit";
|
|
6
|
+
|
|
7
|
+
export type NumberWord = { readonly word: string; readonly kind: NumberWordKind; readonly value: number };
|
|
8
|
+
|
|
9
|
+
/** What the scan needs: the number words, the marks that may stand before or after the figure, and the words of scale. */
|
|
10
|
+
export type NumberVocabulary = {
|
|
11
|
+
readonly words: readonly NumberWord[];
|
|
12
|
+
readonly marksBefore: readonly string[];
|
|
13
|
+
readonly marksAfter: readonly string[];
|
|
14
|
+
readonly multipliers: readonly { readonly word: string; readonly value: number }[];
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
export type WordFigureSlip = { readonly offset: number; readonly end: number; readonly written: string; readonly words: number; readonly figure: number };
|
|
18
|
+
|
|
19
|
+
type Reading = {
|
|
20
|
+
readonly done: number;
|
|
21
|
+
readonly total: number;
|
|
22
|
+
readonly current: number;
|
|
23
|
+
readonly hasCurrent: boolean;
|
|
24
|
+
readonly lastPlace: number;
|
|
25
|
+
readonly lastScale: number;
|
|
26
|
+
};
|
|
27
|
+
|
|
28
|
+
const START: Reading = { done: 0, total: 0, current: 0, hasCurrent: false, lastPlace: Infinity, lastScale: Infinity };
|
|
29
|
+
const TENS_MIN = 20;
|
|
30
|
+
const TENS_MAX = 90;
|
|
31
|
+
const TEN = 10;
|
|
32
|
+
|
|
33
|
+
/** "twenty" then "one" is 21; any other digit after a digit ("five five", 二〇) is not one number. */
|
|
34
|
+
const joinsDigit = (reading: Reading, value: number): boolean =>
|
|
35
|
+
!reading.hasCurrent || (reading.current >= TENS_MIN && reading.current <= TENS_MAX && reading.current % TEN === 0 && value > 0 && value < TEN);
|
|
36
|
+
|
|
37
|
+
const stepWord = (reading: Reading | undefined, word: NumberWord): Reading | undefined => {
|
|
38
|
+
if (reading === undefined) return undefined;
|
|
39
|
+
if (word.kind === "digit") return joinsDigit(reading, word.value) ? { ...reading, current: reading.current + word.value, hasCurrent: true } : undefined;
|
|
40
|
+
if (word.kind === "place") {
|
|
41
|
+
if (word.value >= reading.lastPlace) return undefined;
|
|
42
|
+
return { ...reading, total: reading.total + (reading.hasCurrent ? reading.current : 1) * word.value, current: 0, hasCurrent: false, lastPlace: word.value };
|
|
43
|
+
}
|
|
44
|
+
const group = reading.total + reading.current;
|
|
45
|
+
if (word.kind !== "scale" || word.value >= reading.lastScale || (group === 0 && !reading.hasCurrent)) return undefined;
|
|
46
|
+
return { ...START, done: reading.done + group * word.value, lastScale: word.value };
|
|
47
|
+
};
|
|
48
|
+
|
|
49
|
+
const CLOSES_GROUP: ReadonlySet<NumberWordKind> = new Set(["place", "scale"]);
|
|
50
|
+
|
|
51
|
+
/** Whether each joiner ("and") stands after a place or scale and before a digit: one hundred and five, not one and hundred. */
|
|
52
|
+
const joinersInside = (words: readonly NumberWord[]): boolean =>
|
|
53
|
+
words.every((word, index) => word.kind !== "joiner" || (CLOSES_GROUP.has(words[index - 1]?.kind ?? "joiner") && words[index + 1]?.kind === "digit"));
|
|
54
|
+
|
|
55
|
+
/**
|
|
56
|
+
* The value of a number written in words, read left to right: digits add, a place multiplies the digits before it (five
|
|
57
|
+
* hundred, 三千), a scale multiplies everything before it (fifty thousand, 参拾万). undefined when the words are not one
|
|
58
|
+
* well-formed number: empty, starting with a scale, a digit after a digit, places or scales out of order.
|
|
59
|
+
*/
|
|
60
|
+
export const numberOfWords = (words: readonly NumberWord[]): number | undefined => {
|
|
61
|
+
if (words.length === 0 || words[0]?.kind === "scale" || !joinersInside(words)) return undefined;
|
|
62
|
+
const reading = words.filter((word) => word.kind !== "joiner").reduce<Reading | undefined>(stepWord, START);
|
|
63
|
+
return reading === undefined ? undefined : reading.done + reading.total + reading.current;
|
|
64
|
+
};
|
|
65
|
+
|
|
66
|
+
const FULLWIDTH_ZERO = 0xff10;
|
|
67
|
+
const halfWidth = (text: string): string =>
|
|
68
|
+
text
|
|
69
|
+
.replace(/[0-9]/gu, (char) => String(char.charCodeAt(0) - FULLWIDTH_ZERO))
|
|
70
|
+
.replace(/./gu, ".")
|
|
71
|
+
.replace(/,/gu, ",");
|
|
72
|
+
|
|
73
|
+
const FIGURE = /^(?:\d{1,3}(?:,\d{3})+|\d+)(?:\.\d+)?/u;
|
|
74
|
+
|
|
75
|
+
/** The longest of the words the text starts with, compared without regard to case. */
|
|
76
|
+
const leadingWord = (text: string, words: readonly string[]): string =>
|
|
77
|
+
words
|
|
78
|
+
.filter((word) => word !== "" && text.toLowerCase().startsWith(word.toLowerCase()))
|
|
79
|
+
.reduce((longest, word) => (word.length > longest.length ? word : longest), "");
|
|
80
|
+
|
|
81
|
+
/**
|
|
82
|
+
* The value of a figure in brackets: digits with separators, a currency mark before ($5,000) or after (300,000円), a word of
|
|
83
|
+
* scale ($5 million), a unit after (5%). undefined when the bracket holds anything else (Section 6, a name, a date).
|
|
84
|
+
*/
|
|
85
|
+
export const figureValue = (content: string, vocabulary: NumberVocabulary): number | undefined => {
|
|
86
|
+
const trimmed = halfWidth(content).trim();
|
|
87
|
+
const afterMark = trimmed.slice(leadingWord(trimmed, vocabulary.marksBefore).length).trimStart();
|
|
88
|
+
const figure = FIGURE.exec(afterMark)?.[0];
|
|
89
|
+
if (figure === undefined) return undefined;
|
|
90
|
+
const rest = afterMark.slice(figure.length).trimStart();
|
|
91
|
+
const multiplier = leadingWord(
|
|
92
|
+
rest,
|
|
93
|
+
vocabulary.multipliers.map((entry) => entry.word),
|
|
94
|
+
);
|
|
95
|
+
const tail = rest.slice(multiplier.length).trimStart();
|
|
96
|
+
if (tail.slice(leadingWord(tail, vocabulary.marksAfter).length).trim() !== "") return undefined;
|
|
97
|
+
const scale = vocabulary.multipliers.find((entry) => entry.word === multiplier)?.value ?? 1;
|
|
98
|
+
return Number(figure.replace(/,/gu, "")) * scale;
|
|
99
|
+
};
|
|
100
|
+
|
|
101
|
+
const BRACKET = /[((]([^()()\n]{1,40})[))]/gu;
|
|
102
|
+
const SEPARATOR = " \t-";
|
|
103
|
+
const SPACE = " \t";
|
|
104
|
+
/** How far back spaces are skipped, and how many words one number in words may have (one million two hundred and five is six). */
|
|
105
|
+
const SKIP_REACH = 40;
|
|
106
|
+
const MAX_RUN_WORDS = 16;
|
|
107
|
+
const RUN_KINDS: ReadonlySet<NumberWordKind> = new Set(["digit", "place", "scale", "joiner"]);
|
|
108
|
+
const SCRIPTS = [/\p{Script=Han}/u, /\p{Script=Latin}/u, /\p{Script=Hiragana}/u, /\p{Script=Katakana}/u, /\p{Script=Cyrillic}/u, /\p{Script=Greek}/u];
|
|
109
|
+
|
|
110
|
+
/** Whether two letters are of one script: 統 before 一 makes one word (統一), は before 三 does not. */
|
|
111
|
+
const sameScript = (a: string, b: string): boolean => SCRIPTS.some((script) => script.test(a) && script.test(b));
|
|
112
|
+
|
|
113
|
+
/** The longest of the words the text ends with at `end`, compared without regard to case. */
|
|
114
|
+
const endingWord = <T extends { readonly word: string }>(text: string, end: number, words: readonly T[]): T | undefined =>
|
|
115
|
+
words
|
|
116
|
+
.filter((entry) => entry.word !== "" && text.slice(Math.max(0, end - entry.word.length), end).toLowerCase() === entry.word.toLowerCase())
|
|
117
|
+
.reduce<T | undefined>((longest, entry) => (longest === undefined || entry.word.length > longest.word.length ? entry : longest), undefined);
|
|
118
|
+
|
|
119
|
+
/** Where the run of `chars` (spaces, hyphens) that ends at `end` starts, looking back no further than SKIP_REACH. */
|
|
120
|
+
const skipBack = (text: string, end: number, chars: string): number => {
|
|
121
|
+
const window = text.slice(Math.max(0, end - SKIP_REACH), end).split("");
|
|
122
|
+
const lastOther = window.findLastIndex((char) => !chars.includes(char));
|
|
123
|
+
return end - (window.length - (lastOther + 1));
|
|
124
|
+
};
|
|
125
|
+
|
|
126
|
+
type Placed = { readonly word: NumberWord; readonly start: number };
|
|
127
|
+
|
|
128
|
+
/**
|
|
129
|
+
* The number words that end at `end`, read backwards: the first right at `end`, the others past spaces or hyphens. A run
|
|
130
|
+
* longer than any number in words is not one number, and gives none.
|
|
131
|
+
*/
|
|
132
|
+
const placedBefore = (text: string, end: number, words: readonly NumberWord[], found: readonly Placed[] = []): readonly Placed[] => {
|
|
133
|
+
const from = found.length === 0 ? end : skipBack(text, end, SEPARATOR);
|
|
134
|
+
const word = endingWord(text, from, words);
|
|
135
|
+
if (word === undefined) return found;
|
|
136
|
+
if (found.length >= MAX_RUN_WORDS) return [];
|
|
137
|
+
const start = from - word.word.length;
|
|
138
|
+
return placedBefore(text, start, words, [{ word, start }, ...found]);
|
|
139
|
+
};
|
|
140
|
+
|
|
141
|
+
/** The run of number words before `end`, without the joiners it starts with ("and one" is "one"). */
|
|
142
|
+
const runBefore = (text: string, end: number, words: readonly NumberWord[]): readonly Placed[] => {
|
|
143
|
+
const placed = placedBefore(text, end, words);
|
|
144
|
+
const first = placed.findIndex((entry) => entry.word.kind !== "joiner");
|
|
145
|
+
return first < 0 ? [] : placed.slice(first);
|
|
146
|
+
};
|
|
147
|
+
|
|
148
|
+
/** Numerals written one character to a word and two or more in a row (契約期間十二) are a number even right after a word. */
|
|
149
|
+
const isSolidNumeral = (run: readonly Placed[]): boolean => run.length > 1 && run[0]?.word.word.length === 1;
|
|
150
|
+
|
|
151
|
+
/**
|
|
152
|
+
* Whether the run is a number of its own: the letter before it is of another script, it is a solid numeral, or a lead stands
|
|
153
|
+
* before it (金参, 年五). A single numeral after a word of its script is part of that word (統一, 唯一, often).
|
|
154
|
+
*/
|
|
155
|
+
const startsWord = (text: string, run: readonly Placed[], vocabulary: NumberVocabulary): boolean => {
|
|
156
|
+
const start = run[0]?.start ?? 0;
|
|
157
|
+
const before = text.charAt(start - 1);
|
|
158
|
+
const leads = vocabulary.words.filter((word) => word.kind === "lead");
|
|
159
|
+
return before === "" || !sameScript(before, text.charAt(start)) || isSolidNumeral(run) || endingWord(text, start, leads) !== undefined;
|
|
160
|
+
};
|
|
161
|
+
|
|
162
|
+
const YEAR = /^\s*[12]\d{3}\s*$/u;
|
|
163
|
+
const YEAR_WORDS_BELOW = 1000;
|
|
164
|
+
|
|
165
|
+
/** A bare four-digit figure after a small number in words is a year in brackets ("two (2026)"), not the same number again. */
|
|
166
|
+
const isYear = (content: string, words: number): boolean => YEAR.test(halfWidth(content)) && words < YEAR_WORDS_BELOW;
|
|
167
|
+
|
|
168
|
+
/** Where the words before a bracket end: past the spaces and one unit or currency word ("Dollars", 円, percent). */
|
|
169
|
+
const wordsEnd = (text: string, bracket: number, vocabulary: NumberVocabulary): number => {
|
|
170
|
+
const spaced = skipBack(text, bracket, SPACE);
|
|
171
|
+
const unit = endingWord(
|
|
172
|
+
text,
|
|
173
|
+
spaced,
|
|
174
|
+
vocabulary.marksAfter.map((word) => ({ word })),
|
|
175
|
+
);
|
|
176
|
+
return unit === undefined ? spaced : skipBack(text, spaced - unit.word.length, SPACE);
|
|
177
|
+
};
|
|
178
|
+
|
|
179
|
+
const RELATIVE_TOLERANCE = 1e-9;
|
|
180
|
+
const differ = (a: number, b: number): boolean => Math.abs(a - b) > RELATIVE_TOLERANCE * Math.max(1, Math.abs(a), Math.abs(b));
|
|
181
|
+
|
|
182
|
+
const slipAt = (text: string, match: RegExpExecArray, vocabulary: NumberVocabulary, runWords: readonly NumberWord[]): WordFigureSlip | undefined => {
|
|
183
|
+
const content = match[1] ?? "";
|
|
184
|
+
const run = runBefore(text, wordsEnd(text, match.index, vocabulary), runWords);
|
|
185
|
+
const start = run[0]?.start;
|
|
186
|
+
if (start === undefined || !startsWord(text, run, vocabulary)) return undefined;
|
|
187
|
+
const words = numberOfWords(run.map((entry) => entry.word));
|
|
188
|
+
const figure = figureValue(content, vocabulary);
|
|
189
|
+
if (words === undefined || figure === undefined || !differ(words, figure) || isYear(content, words)) return undefined;
|
|
190
|
+
const end = match.index + match[0].length;
|
|
191
|
+
return { offset: start, end, written: text.slice(start, end), words, figure };
|
|
192
|
+
};
|
|
193
|
+
|
|
194
|
+
/** Every number written in words whose figure in brackets right after it says another number. */
|
|
195
|
+
export const wordFigureSlips = (text: string, vocabulary: NumberVocabulary): WordFigureSlip[] => {
|
|
196
|
+
const runWords = vocabulary.words.filter((word) => RUN_KINDS.has(word.kind));
|
|
197
|
+
if (runWords.length === 0) return [];
|
|
198
|
+
return [...text.matchAll(BRACKET)].flatMap((match) => slipAt(text, match, vocabulary, runWords) ?? []);
|
|
199
|
+
};
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import type { StructureNode } from "../plugin.ts";
|
|
2
2
|
import { inDocumentOrder, type StructureIssue } from "./issues.ts";
|
|
3
3
|
import { numbersQuotedInside } from "./quoted-number.ts";
|
|
4
|
+
import { isVersionHistory } from "./version-order.ts";
|
|
4
5
|
|
|
5
6
|
const labelOf = (node: StructureNode): string => String(node.attrs["label"] ?? node.address);
|
|
6
7
|
|
|
@@ -43,11 +44,13 @@ const breaksIn = (sequence: readonly Ordered[]): StructureIssue[] =>
|
|
|
43
44
|
* 文書全体の通し番号として比べると抜けに見える。最初の番号は見ない。日本語の項は 2 から番号を振る。
|
|
44
45
|
* 1 に戻った番号は新しい並びの始まりとして扱うので、「(a) の後の (a)」の重なりは見逃す。
|
|
45
46
|
* 同じ番号の節を中に持つ節(ほかの文書の条を引いた手本の見出し)は、並びに入れない。
|
|
47
|
+
* 変更履歴の版の見出し(## 3.1.0)は番号の並びではない。版の順番は version-order が見る。
|
|
46
48
|
*/
|
|
47
49
|
export const numberingBreaks = (tree: StructureNode): StructureIssue[] => {
|
|
48
50
|
const quoting = numbersQuotedInside(tree);
|
|
49
51
|
return inDocumentOrder(tree)
|
|
50
52
|
.flatMap((parent) => sequencesOf(parent, quoting))
|
|
53
|
+
.filter((sequence) => !isVersionHistory(sequence.map((ordered) => labelOf(ordered.node))))
|
|
51
54
|
.flatMap(breaksIn)
|
|
52
55
|
.toSorted((left, right) => left.offset - right.offset);
|
|
53
56
|
};
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
// The numbered runs a schedule writes as 第N回, 第N週, Week N or Session N (lexicon ordinal-frame), in the first cell of
|
|
2
|
+
// table rows, at the start of list items or at the start of lines, and the places where such a run skips or repeats a
|
|
3
|
+
// number. Pure: the frames come from the lexicon, the leads from the caller.
|
|
4
|
+
import type { Lexicon } from "../plugin.ts";
|
|
5
|
+
import type { StructureIssue } from "./issues.ts";
|
|
6
|
+
|
|
7
|
+
/** One frame of the lexicon: the form with its number, and the form's opening followed by a figure. */
|
|
8
|
+
export type OrdinalFrame = { readonly group: string; readonly written: RegExp; readonly opened: RegExp | undefined };
|
|
9
|
+
|
|
10
|
+
/** A lead that carries a frame: its number (or the first and last of a joined 1-2) as written. */
|
|
11
|
+
export type FramedNumber = { readonly group: string; readonly ordinal: number; readonly last: number; readonly label: string };
|
|
12
|
+
|
|
13
|
+
/** A lead that opens a frame (第2, Week 3) without the form being readable (第2・第3回): it ends the group's run. */
|
|
14
|
+
export type UnreadableFrame = { readonly group: string; readonly unreadable: true };
|
|
15
|
+
|
|
16
|
+
/** Where a lead starts and what it reads as. */
|
|
17
|
+
export type Lead = { readonly offset: number; readonly read: readonly (FramedNumber | UnreadableFrame)[] };
|
|
18
|
+
|
|
19
|
+
const PLACEHOLDER = "{n}";
|
|
20
|
+
const FIGURES = "[0-90-9]{1,3}";
|
|
21
|
+
const JOINER = "[ \\t]?[-–—~〜~・,、][ \\t]?";
|
|
22
|
+
const FOLLOWER = "(?=$|[\\s\\u3000::|((.))\\]\\-–—、,*_])";
|
|
23
|
+
const SPACE = /[ \t\u3000]+/gu;
|
|
24
|
+
const FULLWIDTH_ZERO = 0xff10;
|
|
25
|
+
|
|
26
|
+
const escaped = (text: string): string => text.replace(/[.*+?^${}()|[\]\\]/gu, "\\$&").replace(SPACE, "[ \\t\\u3000]*");
|
|
27
|
+
|
|
28
|
+
const frameOf = (pattern: string, group: string): OrdinalFrame | undefined => {
|
|
29
|
+
const at = pattern.indexOf(PLACEHOLDER);
|
|
30
|
+
if (at === -1) return undefined;
|
|
31
|
+
const opening = escaped(pattern.slice(0, at));
|
|
32
|
+
const closing = escaped(pattern.slice(at + PLACEHOLDER.length));
|
|
33
|
+
const written = new RegExp(`^${opening}(?<first>${FIGURES})(?:${JOINER}(?<last>${FIGURES}))?${closing}${FOLLOWER}`, "iu");
|
|
34
|
+
return { group, written, opened: opening === "" ? undefined : new RegExp(`^${opening}[0-90-9]`, "iu") };
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
/** The lexicon's frames. An entry without {n} or without a group is not a frame. */
|
|
38
|
+
export const ordinalFramesOf = (lexicon: Lexicon): OrdinalFrame[] =>
|
|
39
|
+
lexicon.flatMap((entry) => {
|
|
40
|
+
const frame = entry.group === undefined ? undefined : frameOf(entry.pattern, entry.group);
|
|
41
|
+
return frame === undefined ? [] : [frame];
|
|
42
|
+
});
|
|
43
|
+
|
|
44
|
+
const figureValue = (figures: string): number =>
|
|
45
|
+
Number([...figures].map((char) => (char >= "0" && char <= "9" ? String(char.charCodeAt(0) - FULLWIDTH_ZERO) : char)).join(""));
|
|
46
|
+
|
|
47
|
+
const readFrame = (lead: string, frame: OrdinalFrame): FramedNumber | UnreadableFrame | undefined => {
|
|
48
|
+
const found = frame.written.exec(lead);
|
|
49
|
+
if (found === null) return frame.opened?.test(lead) === true ? { group: frame.group, unreadable: true } : undefined;
|
|
50
|
+
const ordinal = figureValue(found.groups?.["first"] ?? "");
|
|
51
|
+
const last = found.groups?.["last"];
|
|
52
|
+
return { group: frame.group, ordinal, last: last === undefined ? ordinal : figureValue(last), label: found[0].trim() };
|
|
53
|
+
};
|
|
54
|
+
|
|
55
|
+
/** What the text at the start of a lead reads as, under each frame that matches it. */
|
|
56
|
+
export const framesAt = (lead: string, frames: readonly OrdinalFrame[]): Lead["read"] => {
|
|
57
|
+
const read = frames.flatMap((frame) => readFrame(lead, frame) ?? []);
|
|
58
|
+
const groups = new Set(read.filter((each) => !("unreadable" in each)).map((each) => each.group));
|
|
59
|
+
return read.filter((each) => !("unreadable" in each) || !groups.has(each.group));
|
|
60
|
+
};
|
|
61
|
+
|
|
62
|
+
/** One number of a run, and where its lead starts. */
|
|
63
|
+
export type RunNumber = FramedNumber & { readonly offset: number };
|
|
64
|
+
|
|
65
|
+
/**
|
|
66
|
+
* The leads of one block (one table, one list, one section's lines), cut into runs per group. An unreadable lead ends its
|
|
67
|
+
* group's run, and a number 1 starts a new one (a second term counting again).
|
|
68
|
+
*/
|
|
69
|
+
export const ordinalRuns = (leads: readonly Lead[]): RunNumber[][] => {
|
|
70
|
+
const runs: RunNumber[][] = [];
|
|
71
|
+
const open = new Map<string, RunNumber[]>();
|
|
72
|
+
leads.forEach((lead) =>
|
|
73
|
+
lead.read.forEach((read) => {
|
|
74
|
+
if ("unreadable" in read) {
|
|
75
|
+
open.delete(read.group);
|
|
76
|
+
return;
|
|
77
|
+
}
|
|
78
|
+
const openRun = open.get(read.group) ?? [];
|
|
79
|
+
const run = read.ordinal === 1 && openRun.length > 0 ? [] : openRun;
|
|
80
|
+
if (run.length === 0) runs.push(run);
|
|
81
|
+
open.set(read.group, run);
|
|
82
|
+
run.push({ ...read, offset: lead.offset });
|
|
83
|
+
}),
|
|
84
|
+
);
|
|
85
|
+
return runs;
|
|
86
|
+
};
|
|
87
|
+
|
|
88
|
+
/** A run shorter than this is too short to tell a numbering from a mention. */
|
|
89
|
+
const SHORTEST_RUN = 3;
|
|
90
|
+
|
|
91
|
+
const followsOn = (current: FramedNumber, previous: FramedNumber): boolean => current.ordinal === previous.last + 1;
|
|
92
|
+
|
|
93
|
+
/**
|
|
94
|
+
* Each number in the run that does not follow the one before it: a skip or a repeat. A run
|
|
95
|
+
* where fewer than half the steps follow on lists chosen numbers (weeks 2, 5, 9), not a sequence, and is not read; so
|
|
96
|
+
* is a run shorter than three, and a run writing one number throughout.
|
|
97
|
+
*/
|
|
98
|
+
export const ordinalRunBreaks = (run: readonly RunNumber[]): StructureIssue[] => {
|
|
99
|
+
if (run.length < SHORTEST_RUN || new Set(run.map((item) => item.ordinal)).size < 2) return [];
|
|
100
|
+
const steps = run.slice(1).map((item, index) => ({ item, previous: run[index] ?? item }));
|
|
101
|
+
const breaks = steps.filter(({ item, previous }) => !followsOn(item, previous));
|
|
102
|
+
if (breaks.length * 2 > steps.length) return [];
|
|
103
|
+
return breaks.map(({ item, previous }) => ({
|
|
104
|
+
offset: item.offset,
|
|
105
|
+
values: { previous: previous.label, label: item.label, expected: previous.last + 1, found: item.ordinal },
|
|
106
|
+
}));
|
|
107
|
+
};
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
// A breakdown written in one sentence (「構成比は、Aが50%、Bが30%、Cが20%」, "By product, A made up 50% of sales, B 30% and
|
|
2
2
|
// C 20%") whose shares do not add up to 100%. The table and list form is structure/percent-sum.ts; the words are the same.
|
|
3
|
+
import { escapeRegExp } from "../orthography.ts";
|
|
3
4
|
import type { Span } from "../plugin.ts";
|
|
4
5
|
import type { StructureIssue } from "./issues.ts";
|
|
5
6
|
import type { Amount } from "./total.ts";
|
|
@@ -35,20 +36,62 @@ const toleranceOf = (source: string, shares: readonly Amount[]): number =>
|
|
|
35
36
|
|
|
36
37
|
const isBroken = (sum: number, tolerance: number): boolean => Math.abs(sum - WHOLE) > tolerance && Math.abs(sum - WHOLE) <= BAND;
|
|
37
38
|
|
|
39
|
+
/** How far before a percentage the word for the rest may stand: 「その他が 」, "and other ". */
|
|
40
|
+
const REST_REACH = 16;
|
|
41
|
+
/** What may stand between the word for the rest and its percentage: a space, a colon, a particle, an opening parenthesis. */
|
|
42
|
+
const REST_GAP = /^[\s::、,がはで((]*$/u;
|
|
43
|
+
const LATIN_START = /^[A-Za-z]/u;
|
|
44
|
+
const LETTER_BEFORE = /\p{L}$/u;
|
|
45
|
+
const LETTER = /\p{L}/u;
|
|
46
|
+
|
|
47
|
+
/** A word in a text; a Latin one as a whole word ("other", not "another"; "up", not "upkeep"). */
|
|
48
|
+
const hasWord = (text: string, word: string): boolean => {
|
|
49
|
+
const lowered = text.toLowerCase();
|
|
50
|
+
const target = word.toLowerCase();
|
|
51
|
+
if (!LATIN_START.test(word)) return lowered.includes(target);
|
|
52
|
+
return [...lowered.matchAll(new RegExp(escapeRegExp(target), "gu"))].some(
|
|
53
|
+
(match) => !LETTER.test(lowered[match.index - 1] ?? "") && !LETTER.test(lowered[match.index + target.length] ?? ""),
|
|
54
|
+
);
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
/** How far from a percentage a word for which way it moved may stand: "grew 45%", 「8%増加」. */
|
|
58
|
+
const CHANGE_REACH = 12;
|
|
59
|
+
|
|
60
|
+
const movesNear = (source: string, sentence: Span, share: Amount, changes: readonly string[]): boolean => {
|
|
61
|
+
const near = source.slice(Math.max(sentence.start, share.offset - CHANGE_REACH), Math.min(sentence.end, share.end + CHANGE_REACH));
|
|
62
|
+
return changes.some((word) => hasWord(near, word));
|
|
63
|
+
};
|
|
64
|
+
|
|
65
|
+
/**
|
|
66
|
+
* The last share is the rest of the whole (その他が 5%, other 5%): only the parts of one whole have a rest, and it is listed
|
|
67
|
+
* last. Percentages next to a word for which way they moved (grew 45%, 8%増加) are changes, whose rest is no part of a whole.
|
|
68
|
+
*/
|
|
69
|
+
const namesRest = (source: string, sentence: Span, shares: readonly Amount[], words: ShareWords): boolean => {
|
|
70
|
+
const last = shares.at(-1);
|
|
71
|
+
if (last === undefined || shares.some((share) => movesNear(source, sentence, share, words.changes ?? []))) return false;
|
|
72
|
+
const before = source.slice(Math.max(sentence.start, last.offset - REST_REACH), last.offset).toLowerCase();
|
|
73
|
+
return (words.rests ?? []).some((word) => {
|
|
74
|
+
const at = before.lastIndexOf(word.toLowerCase());
|
|
75
|
+
if (at < 0 || !REST_GAP.test(before.slice(at + word.length))) return false;
|
|
76
|
+
return !(LATIN_START.test(word) && LETTER_BEFORE.test(before.slice(0, at)));
|
|
77
|
+
});
|
|
78
|
+
};
|
|
79
|
+
|
|
38
80
|
const issueIn = (source: string, sentence: Span, percents: readonly Amount[], words: ShareWords): StructureIssue[] => {
|
|
39
81
|
const text = source.slice(sentence.start, sentence.end);
|
|
40
|
-
if (
|
|
82
|
+
if (includesAny(text, words.exceptions)) return [];
|
|
41
83
|
const shares = percents.filter((amount) => amount.offset >= sentence.start && amount.end <= sentence.end);
|
|
42
84
|
if (shares.length < MIN_PARTS || shares.some((share) => isSigned(source, share))) return [];
|
|
85
|
+
if (!includesAny(text, words.labels) && !namesRest(source, sentence, shares, words)) return [];
|
|
43
86
|
const sum = shares.reduce((total, share) => total + share.value, 0);
|
|
44
87
|
const decimals = Math.max(0, ...shares.map((share) => decimalsOf(source, share)));
|
|
45
88
|
if (!isBroken(sum, toleranceOf(source, shares))) return [];
|
|
46
89
|
return [{ offset: shares[0]?.offset ?? sentence.start, values: { sum: `${sum.toFixed(decimals)}${shares[0]?.unit ?? ""}` } }];
|
|
47
90
|
};
|
|
48
91
|
|
|
49
|
-
/** Each sentence that names a share word and three or more unsigned percentages whose sum misses 100% by more than rounding, and by no more than BAND. */
|
|
92
|
+
/** Each sentence that names a share word (or names one share as the rest) and three or more unsigned percentages whose sum misses 100% by more than rounding, and by no more than BAND. */
|
|
50
93
|
export const proseShareMismatches = (source: string, sentences: readonly Span[], amounts: readonly Amount[], words: ShareWords): StructureIssue[] => {
|
|
51
|
-
if (words.labels.length === 0) return [];
|
|
94
|
+
if (words.labels.length === 0 && (words.rests ?? []).length === 0) return [];
|
|
52
95
|
const percents = amounts.filter((amount) => words.units.includes(amount.unit));
|
|
53
96
|
return sentences.flatMap((sentence) => issueIn(source, sentence, percents, words));
|
|
54
97
|
};
|
|
@@ -3,6 +3,7 @@ import { runsOf, TABLE_ROW, TABLE_RULE, type Line } from "./runs.ts";
|
|
|
3
3
|
import { columnOf, isTotalLabel, type Amount } from "./total.ts";
|
|
4
4
|
import { CELL_SEPARATOR } from "./bare-numbers.ts";
|
|
5
5
|
import { joined, lineAbove, linesAbove } from "../text-above.ts";
|
|
6
|
+
import { isShareColumn, mentionsAny } from "./share-column.ts";
|
|
6
7
|
|
|
7
8
|
/**
|
|
8
9
|
* 一つの全体を分けた割合(構成比、内訳、breakdown)の和が 100% にならない。箇条書きの続いた項目か、表の続いた行の百分率を足す。
|
|
@@ -11,8 +12,16 @@ import { joined, lineAbove, linesAbove } from "../text-above.ts";
|
|
|
11
12
|
*/
|
|
12
13
|
export type ShareWords = {
|
|
13
14
|
readonly labels: readonly string[];
|
|
15
|
+
/** 表の列の見出しの升がその語だけのとき、全体を分けた割合の列と読む語(割合、Weight)。 */
|
|
16
|
+
readonly columnLabels?: readonly string[];
|
|
17
|
+
/** 行ごとの率を名指す語(前年比、達成率、growth)。表の上の文にあれば、columnLabels の列は足さない。 */
|
|
18
|
+
readonly rates?: readonly string[];
|
|
14
19
|
/** 足しても 100% にならない集計(複数回答)。 */
|
|
15
20
|
readonly exceptions: readonly string[];
|
|
21
|
+
/** 全体の残りを名指す語(その他、other)。一つの文の百分率のすぐ前にあれば、その文は内訳。 */
|
|
22
|
+
readonly rests?: readonly string[];
|
|
23
|
+
/** 値の動いた向きの語(伸び、grew)。その文の百分率は変化で、「その他」があっても内訳ではない。 */
|
|
24
|
+
readonly changes?: readonly string[];
|
|
16
25
|
readonly units: readonly string[];
|
|
17
26
|
readonly totalLabels: readonly string[];
|
|
18
27
|
};
|
|
@@ -97,12 +106,13 @@ const tolerance = (shares: readonly Share[]): number => Math.max(1, shares.lengt
|
|
|
97
106
|
/** 和は、項目のいちばん細かい桁で、最初の項目の単位を付けて見せる。 */
|
|
98
107
|
const shownSum = (shares: readonly Share[]): string => `${sumOf(shares).toFixed(decimalsOf(shares))}${shares[0]?.unit ?? ""}`;
|
|
99
108
|
|
|
100
|
-
type Named = { readonly header: readonly string[]; readonly above: string };
|
|
109
|
+
type Named = { readonly header: readonly string[]; readonly above: string; readonly rows: string };
|
|
101
110
|
|
|
102
111
|
/** 列が全体を分けた割合と名指されているか。表は列の見出しか、百分率の列が一つだけの表の上の文。箇条書きは上の文。 */
|
|
103
112
|
const namesShares = (named: Named, column: number, percentColumns: number, words: ShareWords): boolean => {
|
|
104
113
|
const header = named.header[column] ?? "";
|
|
105
114
|
if (named.header.length > 0 && includesAny(header, words.labels)) return true;
|
|
115
|
+
if (isShareColumn(header, words.columnLabels ?? []) && !mentionsAny(`${named.above} ${named.rows}`, words.rates ?? [])) return true;
|
|
106
116
|
return (named.header.length === 0 || percentColumns === 1) && includesAny(named.above, words.labels);
|
|
107
117
|
};
|
|
108
118
|
|
|
@@ -110,7 +120,11 @@ const namesShares = (named: Named, column: number, percentColumns: number, words
|
|
|
110
120
|
const isBreakdown = (source: string, run: readonly Line[], totalLabels: readonly string[]): boolean =>
|
|
111
121
|
run.length >= MIN_PARTS && !run.some((line) => isTotalLabel(source.slice(line.start, line.end), totalLabels));
|
|
112
122
|
|
|
113
|
-
const namingOf = (source: string, run: readonly Line[], first: Line): Named => ({
|
|
123
|
+
const namingOf = (source: string, run: readonly Line[], first: Line): Named => ({
|
|
124
|
+
header: headerCells(source, first),
|
|
125
|
+
above: textAbove(source, run),
|
|
126
|
+
rows: run.map((line) => source.slice(line.start, line.end)).join("\n"),
|
|
127
|
+
});
|
|
114
128
|
|
|
115
129
|
const mismatchesIn = (source: string, run: readonly Line[], percents: readonly Amount[], words: ShareWords): StructureIssue[] => {
|
|
116
130
|
const first = run[0];
|