|
|
|
|
|
|
|
|
|
|
|
|
|
import { |
|
asciiControl, |
|
markdownLineEndingOrSpace, |
|
markdownLineEnding |
|
} from 'micromark-util-character' |
|
import {codes} from 'micromark-util-symbol/codes.js' |
|
import {constants} from 'micromark-util-symbol/constants.js' |
|
import {types} from 'micromark-util-symbol/types.js' |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
export function factoryDestination( |
|
effects, |
|
ok, |
|
nok, |
|
type, |
|
literalType, |
|
literalMarkerType, |
|
rawType, |
|
stringType, |
|
max |
|
) { |
|
const limit = max || Number.POSITIVE_INFINITY |
|
let balance = 0 |
|
|
|
return start |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function start(code) { |
|
if (code === codes.lessThan) { |
|
effects.enter(type) |
|
effects.enter(literalType) |
|
effects.enter(literalMarkerType) |
|
effects.consume(code) |
|
effects.exit(literalMarkerType) |
|
return enclosedBefore |
|
} |
|
|
|
|
|
if ( |
|
code === codes.eof || |
|
code === codes.space || |
|
code === codes.rightParenthesis || |
|
asciiControl(code) |
|
) { |
|
return nok(code) |
|
} |
|
|
|
effects.enter(type) |
|
effects.enter(rawType) |
|
effects.enter(stringType) |
|
effects.enter(types.chunkString, {contentType: constants.contentTypeString}) |
|
return raw(code) |
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function enclosedBefore(code) { |
|
if (code === codes.greaterThan) { |
|
effects.enter(literalMarkerType) |
|
effects.consume(code) |
|
effects.exit(literalMarkerType) |
|
effects.exit(literalType) |
|
effects.exit(type) |
|
return ok |
|
} |
|
|
|
effects.enter(stringType) |
|
effects.enter(types.chunkString, {contentType: constants.contentTypeString}) |
|
return enclosed(code) |
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function enclosed(code) { |
|
if (code === codes.greaterThan) { |
|
effects.exit(types.chunkString) |
|
effects.exit(stringType) |
|
return enclosedBefore(code) |
|
} |
|
|
|
if ( |
|
code === codes.eof || |
|
code === codes.lessThan || |
|
markdownLineEnding(code) |
|
) { |
|
return nok(code) |
|
} |
|
|
|
effects.consume(code) |
|
return code === codes.backslash ? enclosedEscape : enclosed |
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function enclosedEscape(code) { |
|
if ( |
|
code === codes.lessThan || |
|
code === codes.greaterThan || |
|
code === codes.backslash |
|
) { |
|
effects.consume(code) |
|
return enclosed |
|
} |
|
|
|
return enclosed(code) |
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function raw(code) { |
|
if ( |
|
!balance && |
|
(code === codes.eof || |
|
code === codes.rightParenthesis || |
|
markdownLineEndingOrSpace(code)) |
|
) { |
|
effects.exit(types.chunkString) |
|
effects.exit(stringType) |
|
effects.exit(rawType) |
|
effects.exit(type) |
|
return ok(code) |
|
} |
|
|
|
if (balance < limit && code === codes.leftParenthesis) { |
|
effects.consume(code) |
|
balance++ |
|
return raw |
|
} |
|
|
|
if (code === codes.rightParenthesis) { |
|
effects.consume(code) |
|
balance-- |
|
return raw |
|
} |
|
|
|
|
|
|
|
|
|
if ( |
|
code === codes.eof || |
|
code === codes.space || |
|
code === codes.leftParenthesis || |
|
asciiControl(code) |
|
) { |
|
return nok(code) |
|
} |
|
|
|
effects.consume(code) |
|
return code === codes.backslash ? rawEscape : raw |
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function rawEscape(code) { |
|
if ( |
|
code === codes.leftParenthesis || |
|
code === codes.rightParenthesis || |
|
code === codes.backslash |
|
) { |
|
effects.consume(code) |
|
return raw |
|
} |
|
|
|
return raw(code) |
|
} |
|
} |
|
|