Skip to content

Commit

Permalink
feat: highlight markdown code blocks (#210)
Browse files Browse the repository at this point in the history
  • Loading branch information
magicmatatjahu authored Jun 15, 2021
1 parent 3274103 commit 36d0bc7
Show file tree
Hide file tree
Showing 8 changed files with 114 additions and 311 deletions.
46 changes: 37 additions & 9 deletions filters/all.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ const fs = require('fs');
const path = require('path');
const React = require('react');
const ReactDOMServer = require('react-dom/server');
const AsyncApiUI = require('@asyncapi/react-component').default;
const { default: AsyncApiComponent, hljs } = require('@asyncapi/react-component');

const filter = module.exports;

Expand Down Expand Up @@ -56,15 +56,32 @@ function replaceCircular(val, cache) {
return val;
}

let initLanguages = false;
/**
* Stringifies the specification with escaping circular refs
* and annotates that specification is parsed.
* Load all language configurations from highlight.js
*/
function stringifySpec(asyncapi) {
asyncapi._json['x-parser-spec-parsed'] = true;
return JSON.stringify(replaceCircular(asyncapi.json()));
function loadLanguagesConfig() {
if (initLanguages === true) {
return;
}

/**
* Retrieve the location of highlight.js.
* It's needed because someone can have installed `highlight.js` as global dependency
* or depper than local `node_modules` of this template.
*/
const hljsPackageDir = path.dirname(require.resolve("highlight.js/package.json"))
const hljsLanguagesPath = path.resolve(hljsPackageDir, 'lib/languages');
const languages = fs.readdirSync(hljsLanguagesPath);

for (let langPath of languages) {
const lang = require(path.resolve(hljsLanguagesPath, langPath));
hljs.registerLanguage(lang.name, lang);
}

initLanguages = true;
}
filter.stringifySpec = stringifySpec;
filter.loadLanguagesConfig = loadLanguagesConfig;

/**
* More safe function to include content of given file than default Nunjuck's `include`.
Expand All @@ -76,6 +93,15 @@ function includeFile(pathFile) {
}
filter.includeFile = includeFile;

/**
* Stringifies the specification with escaping circular refs
* and annotates that specification is parsed.
*/
function stringifySpec(asyncapi) {
return JSON.stringify(replaceCircular(asyncapi.json()));
}
filter.stringifySpec = stringifySpec;

/**
* Stringifies prepared configuration for component.
*/
Expand All @@ -85,10 +111,12 @@ function stringifyConfiguration(params) {
filter.stringifyConfiguration = stringifyConfiguration;

/**
* Renders AsyncApiUI component by given AsyncAPI spec and with corresponding template configuration.
* Renders AsyncApi component by given AsyncAPI spec and with corresponding template configuration.
*/
function renderSpec(asyncapi, params) {
const component = React.createElement(AsyncApiUI, { schema: asyncapi, config: prepareConfiguration(params) });
loadLanguagesConfig();

const component = React.createElement(AsyncApiComponent, { schema: asyncapi, config: prepareConfiguration(params) });
return ReactDOMServer.renderToString(component);
}
filter.renderSpec = renderSpec;
4 changes: 1 addition & 3 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -104,9 +104,7 @@
},
"generator": ">=1.4.0 <2.0.0",
"nonRenderableFiles": [
"js/react.production.min.js",
"js/react-dom.production.min.js",
"js/asyncapi-ui.wp.js"
"js/asyncapi-ui.min.js"
]
},
"jest": {
Expand Down
4 changes: 1 addition & 3 deletions scripts/copy-sources.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,7 @@ const copyFile = util.promisify(fs.copyFile);

// source (node_modules): destination (template)
const filesToCopy = {
"react/umd/react.production.min.js": "js/react.production.min.js",
"react-dom/umd/react-dom.production.min.js": "js/react-dom.production.min.js",
"@asyncapi/react-component/browser/without-parser.js": "js/asyncapi-ui.min.js",
"@asyncapi/react-component/browser/standalone/without-parser.js": "js/asyncapi-ui.min.js",
"@asyncapi/react-component/styles/default.min.css": "css/styles.min.css",
};

Expand Down
13 changes: 1 addition & 12 deletions template/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -20,28 +20,17 @@
<div id="root">{{ asyncapi | renderSpec(params) | safe }}</div>

{% if params.singleFile %}
<script type="text/javascript">
{{ "template/js/react.production.min.js" | includeFile | safe }}
</script>
<script type="text/javascript">
{{ "template/js/react-dom.production.min.js" | includeFile | safe }}
</script>
<script type="text/javascript">
{{ "template/js/asyncapi-ui.min.js" | includeFile | safe }}
</script>
{% else %}
<script src="js/react.production.min.js" type="application/javascript"></script>
<script src="js/react-dom.production.min.js" type="application/javascript"></script>
<script src="js/asyncapi-ui.min.js" type="application/javascript"></script>
{% endif %}

<script>
var schema = {{ asyncapi | stringifySpec | safe }};
var config = {{ params | stringifyConfiguration | safe }};
ReactDOM.hydrate(
React.createElement(AsyncApiComponent, { schema, config }),
document.getElementById("root")
);
AsyncApiStandalone.hydrate({ schema, config }, document.getElementById("root"));
</script>
</body>
</html>
39 changes: 34 additions & 5 deletions template/js/asyncapi-ui.min.js

Large diffs are not rendered by default.

Loading

0 comments on commit 36d0bc7

Please sign in to comment.