23 - the block directive's spellings are one file
CI / publish (push) Waiting to run
CI / gate (push) Successful in 39s

This commit was merged in pull request #122.
This commit is contained in:
2026-09-23 23:13:01 +02:00
parent d3a2129967
commit 7be4f59f0b
14 changed files with 43 additions and 45 deletions
+1 -1
View File
@@ -6,7 +6,7 @@ import { readFileSync } from 'node:fs'
import test from 'node:test' import test from 'node:test'
import type { AttributeKind, AttributeVocabulary } from './adf/attribute-vocabulary.ts' import type { AttributeKind, AttributeVocabulary } from './adf/attribute-vocabulary.ts'
import { blockArgument } from './markdown/block-directive-arguments.ts' import { blockArgument } from './markdown/block-directive.ts'
import { blockNodes } from './adf/block-nodes.ts' import { blockNodes } from './adf/block-nodes.ts'
import { inlineNodes } from './adf/inline-nodes.ts' import { inlineNodes } from './adf/inline-nodes.ts'
import { markAttributes } from './adf/mark-attributes.ts' import { markAttributes } from './adf/mark-attributes.ts'
+1 -3
View File
@@ -9,7 +9,7 @@ import type { JsonValue } from './json-value.ts'
import type { Result } from './result.ts' import type { Result } from './result.ts'
import { adfDocument, attributes, jsonKey, jsonValue, markdownPieces, propertyRuns, propertyTimeout, textOf } from './property-harness.ts' import { adfDocument, attributes, jsonKey, jsonValue, markdownPieces, propertyRuns, propertyTimeout, textOf } from './property-harness.ts'
import { adfToMarkdown } from './markdown/emit/adf-to-markdown.ts' import { adfToMarkdown } from './markdown/emit/adf-to-markdown.ts'
import { blockArgument } from './markdown/block-directive-arguments.ts' import { blockArgument, listBreakName, marksAttribute } from './markdown/block-directive.ts'
import { blockNodes } from './adf/block-nodes.ts' import { blockNodes } from './adf/block-nodes.ts'
import { carryName } from './markdown/opaque-carry.ts' import { carryName } from './markdown/opaque-carry.ts'
import { import {
@@ -25,11 +25,9 @@ import {
} from './markdown/directive-syntax.ts' } from './markdown/directive-syntax.ts'
import { fencedCodeBlock } from './markdown/commonmark/backtick-runs.ts' import { fencedCodeBlock } from './markdown/commonmark/backtick-runs.ts'
import { inlineNodes } from './adf/inline-nodes.ts' import { inlineNodes } from './adf/inline-nodes.ts'
import { listBreakName } from './markdown/list-break.ts'
import { markAttributes } from './adf/mark-attributes.ts' import { markAttributes } from './adf/mark-attributes.ts'
import { markSpelling } from './markdown/mark-spellings.ts' import { markSpelling } from './markdown/mark-spellings.ts'
import { markdownToAdf } from './markdown/parse/markdown-to-adf.ts' import { markdownToAdf } from './markdown/parse/markdown-to-adf.ts'
import { marksAttribute } from './markdown/block-directive-marks.ts'
import { nodeContent, nodeMarks } from './adf/document.ts' import { nodeContent, nodeMarks } from './adf/document.ts'
import { serializeCanonicalJson } from './canonical-json.ts' import { serializeCanonicalJson } from './canonical-json.ts'
import { textDirectiveName } from './markdown/text-directive.ts' import { textDirectiveName } from './markdown/text-directive.ts'
-13
View File
@@ -1,13 +0,0 @@
import type { BlockType } from '../adf/block-nodes.ts'
const argumentByType = new Map(
Object.entries({
blockTaskItem: 'state',
panel: 'panelType',
taskItem: 'state',
} satisfies Partial<Record<BlockType, string>>),
)
export function blockArgument(type: string): string | undefined {
return argumentByType.get(type)
}
-9
View File
@@ -1,9 +0,0 @@
import { blockNodeModel } from '../adf/block-nodes.ts'
import { listBreakName } from './list-break.ts'
export function blockDirectiveForm(name: string): 'container' | 'leaf' | undefined {
if (name === listBreakName) return 'leaf'
const model = blockNodeModel(name)
if (model === undefined) return undefined
return model.contentModel === 'none' ? 'leaf' : 'container'
}
@@ -1,10 +1,36 @@
import type { AdfMark } from '../adf/document.ts' import type { AdfMark } from '../adf/document.ts'
import type { BlockType } from '../adf/block-nodes.ts'
import type { JsonValue } from '../json-value.ts' import type { JsonValue } from '../json-value.ts'
import { blockNodeModel } from '../adf/block-nodes.ts'
import { isAdfMark, nodeAttrs } from '../adf/document.ts' import { isAdfMark, nodeAttrs } from '../adf/document.ts'
import { serializeCanonicalJson } from '../canonical-json.ts' import { serializeCanonicalJson } from '../canonical-json.ts'
import { spellDirectiveOpener } from './directive-syntax.ts'
const argumentByType = new Map(
Object.entries({
blockTaskItem: 'state',
panel: 'panelType',
taskItem: 'state',
} satisfies Partial<Record<BlockType, string>>),
)
export const listBreakName = 'listBreak'
export const listBreakSpelling = spellDirectiveOpener(listBreakName, undefined, '')
export const marksAttribute = 'marks' export const marksAttribute = 'marks'
export function blockArgument(type: string): string | undefined {
return argumentByType.get(type)
}
export function blockDirectiveForm(name: string): 'container' | 'leaf' | undefined {
if (name === listBreakName) return 'leaf'
const model = blockNodeModel(name)
if (model === undefined) return undefined
return model.contentModel === 'none' ? 'leaf' : 'container'
}
export function markValues(marks: readonly AdfMark[]): JsonValue { export function markValues(marks: readonly AdfMark[]): JsonValue {
return marks.map((mark) => { return marks.map((mark) => {
const attrs = nodeAttrs(mark) const attrs = nodeAttrs(mark)
+1 -2
View File
@@ -1,7 +1,7 @@
import type { AdfDocument, AdfNode } from '../../adf/document.ts' import type { AdfDocument, AdfNode } from '../../adf/document.ts'
import type { BlockNodeModel } from '../../adf/block-nodes.ts' import type { BlockNodeModel } from '../../adf/block-nodes.ts'
import { adfDocumentFault, carriesOnly, nodeAttrs, nodeContent, nodeMarks } from '../../adf/document.ts' import { adfDocumentFault, carriesOnly, nodeAttrs, nodeContent, nodeMarks } from '../../adf/document.ts'
import { blockDirectiveForm } from '../block-directive-forms.ts' import { blockDirectiveForm, listBreakSpelling } from '../block-directive.ts'
import { blockNodeModel, blockNodes } from '../../adf/block-nodes.ts' import { blockNodeModel, blockNodes } from '../../adf/block-nodes.ts'
import { carriedBlock } from '../opaque-carry.ts' import { carriedBlock } from '../opaque-carry.ts'
import { emitInlineLine } from './inline-line.ts' import { emitInlineLine } from './inline-line.ts'
@@ -10,7 +10,6 @@ import { fencedCodeBlock } from '../commonmark/backtick-runs.ts'
import { holdsNullCharacter, isBlankLine, isThematicBreak, markerInterruptsParagraph } from '../commonmark/grammar.ts' import { holdsNullCharacter, isBlankLine, isThematicBreak, markerInterruptsParagraph } from '../commonmark/grammar.ts'
import { languageSlot } from '../code-language.ts' import { languageSlot } from '../code-language.ts'
import { largestNesting } from '../../nesting.ts' import { largestNesting } from '../../nesting.ts'
import { listBreakSpelling } from '../list-break.ts'
import { spellBlockDirectiveOpener } from './block-directive-spelling.ts' import { spellBlockDirectiveOpener } from './block-directive-spelling.ts'
import { spellDirectiveCloser, spellDirectiveOpener } from '../directive-syntax.ts' import { spellDirectiveCloser, spellDirectiveOpener } from '../directive-syntax.ts'
import { tryImage } from './image.ts' import { tryImage } from './image.ts'
@@ -1,10 +1,9 @@
import type { AdfNode } from '../../adf/document.ts' import type { AdfNode } from '../../adf/document.ts'
import type { BlockNodeModel } from '../../adf/block-nodes.ts' import type { BlockNodeModel } from '../../adf/block-nodes.ts'
import { attributeNestingMessage, nodeAttrs, nodeMarks } from '../../adf/document.ts' import { attributeNestingMessage, nodeAttrs, nodeMarks } from '../../adf/document.ts'
import { blockArgument } from '../block-directive-arguments.ts' import { blockArgument, markValues, marksAttribute } from '../block-directive.ts'
import { failure, success, type ConvertErrorPath, type Result } from '../../result.ts' import { failure, success, type ConvertErrorPath, type Result } from '../../result.ts'
import { isBareToken, spellAttributes, spellDirectiveOpener, spellJsonAttribute, spellVocabulary } from '../directive-syntax.ts' import { isBareToken, spellAttributes, spellDirectiveOpener, spellJsonAttribute, spellVocabulary } from '../directive-syntax.ts'
import { markValues, marksAttribute } from '../block-directive-marks.ts'
import { overNested } from '../../json-value.ts' import { overNested } from '../../json-value.ts'
import { vocabularyPairs } from '../../adf/attribute-vocabulary.ts' import { vocabularyPairs } from '../../adf/attribute-vocabulary.ts'
-5
View File
@@ -1,5 +0,0 @@
import { spellDirectiveOpener } from './directive-syntax.ts'
export const listBreakName = 'listBreak'
export const listBreakSpelling = spellDirectiveOpener(listBreakName, undefined, '')
+1 -1
View File
@@ -19,7 +19,7 @@ import {
type ThematicBreakTail, type ThematicBreakTail,
} from '../commonmark/grammar.ts' } from '../commonmark/grammar.ts'
import { barePipeCells, isDelimiterRow, isPipeAlignment, isPipeDelimiter, malformedPipeTable, pipeCells } from '../pipe-table-syntax.ts' import { barePipeCells, isDelimiterRow, isPipeAlignment, isPipeDelimiter, malformedPipeTable, pipeCells } from '../pipe-table-syntax.ts'
import { blockDirectiveForm } from '../block-directive-forms.ts' import { blockDirectiveForm } from '../block-directive.ts'
import { directiveEscape, malformedDirective, readDirectiveLine, spellDirectiveCloser } from '../directive-syntax.ts' import { directiveEscape, malformedDirective, readDirectiveLine, spellDirectiveCloser } from '../directive-syntax.ts'
import { readLinkDefinitions } from '../commonmark/link-reference-definitions.ts' import { readLinkDefinitions } from '../commonmark/link-reference-definitions.ts'
+1 -3
View File
@@ -5,14 +5,12 @@ import type { DirectiveAttributes, DirectiveValue } from '../directive-syntax.ts
import type { Elsewhere } from './directive-attributes.ts' import type { Elsewhere } from './directive-attributes.ts'
import { attributeNestingMessage, nodeAttrs, nodeContent, nodeMarks } from '../../adf/document.ts' import { attributeNestingMessage, nodeAttrs, nodeContent, nodeMarks } from '../../adf/document.ts'
import { attributeValue, directivePrefix, spellAttributeValue, unknownDirectiveFault } from '../directive-syntax.ts' import { attributeValue, directivePrefix, spellAttributeValue, unknownDirectiveFault } from '../directive-syntax.ts'
import { blockArgument } from '../block-directive-arguments.ts' import { blockArgument, blockDirectiveForm, marksAttribute, readMarkValues } from '../block-directive.ts'
import { blockDirectiveForm } from '../block-directive-forms.ts'
import { blockNodeModel } from '../../adf/block-nodes.ts' import { blockNodeModel } from '../../adf/block-nodes.ts'
import { carryName } from '../opaque-carry.ts' import { carryName } from '../opaque-carry.ts'
import { failure, faulted, success, type ConvertErrorPath, type Result } from '../../result.ts' import { failure, faulted, success, type ConvertErrorPath, type Result } from '../../result.ts'
import { inlineMarkSpellingFault } from './directive-marks.ts' import { inlineMarkSpellingFault } from './directive-marks.ts'
import { inlineNodeModel } from '../../adf/inline-nodes.ts' import { inlineNodeModel } from '../../adf/inline-nodes.ts'
import { marksAttribute, readMarkValues } from '../block-directive-marks.ts'
import { readVocabulary } from './directive-attributes.ts' import { readVocabulary } from './directive-attributes.ts'
import { slotLineEndingFault } from '../directive-syntax.ts' import { slotLineEndingFault } from '../directive-syntax.ts'
import { textDirectiveName } from '../text-directive.ts' import { textDirectiveName } from '../text-directive.ts'
+1 -1
View File
@@ -9,7 +9,7 @@ import { commonMarkSpelling, type SpellingMemo } from '../emit/adf-to-markdown.t
import { failure, faulted, positioned, success, type ConvertErrorPath, type ParseError, type Result, type SourcePosition } from '../../result.ts' import { failure, faulted, positioned, success, type ConvertErrorPath, type ParseError, type Result, type SourcePosition } from '../../result.ts'
import { languageSlot } from '../code-language.ts' import { languageSlot } from '../code-language.ts'
import { largestNesting } from '../../nesting.ts' import { largestNesting } from '../../nesting.ts'
import { listBreakName, listBreakSpelling } from '../list-break.ts' import { listBreakName, listBreakSpelling } from '../block-directive.ts'
import { nodeAttrs } from '../../adf/document.ts' import { nodeAttrs } from '../../adf/document.ts'
import { parseBlocks } from './blocks.ts' import { parseBlocks } from './blocks.ts'
import { parseInlineContent } from './inline-content.ts' import { parseInlineContent } from './inline-content.ts'
+1 -1
View File
@@ -6,7 +6,7 @@ import type { AdfAttributes, AdfDocument, AdfMark, AdfNode } from './adf/documen
import type { Arbitrary } from 'fast-check' import type { Arbitrary } from 'fast-check'
import type { AttributeKind, AttributeVocabulary } from './adf/attribute-vocabulary.ts' import type { AttributeKind, AttributeVocabulary } from './adf/attribute-vocabulary.ts'
import type { JsonValue } from './json-value.ts' import type { JsonValue } from './json-value.ts'
import { blockArgument } from './markdown/block-directive-arguments.ts' import { blockArgument } from './markdown/block-directive.ts'
import { blockNodes } from './adf/block-nodes.ts' import { blockNodes } from './adf/block-nodes.ts'
import { directivePrefix } from './markdown/directive-syntax.ts' import { directivePrefix } from './markdown/directive-syntax.ts'
import { inlineNodes } from './adf/inline-nodes.ts' import { inlineNodes } from './adf/inline-nodes.ts'
+8
View File
@@ -1030,6 +1030,14 @@ The done `todo.md` items in full, as they were written. `todo.md` keeps a one-li
the block directive's `marks` spelling refuses its own over-deep JSON with the parser's the block directive's `marks` spelling refuses its own over-deep JSON with the parser's
message and the node's path, and §8 says a deeper spelling refuses in its own format. message and the node's path, and §8 says a deeper spelling refuses in its own format.
- [x] **23 — The block-directive fragments are one file (`0.2.0`).** `block-directive-arguments.ts`,
`-forms.ts` and `-marks.ts` are three files under 25 lines answering one question. Fold them,
and take `src/markdown/` — the worst level both architects named, 13 entries with no
organising question — down with them.
**Done** (2026-09-23): `markdown/block-directive.ts` holds the form, the argument, the `marks`
attribute and the `listBreak` spelling — what the block directive spells of a node that the
grammar does not — and `src/markdown/` drops from 15 entries to 12.
## 5 — Ship `0.1.0` ## 5 — Ship `0.1.0`
- [ ] **5 — Ship `0.1.0`.** Only the maintainer's own acts are left (§15): make the Gitea repo - [ ] **5 — Ship `0.1.0`.** Only the maintainer's own acts are left (§15): make the Gitea repo
+1 -4
View File
@@ -56,10 +56,6 @@ chunk clearing a §11 seam.
upward, so the first raise to the measured figure reddens a run that changed nothing. Make upward, so the first raise to the measured figure reddens a run that changed nothing. Make
the measurement repeatable, or state the number the floor may be raised to and why it is not the measurement repeatable, or state the number the floor may be raised to and why it is not
the measured one. the measured one.
- [ ] **23 — The block-directive fragments are one file (`0.2.0`).** `block-directive-arguments.ts`,
`-forms.ts` and `-marks.ts` are three files under 25 lines answering one question. Fold them,
and take `src/markdown/` — the worst level both architects named, 13 entries with no
organising question — down with them.
- [ ] **24 — The conformance gates have a directory (`0.2.0`).** Six root tests with no sibling - [ ] **24 — The conformance gates have a directory (`0.2.0`).** Six root tests with no sibling
source (`adf-property`, `adf-schema`, `commonmark-spec`, `corpus`, `flavour`, source (`adf-property`, `adf-schema`, `commonmark-spec`, `corpus`, `flavour`,
`markdown-property`) plus `property-harness.ts` are the machinery that makes the docs `markdown-property`) plus `property-harness.ts` are the machinery that makes the docs
@@ -281,6 +277,7 @@ chunk clearing a §11 seam.
- [x] **20 — The give-way channel is unmistakable (`0.2.0`).** - [x] **20 — The give-way channel is unmistakable (`0.2.0`).**
- [x] **21 — The ADF tables carry ADF's nouns (`0.2.0`).** - [x] **21 — The ADF tables carry ADF's nouns (`0.2.0`).**
- [x] **22 — `LineContainer` sits at the markdown level (`0.2.0`).** - [x] **22 — `LineContainer` sits at the markdown level (`0.2.0`).**
- [x] **23 — The block-directive fragments are one file (`0.2.0`).**
- [x] **28 — `emitLine`'s retry loop cannot spin (`0.2.0`).** - [x] **28 — `emitLine`'s retry loop cannot spin (`0.2.0`).**
- [x] **29 — The README reads raw HTML as refused for good (`0.2.0`).** - [x] **29 — The README reads raw HTML as refused for good (`0.2.0`).**
- [x] **30 — AGENTS.md says each thing once (`0.2.0`).** - [x] **30 — AGENTS.md says each thing once (`0.2.0`).**