-
Notifications
You must be signed in to change notification settings - Fork 15
/
hugo-build-script.js
146 lines (130 loc) · 4.75 KB
/
hugo-build-script.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
/*!
* Copyright (c) Microsoft Corporation. All rights reserved.
* Licensed under the MIT License.
*/
const fs = require('fs');
const inputPath = __dirname + '/storybook-static/index.html';
const iFramePath = __dirname + '/storybook-static/iframe.html';
const outputPath = __dirname + '/storybook-static/playground.html';
const cacheScriptsPath = __dirname + '/storybook-static/cache-scripts.js';
fs.readFile(inputPath, (err, indexContent) => {
if (err) {
throw err;
}
// Read in index.html content
if (indexContent) {
// Read in iframe to grab appropriate scripts to cache
fs.readFile(iFramePath, (err, iFrameContent) => {
if (err) {
throw err;
}
extractAndGenerateContent(indexContent, iFrameContent);
});
}
else {
console.log('Unable to find index.html file');
}
});
function extractAndGenerateContent(indexContent, iFrameContent) {
let stylesheetLinksContent;
let scriptMatches;
let iFrameScriptMatches;
const content = indexContent.toString().match(/<head>(?<head>.*?)<\/head>\s*<body>(?<body>.*?)<\/body>/s);
if (content && content.groups) {
stylesheetLinksContent = content.groups.head.match(/<link\s+rel="stylesheet".*?(>|\/>|<\/link>)/gs);
scriptMatches = Array.from(content.groups.body.matchAll(/<script\s+src="(?<src>.*?)"><\/script>/g),
match => match.groups.src);
iFrameScriptMatches = Array.from(iFrameContent.toString().matchAll(/<script\s+src="(?<src>.*?)"><\/script>/g),
match => match.groups.src);
}
else {
const errorMsg = 'Error finding content.groups used for body or head';
console.log(errorMsg);
throw new Error(errorMsg);
}
const { stylesheetLinks, body } = cleanupContent(stylesheetLinksContent, content);
// Create playground.html
createPlaygroundHtml(stylesheetLinks, body);
// Create cache-script.js
createCacheScriptsJS(scriptMatches, iFrameScriptMatches);
}
function createCacheScriptsJS(scriptMatches, iFrameScriptMatches) {
let scripts = [];
getScripts(scriptMatches, scripts);
getScripts(iFrameScriptMatches, scripts);
const cacheScript = createJSCacheScript(scripts);
fs.writeFile(cacheScriptsPath, cacheScript, (err) => {
if (err) {
throw err;
}
console.log(`CREATED: ${cacheScriptsPath}`);
});
}
function getScripts(scriptMatches, scripts) {
if (scriptMatches && scriptMatches.length) {
for (const script of scriptMatches) {
// We're only interested in scripts that start with vendors~main.
// Others are pretty small and can be loaded on-demand.
if (script.startsWith('vendors~main')) {
scripts.push(script);
}
}
}
}
function createPlaygroundHtml(stylesheetLinks, body) {
const outputContent = createHugoTemplate(stylesheetLinks, body);
fs.writeFile(outputPath, outputContent, (err) => {
if (err) {
throw err;
}
console.log(`CREATED: ${outputPath}`);
});
}
function cleanupContent(stylesheetLinksContent, content) {
let stylesheetLinks;
let body;
if (stylesheetLinksContent && stylesheetLinksContent.length && content.groups) {
stylesheetLinks = stylesheetLinksContent.join('\n');
// Remove any unnecessary white space (not required - but easier to read output)
body = content.groups.body.replace(/\n|\s{2,}/gs, '');
}
else {
const errorMsg = 'Error finding stylesheets or body content!';
console.log(errorMsg);
throw new Error(errorMsg);
}
return { stylesheetLinks, body };
}
function createHugoTemplate(stylesheetLinks, bodyContent) {
return `{{ define "header" }}
{{ partial "header.html" . }}
{{ end }}
{{ define "main" }}
<script>
var base = document.createElement('base');
base.href = '/playground/';
document.getElementsByTagName('head')[0].appendChild(base);
</script>
${stylesheetLinks}
${bodyContent}
{{ block "footer" . -}}{{ end }}
{{- if templates.Exists "partials/extra-foot.html" -}}
{{ partial "extra-foot.html" . }}
{{- end }}
{{ end }}`;
}
function createJSCacheScript(hashedBundles) {
return `// Cache scripts for performance
if (location.href.indexOf('/playground') === -1) {
var scripts = [ 'sb_dll/storybook_ui_dll.js', 'sb_dll/storybook_docs_dll.js', '${hashedBundles.join('\',\'')}' ];
for (var i=0;i<scripts.length;i++) {
var name = scripts[i];
var path = '/playground/' + name;
const script = document.createElement('link');
script.id = name;
script.href = path;
script.rel = "prefetch";
document.body.appendChild(script);
}
}`;
}