diff options
| author | altaf-creator <dev@altafcreator.com> | 2026-04-30 22:01:53 +0800 |
|---|---|---|
| committer | altaf-creator <dev@altafcreator.com> | 2026-04-30 22:01:53 +0800 |
| commit | db1c6676a13798ee57dbac429a1d5045b60356fb (patch) | |
| tree | 5ff305c09686de50bbcac404c1954e42c26ba494 /packages/markdown-it-14.1.0/lib/rules_core/linkify.mjs | |
| parent | 97fa8f57fbefcbfa6b3e56c31a1e5b60ef1a9e37 (diff) | |
quite a big commit
Diffstat (limited to 'packages/markdown-it-14.1.0/lib/rules_core/linkify.mjs')
| -rw-r--r-- | packages/markdown-it-14.1.0/lib/rules_core/linkify.mjs | 134 |
1 files changed, 0 insertions, 134 deletions
diff --git a/packages/markdown-it-14.1.0/lib/rules_core/linkify.mjs b/packages/markdown-it-14.1.0/lib/rules_core/linkify.mjs deleted file mode 100644 index a225280..0000000 --- a/packages/markdown-it-14.1.0/lib/rules_core/linkify.mjs +++ /dev/null @@ -1,134 +0,0 @@ -// Replace link-like texts with link nodes. -// -// Currently restricted by `md.validateLink()` to http/https/ftp -// - -import { arrayReplaceAt } from '../common/utils.mjs' - -function isLinkOpen (str) { - return /^<a[>\s]/i.test(str) -} -function isLinkClose (str) { - return /^<\/a\s*>/i.test(str) -} - -export default function linkify (state) { - const blockTokens = state.tokens - - if (!state.md.options.linkify) { return } - - for (let j = 0, l = blockTokens.length; j < l; j++) { - if (blockTokens[j].type !== 'inline' || - !state.md.linkify.pretest(blockTokens[j].content)) { - continue - } - - let tokens = blockTokens[j].children - - let htmlLinkLevel = 0 - - // We scan from the end, to keep position when new tags added. - // Use reversed logic in links start/end match - for (let i = tokens.length - 1; i >= 0; i--) { - const currentToken = tokens[i] - - // Skip content of markdown links - if (currentToken.type === 'link_close') { - i-- - while (tokens[i].level !== currentToken.level && tokens[i].type !== 'link_open') { - i-- - } - continue - } - - // Skip content of html tag links - if (currentToken.type === 'html_inline') { - if (isLinkOpen(currentToken.content) && htmlLinkLevel > 0) { - htmlLinkLevel-- - } - if (isLinkClose(currentToken.content)) { - htmlLinkLevel++ - } - } - if (htmlLinkLevel > 0) { continue } - - if (currentToken.type === 'text' && state.md.linkify.test(currentToken.content)) { - const text = currentToken.content - let links = state.md.linkify.match(text) - - // Now split string to nodes - const nodes = [] - let level = currentToken.level - let lastPos = 0 - - // forbid escape sequence at the start of the string, - // this avoids http\://example.com/ from being linkified as - // http:<a href="//example.com/">//example.com/</a> - if (links.length > 0 && - links[0].index === 0 && - i > 0 && - tokens[i - 1].type === 'text_special') { - links = links.slice(1) - } - - for (let ln = 0; ln < links.length; ln++) { - const url = links[ln].url - const fullUrl = state.md.normalizeLink(url) - if (!state.md.validateLink(fullUrl)) { continue } - - let urlText = links[ln].text - - // Linkifier might send raw hostnames like "example.com", where url - // starts with domain name. So we prepend http:// in those cases, - // and remove it afterwards. - // - if (!links[ln].schema) { - urlText = state.md.normalizeLinkText('http://' + urlText).replace(/^http:\/\//, '') - } else if (links[ln].schema === 'mailto:' && !/^mailto:/i.test(urlText)) { - urlText = state.md.normalizeLinkText('mailto:' + urlText).replace(/^mailto:/, '') - } else { - urlText = state.md.normalizeLinkText(urlText) - } - - const pos = links[ln].index - - if (pos > lastPos) { - const token = new state.Token('text', '', 0) - token.content = text.slice(lastPos, pos) - token.level = level - nodes.push(token) - } - - const token_o = new state.Token('link_open', 'a', 1) - token_o.attrs = [['href', fullUrl]] - token_o.level = level++ - token_o.markup = 'linkify' - token_o.info = 'auto' - nodes.push(token_o) - - const token_t = new state.Token('text', '', 0) - token_t.content = urlText - token_t.level = level - nodes.push(token_t) - - const token_c = new state.Token('link_close', 'a', -1) - token_c.level = --level - token_c.markup = 'linkify' - token_c.info = 'auto' - nodes.push(token_c) - - lastPos = links[ln].lastIndex - } - if (lastPos < text.length) { - const token = new state.Token('text', '', 0) - token.content = text.slice(lastPos) - token.level = level - nodes.push(token) - } - - // replace current node - blockTokens[j].children = tokens = arrayReplaceAt(tokens, i, nodes) - } - } - } -} |
