discourse/app/assets/javascripts/pretty-text/engines/discourse-markdown/onebox.js
Josh Soref 59097b207f
DEV: Correct typos and spelling mistakes (#12812)
Over the years we accrued many spelling mistakes in the code base. 

This PR attempts to fix spelling mistakes and typos in all areas of the code that are extremely safe to change 

- comments
- test descriptions
- other low risk areas
2021-05-21 11:43:47 +10:00

119 lines
3.3 KiB
JavaScript

import { cachedInlineOnebox } from "pretty-text/inline-oneboxer";
import { lookupCache } from "pretty-text/oneboxer-cache";
const ONEBOX = 1;
const INLINE = 2;
function isTopLevel(href) {
let split = href.split(/https?:\/\/[^\/]+[\/?]/i);
let hasExtra = split && split[1] && split[1].length > 0;
return !hasExtra;
}
function applyOnebox(state, silent) {
if (silent || !state.tokens) {
return;
}
for (let i = 1; i < state.tokens.length; i++) {
let token = state.tokens[i];
let prev = state.tokens[i - 1];
let mode =
prev.type === "paragraph_open" && prev.level === 0 ? ONEBOX : INLINE;
if (token.type === "inline") {
let children = token.children;
for (let j = 0; j < children.length - 2; j++) {
let child = children[j];
if (
child.type === "link_open" &&
child.markup === "linkify" &&
child.info === "auto"
) {
if (j > children.length - 3) {
continue;
}
if (j === 0 && token.leading_space) {
mode = INLINE;
} else if (j > 0) {
let prevSibling = children[j - 1];
if (prevSibling.tag !== "br" || prevSibling.leading_space) {
mode = INLINE;
}
}
// look ahead for soft or hard break
let text = children[j + 1];
let close = children[j + 2];
let lookahead = children[j + 3];
if (lookahead && lookahead.tag !== "br") {
mode = INLINE;
}
// check attrs only include a href
let attrs = child.attrs;
if (!attrs || attrs.length !== 1 || attrs[0][0] !== "href") {
continue;
}
let href = attrs[0][1];
// edge case ... what if this is not http or protocolless?
if (!/^http|^\/\//i.test(href)) {
continue;
}
// we already know text matches cause it is an auto link
if (!close || close.type !== "link_close") {
continue;
}
if (mode === ONEBOX) {
// we already determined earlier that 0 0 was href
let cached = lookupCache(attrs[0][1]);
if (cached) {
// replace link with 2 blank text nodes and inline html for onebox
child.type = "html_raw";
child.content = cached;
child.inline = true;
child.onebox = true;
text.type = "html_raw";
text.content = "";
text.inline = true;
close.type = "html_raw";
close.content = "";
close.inline = true;
} else {
// decorate...
attrs.push(["class", "onebox"]);
attrs.push(["target", "_blank"]);
}
} else if (mode === INLINE && !isTopLevel(href)) {
const onebox = cachedInlineOnebox(href);
if (onebox && onebox.title) {
text.content = onebox.title;
attrs.push(["class", "inline-onebox"]);
} else if (!onebox) {
attrs.push(["class", "inline-onebox-loading"]);
}
}
}
}
}
}
}
export function setup(helper) {
helper.registerPlugin((md) => {
md.core.ruler.after("linkify", "onebox", applyOnebox);
});
}