8000 feat: adjust `pre` option in webindex to a string instead of an objec… · fuse-box/fuse-box@8d13bd9 · GitHub
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content 8000
This repository was archived by the owner on Jun 20, 2023. It is now read-only.

Commit 8d13bd9

Browse files
Christian Toddnchanged
authored andcommitted
feat: adjust pre option in webindex to a string instead of an object and update docs.
1 parent <
8000
a class="color-fg-default Link--inTextBlock prc-Link-Link-85e08" data-hotkey="p" data-hovercard-url="/fuse-box/fuse-box/commit/163ef97e77a3449f42c29650e211d12745b81f27/hovercard" href="/fuse-box/fuse-box/commit/163ef97e77a3449f42c29650e211d12745b81f27" data-discover="true">163ef97 commit 8d13bd9

File tree

3 files changed

+125
-92
lines changed

3 files changed

+125
-92
lines changed

docs/plugins/html/WebIndexPlugin.md

Lines changed: 47 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -21,29 +21,47 @@ fuse.plugin(
2121
)
2222
```
2323

24+
Include in the `plugins` array property in the `init` configuration
25+
26+
```js
27+
fuse.init({
28+
homeDir: 'src',
29+
output: 'build/$name.js',
30+
target: 'browser',
31+
plugins: [
32+
WebIndexPlugin()
33+
]
34+
});
35+
```
36+
2437
## Options
2538

26-
| Name | Meaning |
27-
| ------------- | ------------- |
28-
| ` title ` | Sets the title |
29-
| ` bundles ` | Provide a list of bundle names (if not set all registered bundles are through) |
30-
| ` path ` | The relative url bundles are served from. Default is `/`. Empty is set with `.` |
31-
| ` template ` | Provide a path to your own template |
32-
| ` engine ` | You can use conslidate plugin by providing an engine name |
33-
| ` locals ` | Pass variable to consolidate module |
34-
| ` templateString ` | Provide your own template as a string |
35-
| ` target ` | The main filename. Default is `index.html` |
36-
| ` resolve ` | `resolve ?: {(output : UserOutput) : string}` Allows to completely override the output |
37-
| `pre ` | `{ relType: 'fetch' | 'load' }` Config object to either preload or prefetch the output javascript bundles in the head of the document |
38-
| ` appendBundles ` | Append $bundles to provided template |
39-
| ` async ` | Provide `async` attribute to `<script>` tags (boolean) |
40-
| ` scriptAttributes ` | Provide additional attribute(s) to `<script>` tags (string) |
41-
42-
43-
note: If you specify template and templateString then template will take precedent
39+
> Note: If a `template` and `templateString` option are both specified, then the `template`
40+
> will take precedent.
41+
> If no default value is specified below, the option will not be applied.
42+
43+
| Name | Type | Description | Default |
44+
| -----| ---- | ----------- | -------
45+
| `appendBundles` | `boolean` | Append the $bundles to provided template | `true` |
46+
| `async` | `boolean`| Adds the `async` attribute to the `<script />` tags that link the output javascript bundles | `false` |
47+
| `author` | `string` | Set the the `content` attribute of a `<meta name="author"` tag |
48+
| `bundles` | `string[]` | Provide a list of bundle names. (if not set all registered bundles are through) |
49+
| `charset` | `string` | Set the the `charset` attribute of a `<meta />` tag |
50+
| `description` | `string` | Set the the `content` attribute of a `<meta name="description" />` tag |
51+
| `emitBundles` | `(bundles: string[]) => string` | Function that returns the list of paths to each output bundle |
52+
| `engine` | `string` | You can use conslidate plugin by providing an engine name |
53+
| `keywords`| `string` | Set the the `content` attribute of a `<meta name="keywords" />` tag |
54+
| `locals` | `{ [key: string]: any }` | Pass variable to consolidate module |
55+
| `path` | `string` | The relative url that bundles are served from. Empty is set with `"."` | `"/"` |
56+
| `pre` | `string` | Must be specified using either `'fetch'` or `'load'`. Adds `<link />` tags with `preload` or `prefetch` attributes for each of the output javascript bundles. The tags will be injected into the head of the html document or where specified by the `$pre` macro |
57+
| `resolve` | `resolve ?: {(output : UserOutput) : string}` | Function that allows to completely override the output |
58+
| `target` | `string` | The name of the output `.html` file | `index.html` |
59+
| `template`| `string`| Provide a path to your own template |
60+
| `templateString` | `string` | Provide your own template |
61+
| `title` | `string` | Sets the title of the generated HTML document |
4462

4563
### Resolve example
46-
`resolve` option allows you to completely override the path
64+
The `resolve` option allows you to completely override the path.
4765

4866
```js
4967
WebIndexPlugin({
@@ -54,12 +72,15 @@ WebIndexPlugin({
5472

5573
## Custom template
5674

57-
A custom template has the following macro available:
75+
A custom template has the following macros available:
5876

59-
| Symbol | Meaning |
77+
| Macro | Meaning |
6078
| ------------- | ------------- |
61-
| ` $title ` | Html Title |
62-
| ` $bundles ` | A list of script tags |
63-
| ` $css ` | A list of styles tags |
64-
65-
github_example: vendor-splitting
79+
| `$author` | Define where the author meta tags will be injected into the html document |
80+
| `$bundles` | A list of script tags |
81+
| `$charset` | Define where the charset meta tags will be injected into the html document |
82+
| `$css` | A list of styles tags |
83+
| `$description` | Define where the description meta tags will be injected into the html document |
84+
| `$keywords` | Define where the keywords meta tags will be injected into the html document |
85+
| `$pre` | Define where the prefetch/preload link tags will be injected into the html document |
86+
| `$title` | Html Title |

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -124,4 +124,4 @@
124124
"path": "cz-conventional-changelog"
125125
}
126126
}
127-
}
127+
}

src/plugins/WebIndexPlugin.ts

Lines changed: 77 additions & 65 deletions
Original file line numberDiff line numberDiff line change
@@ -1,78 +1,86 @@
1-
import { } from "../core/File";
2-
import { Plugin } from "../core/WorkflowContext";
3-
import { BundleProducer } from "../core/BundleProducer";
4-
import * as fs from "fs";
5-
import { ensureAbsolutePath, joinFuseBoxPath } from "../Utils";
6-
import { UserOutput } from "../core/UserOutput";
7-
import * as path from "path";
1+
import * as fs from 'fs';
2+
import * as path from 'path';
3+
4+
import { } from '../core/File';
5+
import { Plugin } from '../core/WorkflowContext';
6+
import { BundleProducer } from '../core/BundleProducer';
7+
import { UserOutput } from '../core/UserOutput';
8+
import { ensureAbsolutePath, joinFuseBoxPath } from '../Utils';
89

910
export interface IndexPluginOptions {
10-
title?: string;
11+
appendBundles?: boolean;
12+
async?: boolean;
13+
author?: string;
14+
bundles?: string[];
1115
charset?: string;
1216
description?: string;
17+
emitBundles?: (bundles: string[]) => string;
18+
engine?: string;
1319
keywords?: string;
14-
author?: string;
15-
bundles?: string[];
20+
locals?: { [key: string]: any }
1621
path?: string;
22+
pre?: string;
23+
resolve?: { (output: UserOutput): string };
24+
scriptAttributes?: string;
1725
target?: string;
1826
template?: string;
1927
templateString?: string;
20-
appendBundles?: boolean;
21-
engine?: string;
22-
locals?: {[key:string]: any}
23-
async?: boolean;
24-
scriptAttributes?: string;
25-
pre?: { relType: 'fetch' | 'load' };
26-
resolve?: { (output: UserOutput): string };
27-
emitBundles?: (bundles: string[]) => string;
28+
title?: string;
2829
}
30+
31+
const validPreAttrs = ['fetch', 'load'];
32+
2933
export class WebIndexPluginClass implements Plugin {
3034
constructor(public opts?: IndexPluginOptions) {
3135

3236
}
3337

3438
private async generate(producer: BundleProducer) {
39+
const bundles = producer.sortBundles();
3540
let bundlePaths = [];
36-
let bundles = producer.sortBundles();
37-
bundles.forEach((bundle) => {
41+
42+
bundles.forEach(bundle => {
3843
let pass = true;
39-
if (this.opts.bundles) {
40-
if (this.opts.bundles.indexOf(bundle.name) === -1) {
41-
pass = false;
42-
}
44+
45+
if (this.opts.bundles && !this.opts.bundles.includes(bundle.name)) {
46+
pass = false;
4347
}
48+
4449
pass = pass && bundle.webIndexed;
50+
4551
if (pass) {
4652
const output = bundle.context.output;
4753
if (output && output.lastPrimaryOutput) {
4854
if (this.opts.resolve) {
49-
bundlePaths.push(this.opts.resolve(output))
55+
bundlePaths.push(this.opts.resolve(output));
5056
} else {
5157
bundlePaths.push(
52-
joinFuseBoxPath(this.opts.path ? this.opts.path : "/", output.folderFromBundleName || "/",
58+
joinFuseBoxPath(this.opts.path ? this.opts.path : '/', output.folderFromBundleName || '/',
5359
output.lastPrimaryOutput.filename)
54-
)
60+
);
5561
}
5662
}
57-
5863
}
5964
});
6065

6166

62-
let html = this.opts.templateString || `<!DOCTYPE html><html>
63-
<head>
64-
<title>$title</title>
65-
$charset
66-
$description
67-
$keywords
68-
$preload
69-
$author
70-
$css
71-
</head>
72-
<body>
73-
$bundles
74-
</body>
75-
</html>`;
67+
let html = this.opts.templateString
68+
|| `<!doctype html>
69+
<html>
70+
<head>
71+
<title>$title</title>
72+
$charset
73+
$description
74+
$keywords
75+
$pre
76+
$author
77+
$css
78+
</head>
79+
<body>
80+
$bundles
81+
</body>
82+
</html>`;
83+
7684
if (this.opts.engine) {
7785
const engine = this.opts.engine;
7886
const consolidate = require('consolidate');
@@ -87,13 +95,13 @@ $bundles
8795
html = await consolidate[engine](filePath, this.opts.locals || {});
8896
} else {
8997
if (this.opts.template) {
90-
let filePath = ensureAbsolutePath(this.opts.template);
91-
html = fs.readFileSync(filePath).toString();
98+
const pathToTemplate = ensureAbsolutePath(this.opts.template);
99+
html = fs.readFileSync(pathToTemplate, 'UTF-8')
92100

93-
if (this.opts.appendBundles && html.indexOf('$bundles') === -1) {
94-
if (html.indexOf('</body>') !== -1) {
101+
if (this.opts.appendBundles && !html.includes('$bundles')) {
102+
if (!html.includes('</body>')) {
95103
html = html.replace('</body>', '$bundles</body>');
96-
} else if (html.indexOf('</head>') !== -1) {
104+
} else if (!html.includes('</head>')) {
97105
html = html.replace('</head>', '$bundles</head>');
98106
} else {
99107
html = `${html}$bundles`;
@@ -102,40 +110,44 @@ $bundles
102110
}
103111
}
104112

105-
let jsTags = this.opts.emitBundles
113+
const jsTags = this.opts.emitBundles
106114
? this.opts.emitBundles(bundlePaths)
107115
: bundlePaths.map(bundle => `<script ${this.opts.async ? 'async' : ''} ${this.opts.scriptAttributes ? this.opts.scriptAttributes : ''} type="text/javascript" src="${bundle}"></script>`).join('\n');
108116

109-
let preloadTags;
110-
if (this.opts.pre) {
111-
preloadTags = bundlePaths.map(bundle =>
112-
`<link rel="pre${this.opts.pre.relType}" as="script" href="${bundle}">`
113-
).join("\n");
117+
let preLinkTags;
118+
if (this.opts.pre && validPreAttrs.includes[this.opts.pre]) {
119+
preLinkTags = bundlePaths.map(bundle =>
120+
`<link rel="pre${this.opts.pre}" as="script" href="${bundle}">`
121+
).join('\n');
114122
}
123+
115124
let cssInjection = [];
116125
if (producer.injectedCSSFiles.size > 0) {
117-
producer.injectedCSSFiles.forEach(f => {
118-
const resolvedFile = this.opts.path ? path.join(this.opts.path, f) : path.join("/", f);
119-
cssInjection.push(`<link rel="stylesheet" href="${resolvedFile}"/>`)
120-
})
126+
producer.injectedCSSFiles.forEach(file => {
127+
const resolvedFile = this.opts.path ? path.join(this.opts.path, file) : path.join('/', file);
128+
cssInjection.push(`<link rel="stylesheet" href="${resolvedFile}"/>`);
129+
});
121130
}
122131

123132
let macro = {
124-
css: cssInjection.join('\n'),
125-
title: this.opts.title ? this.opts.title : "",
126-
charset: this.opts.charset ? `<meta charset="${this.opts.charset}">` : "",
127-
description: this.opts.description ? `<meta name="description" content="${this.opts.description}">` : "",
128-
keywords: this.opts.keywords ? `<meta name="keywords" content="${this.opts.keywords}">` : "",
129-
author: this.opts.author ? `<meta name="author" content="${this.opts.author}">` : "",
133+
author: this.opts.author ? `<meta name="author" content="${this.opts.author}">` : '',
130134
bundles: jsTags,
131-
preload: this.opts.pre ? preloadTags : "",
135+
charset: this.opts.charset ? `<meta charset="${this.opts.charset}">` : '',
136+
css: cssInjection.join('\n'),
137+
description: this.opts.description ? `<meta name="description" content="${this.opts.description}">` : '',
138+
keywords: this.opts.keywords ? `<meta name="keywords" content="${this.opts.keywords}">` : '',
139+
pre: this.opts.pre ? preLinkTags : '',
140+
title: this.opts.title ? this.opts.title : '',
132141
}
142+
133143
for (let key in macro) {
134144
html = html.replace('$' + key, macro[key])
135145
}
146+
136147
producer.fuse.context
137-
.output.writeToOutputFolder(this.opts.target || "index.html", html);
148+
.output.writeToOutputFolder(this.opts.target || 'index.html', html);
138149
}
150+
139151
producerEnd(producer: BundleProducer) {
140152
this.generate(producer);
141153
producer.sharedEvents.on('file-changed', () => {

0 commit comments

Comments
 (0)
0