Browse Source

temp

feat/shiki-twoslash-rehype
Patrick Gray 4 years ago
parent
commit
c969a386c3
  1. 5
      lib/rehype-plugins.js
  2. 146
      lib/rehype-shiki-twoslash.js
  3. 1
      package.json
  4. 2
      src/pages/understand-stacks/local-development.md
  5. 51
      yarn.lock

5
lib/rehype-plugins.js

@ -1,7 +1,8 @@
const memoize = require('micro-memoize');
const { rehypeVscode } = require('unified-vscode');
// const { rehypeVscode } = require('unified-vscode');
const { rehypeShikiTwoslash } = require('./rehype-shiki-twoslash');
const rehypeImgs = require('./rehype-image-size');
const rehypePlugins = [memoize(rehypeVscode), rehypeImgs];
const rehypePlugins = [rehypeShikiTwoslash, rehypeImgs];
module.exports = { rehypePlugins };

146
lib/rehype-shiki-twoslash.js

@ -0,0 +1,146 @@
const createShikiHighlighter = require('shiki-twoslash');
const memoize = require('micro-memoize');
const visit = require('unist-util-visit');
const pAll = require('p-all');
const hastToString = require('hast-util-to-string');
const DEFAULT_THEME = 'dark-plus';
function getTokenClassNames(token) {
let classNames;
let classNameString = '';
token.explanation.forEach(expl => {
const thing = expl.scopes.find(scope => scope.themeMatches.length > 0);
const themeMatches = thing && thing.themeMatches && thing.themeMatches[0];
const name = themeMatches && themeMatches.name;
const formatted =
name &&
name
.toString()
.split(', ')
.map(entry => entry.toLowerCase());
if (formatted) {
classNames = formatted;
}
});
classNames &&
classNames.length &&
classNames.forEach((className, index) => {
classNameString += `${slugify(className)}${index !== classNames.length - 1 ? ' ' : ''}`;
});
return classNameString === '' ? 'plain' : classNameString;
}
function removeEmptyLine(index, tree) {
const [item] = tree.slice(index * -1);
if (item && item.properties && item.properties.className.includes('empty')) {
tree.pop();
}
}
function codeLanguage(node) {
const className = node.properties.className || [];
let value;
for (const element of className) {
value = element;
if (value.slice(0, 9) === 'language-') {
return value.slice(9);
}
}
return 'bash';
}
const rehypeShikiTwoslash = options => {
let theme = options.theme || DEFAULT_THEME;
const generateHighlighter = memoize(async () => createShikiHighlighter({ theme, cache }), {
isPromise: true,
});
const highlight = async (node, lang) => {
const hash = generateHash(node);
return cache.wrap(hash, async () => {
const highlighter = await generateHighlighter();
return highlighter.codeToThemedTokens(node, lang);
});
};
function tokensToHast(lines) {
const tokenLineClassName = (options && options.tokenLineClassName) || 'token-line';
const tokenLineElement = (options && options.tokenLineElement) || 'span';
const tree = [];
for (const line of lines) {
if (line.length === 0) {
tree.push(
u('element', {
tagName: tokenLineElement,
properties: { className: `${tokenLineClassName} ${tokenLineClassName}__empty` },
})
);
} else {
const lineChildren = [];
for (const token of line) {
const className = getTokenClassNames(token);
lineChildren.push(
u(
'element',
{
tagName: 'span',
properties: { style: `color: ${token.color}`, className: `token ${className}` },
},
[u('text', token.content)]
)
);
}
tree.push(
u(
'element',
{ tagName: tokenLineElement, properties: { className: tokenLineClassName } },
lineChildren
)
);
}
}
removeEmptyLine(2, tree);
removeEmptyLine(1, tree);
return tree;
}
async function transformer(tree) {
const nodes = [];
visit(tree, 'element', (node, index, parent) => {
if (!parent || parent.tagName !== 'pre' || node.tagName !== 'code') {
return;
} else {
nodes.push(node);
}
});
await pAll(
nodes.map(node => () => visitor(node)),
{ concurrency: 25 }
);
return tree;
}
async function visitor(node) {
const lang = codeLanguage(node);
const tokens = await highlight(hastToString(node), lang);
const tree = tokensToHast(tokens);
node.properties.lines = tokens.length - 1;
node.properties.lang = lang;
node.children = tree;
}
return transformer;
};
module.exports = rehypeShikiTwoslash;

1
package.json

@ -79,6 +79,7 @@
"remark-squeeze-paragraphs": "^4.0.0",
"remark-unwrap-images": "2.0.0",
"remark-vscode": "^1.0.0-beta.2",
"shiki-twoslash": "^1.4.1",
"strip-markdown": "^4.0.0",
"stylis": "^4.0.6",
"swr": "^0.3.11",

2
src/pages/understand-stacks/local-development.md

@ -31,7 +31,7 @@ This guide helps you understand how to set up and run a mocknet for local develo
```bash
cp sample.env .env
```
3. Start the Mocknet:
```bash

51
yarn.lock

@ -2176,6 +2176,22 @@
"@typescript-eslint/types" "4.9.0"
eslint-visitor-keys "^2.0.0"
"@typescript/twoslash@1.1.7":
version "1.1.7"
resolved "https://registry.yarnpkg.com/@typescript/twoslash/-/twoslash-1.1.7.tgz#9fc5709f37940f2deda396b74e503c6c33c54d6e"
integrity sha512-+oASPajHbUpmwsZgf0/ioBn9vjIodAO4c0na2nMLWxBKDMGAo16m8uEFtxjIrEYp6l+h3rBvHchSFucv1/qcNQ==
dependencies:
"@typescript/vfs" "1.3.4"
debug "^4.1.1"
lz-string "^1.4.4"
"@typescript/vfs@1.3.4":
version "1.3.4"
resolved "https://registry.yarnpkg.com/@typescript/vfs/-/vfs-1.3.4.tgz#07f89d2114f6e29255d589395ed7f3b4af8a00c2"
integrity sha512-RbyJiaAGQPIcAGWFa3jAXSuAexU4BFiDRF1g3hy7LmRqfNpYlTQWGXjcrOaVZjJ8YkkpuwG0FcsYvtWQpd9igQ==
dependencies:
debug "^4.1.1"
"@webassemblyjs/ast@1.9.0":
version "1.9.0"
resolved "https://registry.yarnpkg.com/@webassemblyjs/ast/-/ast-1.9.0.tgz#bd850604b4042459a5a41cd7d338cbed695ed964"
@ -6103,6 +6119,11 @@ lru-cache@^5.1.1:
dependencies:
yallist "^3.0.2"
lz-string@^1.4.4:
version "1.4.4"
resolved "https://registry.yarnpkg.com/lz-string/-/lz-string-1.4.4.tgz#c0d8eaf36059f705796e1e344811cf4c498d3a26"
integrity sha1-wNjq82BZ9wV5bh40SBHPTEmNOiY=
make-dir@^2.0.0:
version "2.1.0"
resolved "https://registry.yarnpkg.com/make-dir/-/make-dir-2.1.0.tgz#5f0310e18b8be898cc07009295a30ae41e91e6f5"
@ -6911,7 +6932,7 @@ once@^1.3.0, once@^1.3.1, once@^1.4.0:
dependencies:
wrappy "1"
onigasm@^2.2.1:
onigasm@^2.2.1, onigasm@^2.2.5:
version "2.2.5"
resolved "https://registry.yarnpkg.com/onigasm/-/onigasm-2.2.5.tgz#cc4d2a79a0fa0b64caec1f4c7ea367585a676892"
integrity sha512-F+th54mPc0l1lp1ZcFMyL/jTs2Tlq4SqIHKIXGZOR/VkHkF9A7Fr5rRr5+ZG/lWeRsyrClLYRq7s/yFQ/XhWCA==
@ -8378,6 +8399,24 @@ shell-quote@1.7.2:
resolved "https://registry.yarnpkg.com/shell-quote/-/shell-quote-1.7.2.tgz#67a7d02c76c9da24f99d20808fcaded0e0e04be2"
integrity sha512-mRz/m/JVscCrkMyPqHc/bczi3OQHkLTqXHEFu0zDhK/qfv3UcOA4SVmRCLmos4bhjr9ekVQubj/R7waKapmiQg==
shiki-twoslash@^1.4.1:
version "1.4.1"
resolved "https://registry.yarnpkg.com/shiki-twoslash/-/shiki-twoslash-1.4.1.tgz#cab11b13214c51f88bed733512feb2654da0716e"
integrity sha512-PB55xKMbiDwiOc9OoJAsxsdKURsqqmHrc8hL0gsRuiJrcN+iz4NupKYwxzp+VzhBkKAZMG8YXwt//XithLpGJQ==
dependencies:
"@typescript/twoslash" "1.1.7"
"@typescript/vfs" "1.3.4"
shiki "^0.9.3"
typescript ">3"
shiki@^0.9.3:
version "0.9.3"
resolved "https://registry.yarnpkg.com/shiki/-/shiki-0.9.3.tgz#7bf7bcf3ed50ca525ec89cc09254abce4264d5ca"
integrity sha512-NEjg1mVbAUrzRv2eIcUt3TG7X9svX7l3n3F5/3OdFq+/BxUdmBOeKGiH4icZJBLHy354Shnj6sfBTemea2e7XA==
dependencies:
onigasm "^2.2.5"
vscode-textmate "^5.2.0"
signal-exit@^3.0.0, signal-exit@^3.0.2:
version "3.0.3"
resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.3.tgz#a1410c2edd8f077b08b4e253c8eacfcaf057461c"
@ -9205,6 +9244,11 @@ typedarray@^0.0.6:
resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777"
integrity sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=
typescript@>3:
version "4.3.2"
resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.3.2.tgz#399ab18aac45802d6f2498de5054fcbbe716a805"
integrity sha512-zZ4hShnmnoVnAHpVHWpTcxdv7dWP60S2FsydQLV8V5PbS3FifjWFFRiHSWpDJahly88PRyV5teTSLoq4eG7mKw==
typescript@^4.1.2:
version "4.1.2"
resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.1.2.tgz#6369ef22516fe5e10304aae5a5c4862db55380e9"
@ -9613,6 +9657,11 @@ vm-browserify@1.1.2, vm-browserify@^1.0.1:
resolved "https://registry.yarnpkg.com/vm-browserify/-/vm-browserify-1.1.2.tgz#78641c488b8e6ca91a75f511e7a3b32a86e5dda0"
integrity sha512-2ham8XPWTONajOR0ohOKOHXkm3+gaBmGut3SRuu75xLd/RRaY6vqgh8NBYYk7+RW3u5AtzPQZG8F10LHkl0lAQ==
vscode-textmate@^5.2.0:
version "5.4.0"
resolved "https://registry.yarnpkg.com/vscode-textmate/-/vscode-textmate-5.4.0.tgz#4b25ffc1f14ac3a90faf9a388c67a01d24257cd7"
integrity sha512-c0Q4zYZkcLizeYJ3hNyaVUM2AA8KDhNCA3JvXY8CeZSJuBdAy3bAvSbv46RClC4P3dSO9BdwhnKEx2zOo6vP/w==
"vscode-textmate@https://github.com/octref/vscode-textmate":
version "4.0.1"
resolved "https://github.com/octref/vscode-textmate#e65aabe2227febda7beaad31dd0fca1228c5ddf3"

Loading…
Cancel
Save