Read a carry fence's type in one function

This commit is contained in:
2026-10-03 14:45:48 +02:00
parent 2700184e56
commit c3bc2eb572
3 changed files with 11 additions and 5 deletions
+2 -2
View File
@@ -1,5 +1,5 @@
import type { JsonValue } from '../json-value.ts' import type { JsonValue } from '../json-value.ts'
import { carryFencePrefix } from './opaque-carry.ts' import { carryFenceType } from './opaque-carry.ts'
import { infoStringCarries } from './commonmark/grammar.ts' import { infoStringCarries } from './commonmark/grammar.ts'
export type LanguageSlot = { info: string; kind: 'fence' } | { kind: 'attribute' } | { kind: 'none' } export type LanguageSlot = { info: string; kind: 'fence' } | { kind: 'attribute' } | { kind: 'none' }
@@ -7,6 +7,6 @@ export type LanguageSlot = { info: string; kind: 'fence' } | { kind: 'attribute'
// spec/flavour.md, The CommonMark blocks: the one slot a codeBlock's language rides. // spec/flavour.md, The CommonMark blocks: the one slot a codeBlock's language rides.
export function languageSlot(language: JsonValue | undefined): LanguageSlot { export function languageSlot(language: JsonValue | undefined): LanguageSlot {
if (language === undefined) return { kind: 'none' } if (language === undefined) return { kind: 'none' }
if (typeof language !== 'string' || language.startsWith(carryFencePrefix) || !infoStringCarries(language)) return { kind: 'attribute' } if (typeof language !== 'string' || carryFenceType(language) !== undefined || !infoStringCarries(language)) return { kind: 'attribute' }
return { info: language, kind: 'fence' } return { info: language, kind: 'fence' }
} }
+5
View File
@@ -32,6 +32,11 @@ export function carriedInline(node: AdfNode, path: ConvertErrorPath): Result<str
return success(spellInlineLeafDirective(carryName, spellAttributes([[jsonAttribute, spellStringAttribute(json.value.json)]]))) return success(spellInlineLeafDirective(carryName, spellAttributes([[jsonAttribute, spellStringAttribute(json.value.json)]])))
} }
// The type a fence's info string names, `undefined` where the info string opens no carry.
export function carryFenceType(info: string): string | undefined {
return info.startsWith(carryFencePrefix) ? info.slice(carryFencePrefix.length) : undefined
}
export function readCarriedBlock(type: string, body: string, depth: number): Read<AdfNode> { export function readCarriedBlock(type: string, body: string, depth: number): Read<AdfNode> {
if (type !== '' && !infoStringCarries(type)) { if (type !== '' && !infoStringCarries(type)) {
return { fault: unsupportedNodeShape(`the carry fence names a type no info string carries back: spell it ${carryFencePrefix} with the type in the JSON`) } return { fault: unsupportedNodeShape(`the carry fence names a type no info string carries back: spell it ${carryFencePrefix} with the type in the JSON`) }
+4 -3
View File
@@ -5,7 +5,7 @@ import type { ConvertFault } from '../../result.ts'
import type { Flavour } from '../plain-conventions.ts' import type { Flavour } from '../plain-conventions.ts'
import type { LineContainer } from '../line-container.ts' import type { LineContainer } from '../line-container.ts'
import type { LinkDefinitions } from './inline-content.ts' import type { LinkDefinitions } from './inline-content.ts'
import { carryFencePrefix, readCarriedBlock } from '../opaque-carry.ts' import { carryFenceType, readCarriedBlock } from '../opaque-carry.ts'
import { commonMarkSpelling, type SpellingMemo } from '../emit/adf-to-markdown.ts' import { commonMarkSpelling, type SpellingMemo } from '../emit/adf-to-markdown.ts'
import { documentAttribute, documentName, documentSpelling, listBreakName, listBreakSpelling } from '../block-directive.ts' import { documentAttribute, documentName, documentSpelling, listBreakName, listBreakSpelling } from '../block-directive.ts'
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'
@@ -303,8 +303,9 @@ function listNode(node: AdfNode, items: readonly Block[][], reading: Reading, pa
} }
function codeBlockNode(language: string, text: string, reading: Reading, path: ConvertErrorPath, depth: number): Result<AdfNode> { function codeBlockNode(language: string, text: string, reading: Reading, path: ConvertErrorPath, depth: number): Result<AdfNode> {
if (language.startsWith(carryFencePrefix)) { const carriedType = carryFenceType(language)
const carried = readCarriedBlock(language.slice(carryFencePrefix.length), text, depth) if (carriedType !== undefined) {
const carried = readCarriedBlock(carriedType, text, depth)
if (carried.fault !== undefined) return faulted(carried.fault, path) if (carried.fault !== undefined) return faulted(carried.fault, path)
reading.carried.add(carried.value) reading.carried.add(carried.value)
return success(carried.value) return success(carried.value)