jalla 1.0.0-4 → 1.0.0-40
Sign up to get free protection for your applications and to get access to all the features.
- package/README.md +34 -17
- package/bin.js +18 -15
- package/index.js +46 -33
- package/lib/app.js +49 -19
- package/lib/build.js +13 -129
- package/lib/compile.js +6 -3
- package/lib/document.js +77 -50
- package/lib/manifest.js +3 -5
- package/lib/pipeline.js +13 -10
- package/lib/render.js +53 -33
- package/lib/script.js +51 -30
- package/lib/service-worker.js +14 -7
- package/lib/style.js +7 -2
- package/lib/ui.js +15 -8
- package/package.json +46 -46
package/lib/document.js
CHANGED
@@ -3,15 +3,16 @@ var posthtmlify = require('posthtmlify')
|
|
3
3
|
var documentify = require('documentify')
|
4
4
|
var { Readable } = require('stream')
|
5
5
|
var hyperstream = require('hstream')
|
6
|
+
var caniuse = require('caniuse-api')
|
7
|
+
var purgecss = require('purgecss')
|
6
8
|
var through = require('through2')
|
7
9
|
var resolve = require('resolve')
|
8
|
-
var
|
9
|
-
var dedent = require('dedent')
|
10
|
+
var jsesc = require('jsesc')
|
10
11
|
var path = require('path')
|
11
12
|
|
12
13
|
module.exports = document
|
13
14
|
|
14
|
-
var TEMPLATE =
|
15
|
+
var TEMPLATE = `
|
15
16
|
<!doctype html>
|
16
17
|
<html>
|
17
18
|
<head></head>
|
@@ -20,65 +21,80 @@ var TEMPLATE = dedent`
|
|
20
21
|
`
|
21
22
|
|
22
23
|
function document (body, state, app, cb) {
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
24
|
+
resolve('./index', {
|
25
|
+
basedir: path.dirname(app.entry),
|
26
|
+
extensions: ['.html']
|
27
|
+
}, function (err, file) {
|
28
|
+
try {
|
29
|
+
if (err) cb(null, render(null, TEMPLATE))
|
30
|
+
else cb(null, render(file, null))
|
31
|
+
} catch (err) {
|
32
|
+
cb(err)
|
33
|
+
}
|
28
34
|
})
|
29
35
|
|
30
36
|
function render (template, html) {
|
31
|
-
var selector = require(app.entry).selector
|
37
|
+
var selector = require(app.entry).selector
|
32
38
|
var d = documentify(template, html)
|
33
39
|
|
34
40
|
d.transform(function () {
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
})
|
41
|
+
var opts = { html: { lang: state.language || 'en' } }
|
42
|
+
if (selector && body) opts[selector] = { _replaceHtml: body }
|
43
|
+
return hyperstream(opts)
|
39
44
|
})
|
40
45
|
|
41
46
|
d.transform((str) => hyperstream({ body: { _appendHtml: str } }), `
|
42
|
-
<script>window.initialState = ${stringify(state)}</script>
|
47
|
+
<script>window.initialState = JSON.parse(${stringify(state)})</script>
|
43
48
|
`)
|
44
49
|
|
50
|
+
/**
|
51
|
+
* The following transforms are prepended in reverse order to ensure that
|
52
|
+
* they come _before_ possible custom html head elements
|
53
|
+
*/
|
54
|
+
|
45
55
|
if (app.env === 'development') {
|
46
56
|
d.transform(prependToHead, `
|
47
|
-
|
48
|
-
|
57
|
+
<script src="${app.context.assets.get('bundle.js').url}" defer></script>
|
58
|
+
<link rel="stylesheet" href="${app.context.assets.get('bundle.css').url}">
|
49
59
|
`)
|
50
60
|
} else {
|
51
|
-
|
52
|
-
|
53
|
-
|
61
|
+
const script = app.context.assets.get('bundle.js')
|
62
|
+
const styles = app.context.assets.get('bundle.css')
|
63
|
+
const features = process.env.POLYFILL_FEATURES
|
64
|
+
|
65
|
+
if (!caniuse.isSupported('link-rel-preload', app.browsers.join(','))) {
|
66
|
+
d.transform(prependToHead, `
|
67
|
+
<script>
|
68
|
+
(function (tokens) {
|
69
|
+
try {
|
70
|
+
var supports = tokens.supports('preload');
|
71
|
+
} catch (e) {}
|
72
|
+
if (supports) return;
|
73
|
+
var links = document.querySelectorAll('link[rel=preload][as=style]');
|
74
|
+
for (var i = 0, len = links.length; i < len; i++) {
|
75
|
+
var link = document.createElement('link');
|
76
|
+
link.rel = 'stylesheet';
|
77
|
+
link.href = links[i].href;
|
78
|
+
document.head.append(link);
|
79
|
+
}
|
80
|
+
}(document.createElement('link').relList))
|
81
|
+
</script>
|
82
|
+
`)
|
83
|
+
}
|
54
84
|
|
55
|
-
let features = process.env.POLYFILL_FEATURES
|
56
85
|
d.transform(prependToHead, `
|
57
86
|
<link rel="preload" as="style" href="${styles.url}" onload="this.rel='stylesheet'">
|
58
87
|
<script src="https://polyfill.io/v3/polyfill.min.js${features ? `?features=${features}` : ''}"></script>
|
59
88
|
<script src="${script.url}" defer></script>
|
60
|
-
<script>
|
61
|
-
(function (tokens) {
|
62
|
-
try {
|
63
|
-
var supports = tokens.supports('preload');
|
64
|
-
} catch (e) {}
|
65
|
-
if (supports) return;
|
66
|
-
var links = document.querySelectorAll('link[rel=preload][as=style]');
|
67
|
-
for (var i = 0, len = links.length; i < len; i++) {
|
68
|
-
var link = document.createElement('link');
|
69
|
-
link.rel = 'stylesheet';
|
70
|
-
link.href = links[i].href;
|
71
|
-
document.head.append(link);
|
72
|
-
}
|
73
|
-
}(document.createElement('link').relList))
|
74
|
-
</script>
|
75
89
|
`)
|
90
|
+
|
91
|
+
d.transform(prependCriticalCSS(styles.read.bind(styles)))
|
76
92
|
}
|
77
93
|
|
78
94
|
if (state.meta) {
|
79
|
-
|
95
|
+
const keys = Object.keys(state.meta)
|
80
96
|
if (keys.length) {
|
81
|
-
|
97
|
+
const tags = keys.map(function (key) {
|
82
98
|
if (key === 'title') return
|
83
99
|
var type = key.indexOf('og:') !== -1 ? 'property' : 'name'
|
84
100
|
var value = state.meta[key]
|
@@ -98,7 +114,7 @@ function document (body, state, app, cb) {
|
|
98
114
|
`)
|
99
115
|
|
100
116
|
if (state.title) {
|
101
|
-
|
117
|
+
const title = state.title.trim().replace(/\n/g, '')
|
102
118
|
d.transform(prependToHead, `<title>${title}</title>`)
|
103
119
|
}
|
104
120
|
|
@@ -122,13 +138,13 @@ function document (body, state, app, cb) {
|
|
122
138
|
}
|
123
139
|
}
|
124
140
|
|
125
|
-
// stringify
|
126
|
-
// see: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/JSON/stringify#Issue_with_plain_JSON.stringify_for_use_as_JavaScript
|
141
|
+
// stringify data as safely escaped JSON
|
127
142
|
// obj -> str
|
128
|
-
function stringify (
|
129
|
-
return JSON.stringify(
|
130
|
-
|
131
|
-
|
143
|
+
function stringify (data) {
|
144
|
+
return jsesc(JSON.stringify(data), {
|
145
|
+
json: true,
|
146
|
+
isScriptContext: true
|
147
|
+
})
|
132
148
|
}
|
133
149
|
|
134
150
|
// create documentify transform adding content to `head`
|
@@ -139,7 +155,7 @@ function prependToHead (str) {
|
|
139
155
|
|
140
156
|
// create documentify transform inlining critical CSS
|
141
157
|
// str -> Stream
|
142
|
-
function
|
158
|
+
function prependCriticalCSS (getStyles) {
|
143
159
|
var html = ''
|
144
160
|
|
145
161
|
return function () {
|
@@ -160,20 +176,31 @@ function inlineCriticalCSS (getStyles) {
|
|
160
176
|
var self = this
|
161
177
|
|
162
178
|
getStyles().then(function (css) {
|
163
|
-
|
164
|
-
|
179
|
+
css = css.toString().replace(/\/\*#\s*sourceMappingURL=.+?\s*\*\//g, '')
|
180
|
+
return new purgecss.PurgeCSS().purge({
|
181
|
+
content: [{ raw: html, extension: 'html' }],
|
182
|
+
css: [{ raw: css }]
|
183
|
+
}).then(function (result) {
|
184
|
+
return result.reduce((acc, { css }) => acc + css, '')
|
185
|
+
})
|
186
|
+
}).then(function (css) {
|
187
|
+
var prepend = hyperstream({
|
165
188
|
head: {
|
166
|
-
|
189
|
+
_prependHtml: `<style>${css}</style>`
|
167
190
|
}
|
168
191
|
})
|
169
192
|
var stream = new Readable()
|
170
193
|
stream._read = Function.prototype
|
171
194
|
|
172
195
|
// pipe the collected html through hyperstream forwarding to self
|
173
|
-
stream.pipe(
|
196
|
+
stream.pipe(prepend).pipe(through(write, end))
|
174
197
|
stream.push(html)
|
175
198
|
stream.push(null)
|
176
|
-
}
|
199
|
+
}).catch(function () {
|
200
|
+
// fail silently and skip inline styles
|
201
|
+
self.push(html)
|
202
|
+
return cb()
|
203
|
+
})
|
177
204
|
|
178
205
|
// collect the resulting html with inlined CSS
|
179
206
|
// (str, str, fn) -> void
|
package/lib/manifest.js
CHANGED
@@ -10,14 +10,12 @@ function manifest (state, emit) {
|
|
10
10
|
try {
|
11
11
|
emit('progress', 'manifest.json', 0)
|
12
12
|
|
13
|
-
var
|
14
|
-
var name =
|
15
|
-
return str[0].toUpperCase() + str.substr(1)
|
16
|
-
}).join(' ')
|
13
|
+
var res = await readPkgUp({ cwd: path.dirname(state.entry) })
|
14
|
+
var { name } = res.packageJson
|
17
15
|
|
18
16
|
var buff = Buffer.from(JSON.stringify({
|
19
17
|
name: name,
|
20
|
-
short_name: name.length > 12 ? name.
|
18
|
+
short_name: name.length > 12 ? name.substr(0, 12) + '…' : name,
|
21
19
|
start_url: '/',
|
22
20
|
display: 'minimal-ui',
|
23
21
|
background_color: '#fff',
|
package/lib/pipeline.js
CHANGED
@@ -43,7 +43,7 @@ module.exports = class Pipeline extends Nanobus {
|
|
43
43
|
state.deps.add(dep)
|
44
44
|
})
|
45
45
|
emitter.on('reset', function () {
|
46
|
-
for (
|
46
|
+
for (const dep of deps) state.deps.delete(dep)
|
47
47
|
})
|
48
48
|
emitter.on('remove', function (id) {
|
49
49
|
self.assets.delete(id)
|
@@ -57,15 +57,15 @@ module.exports = class Pipeline extends Nanobus {
|
|
57
57
|
|
58
58
|
if (meta.map) {
|
59
59
|
// create an asset for the source map
|
60
|
-
|
60
|
+
const mapAsset = add(id + '.map', meta.map, {
|
61
61
|
mime: 'application/json'
|
62
62
|
})
|
63
63
|
|
64
64
|
// add map comment to buffer
|
65
|
-
|
65
|
+
const map = sourcemap.generateMapFileComment(mapAsset.url, {
|
66
66
|
multiline: /\.css$/.test(id)
|
67
67
|
})
|
68
|
-
|
68
|
+
const src = buff.toString()
|
69
69
|
buff = Buffer.from(src.replace(/\n?$/, '\n' + map))
|
70
70
|
}
|
71
71
|
|
@@ -80,7 +80,7 @@ module.exports = class Pipeline extends Nanobus {
|
|
80
80
|
}
|
81
81
|
|
82
82
|
if (!meta.static && state.env !== 'development') {
|
83
|
-
|
83
|
+
const hex = hash.toString('hex')
|
84
84
|
asset.url = base + hex.slice(0, 16) + '.' + path.basename(id)
|
85
85
|
} else {
|
86
86
|
asset.url = base + id
|
@@ -129,8 +129,7 @@ module.exports = class Pipeline extends Nanobus {
|
|
129
129
|
async function read () {
|
130
130
|
if (busy.has(this.id)) {
|
131
131
|
// wait for bundling to finish
|
132
|
-
|
133
|
-
await defer(`${this.label}:end`)
|
132
|
+
await new Promise((resolve) => self.once(`${this.label}:end`, resolve))
|
134
133
|
}
|
135
134
|
|
136
135
|
if (this.buffer) return this.buffer
|
@@ -144,16 +143,20 @@ module.exports = class Pipeline extends Nanobus {
|
|
144
143
|
if (step) return step.hooks
|
145
144
|
}
|
146
145
|
|
147
|
-
middleware () {
|
146
|
+
middleware (state) {
|
148
147
|
var self = this
|
149
148
|
|
150
149
|
return async function (ctx, next) {
|
151
150
|
if (ctx.body) return next()
|
152
151
|
|
153
|
-
for (
|
152
|
+
for (const asset of self.assets.values()) {
|
154
153
|
if (asset.url === ctx.path) {
|
155
154
|
ctx.body = await asset.read()
|
156
155
|
ctx.type = asset.mime || mime.getType(asset.url)
|
156
|
+
const cache = state.env !== 'development' && !state.watch
|
157
|
+
const maxAge = cache ? 60 * 60 * 24 * 365 : 0
|
158
|
+
const value = `${cache ? 'public, ' : ''}max-age=${maxAge}`
|
159
|
+
ctx.set('Cache-Control', value)
|
157
160
|
return
|
158
161
|
}
|
159
162
|
}
|
@@ -181,7 +184,7 @@ module.exports = class Pipeline extends Nanobus {
|
|
181
184
|
}
|
182
185
|
|
183
186
|
* [Symbol.iterator] () {
|
184
|
-
for (
|
187
|
+
for (const asset of this.assets.values()) {
|
185
188
|
yield asset
|
186
189
|
}
|
187
190
|
}
|
package/lib/render.js
CHANGED
@@ -1,50 +1,70 @@
|
|
1
1
|
var path = require('path')
|
2
|
+
var concat = require('concat-stream')
|
2
3
|
var document = require('./document')
|
3
4
|
|
5
|
+
var FONT = /\.(woff2?|eot|ttf)$/
|
6
|
+
|
4
7
|
module.exports = render
|
5
8
|
|
6
9
|
function render (app) {
|
7
10
|
return async function render (ctx, next) {
|
8
11
|
try {
|
9
12
|
await next()
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
ctx.type = 'text/html'
|
31
|
-
ctx.status = isNaN(+state.status) ? 200 : state.status
|
32
|
-
ctx.body = await new Promise(function (resolve, reject) {
|
33
|
-
document(html, state, app, function (err, stream) {
|
34
|
-
if (err) return reject(err)
|
35
|
-
resolve(stream)
|
36
|
-
})
|
13
|
+
|
14
|
+
if (ctx.body || !ctx.accepts('html') || ctx.response.get('Location')) {
|
15
|
+
return
|
16
|
+
}
|
17
|
+
|
18
|
+
const href = path.join(app.base, ctx.url).replace(/\/$/, '') || '/'
|
19
|
+
const client = require(app.entry)
|
20
|
+
const state = Object.assign({
|
21
|
+
prefetch: [],
|
22
|
+
req: ctx.req,
|
23
|
+
res: ctx.res
|
24
|
+
}, ctx.state)
|
25
|
+
|
26
|
+
// first render pass, collect prefetch operations
|
27
|
+
client.toString(href, state)
|
28
|
+
|
29
|
+
await Promise.all(state.prefetch.map(function (p) {
|
30
|
+
return p.catch(function (err) {
|
31
|
+
if (err.status) state.status = err.status
|
37
32
|
})
|
33
|
+
}))
|
34
|
+
delete state.prefetch
|
35
|
+
delete state.req
|
36
|
+
delete state.res
|
37
|
+
|
38
|
+
// second render pass
|
39
|
+
const html = client.toString(href, state)
|
38
40
|
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
41
|
+
if (app.env !== 'development') {
|
42
|
+
const fonts = []
|
43
|
+
for (const [id, asset] of ctx.assets) {
|
44
|
+
if (FONT.test(id)) {
|
45
|
+
fonts.push(`<${asset.url}>; rel=preload; crossorigin=anonymous; as=font`)
|
46
|
+
}
|
44
47
|
}
|
48
|
+
|
49
|
+
// push primary bundles and font files
|
50
|
+
ctx.append('Link', [
|
51
|
+
`<${ctx.assets.get('bundle.js').url}>; rel=preload; as=script`,
|
52
|
+
`<${ctx.assets.get('bundle.css').url}>; rel=preload; as=style`
|
53
|
+
].concat(fonts))
|
45
54
|
}
|
55
|
+
|
56
|
+
ctx.type = 'text/html'
|
57
|
+
ctx.status = isNaN(+state.status) ? 200 : state.status
|
58
|
+
ctx.body = await new Promise(function (resolve, reject) {
|
59
|
+
document(html, state, app, function (err, stream) {
|
60
|
+
if (err) return reject(err)
|
61
|
+
stream.pipe(concat({ encoding: 'buffer' }, function (buff) {
|
62
|
+
resolve(buff)
|
63
|
+
}))
|
64
|
+
})
|
65
|
+
})
|
46
66
|
} catch (err) {
|
47
|
-
ctx.throw(err.status ||
|
67
|
+
ctx.throw(err.status || 500, err)
|
48
68
|
}
|
49
69
|
}
|
50
70
|
}
|
package/lib/script.js
CHANGED
@@ -1,28 +1,20 @@
|
|
1
1
|
var path = require('path')
|
2
2
|
var brfs = require('brfs')
|
3
3
|
var tinyify = require('tinyify')
|
4
|
+
var tfilter = require('tfilter')
|
4
5
|
var through = require('through2')
|
5
6
|
var nanohtml = require('nanohtml')
|
6
7
|
var babelify = require('babelify')
|
7
8
|
var watchify = require('watchify')
|
8
9
|
var caniuse = require('caniuse-api')
|
9
|
-
var envify = require('envify/custom')
|
10
10
|
var concat = require('concat-stream')
|
11
11
|
var browserify = require('browserify')
|
12
|
-
var browserslist = require('browserslist')
|
13
12
|
var splitRequire = require('split-require')
|
14
13
|
var sourcemap = require('convert-source-map')
|
14
|
+
var envify = require('@goto-bus-stop/envify')
|
15
15
|
var babelPresetEnv = require('@babel/preset-env')
|
16
16
|
var inject = require('./inject')
|
17
17
|
|
18
|
-
var DEFAULT_BROWSERS = [
|
19
|
-
'last 2 Chrome versions',
|
20
|
-
'last 2 Firefox versions',
|
21
|
-
'last 2 Safari versions',
|
22
|
-
'last 2 Edge versions',
|
23
|
-
'> 1%'
|
24
|
-
]
|
25
|
-
|
26
18
|
module.exports = script
|
27
19
|
|
28
20
|
function script (state, emit) {
|
@@ -38,11 +30,12 @@ function script (state, emit) {
|
|
38
30
|
|
39
31
|
b.plugin(splitRequire, {
|
40
32
|
filename: function (record) {
|
41
|
-
var
|
33
|
+
var extension = path.extname(record.sourceFile)
|
34
|
+
var basename = path.basename(record.sourceFile, extension)
|
42
35
|
var isIndex = basename === 'index'
|
43
36
|
var id = basename
|
44
37
|
if (isIndex) id = path.dirname(record.sourceFile).split('/').slice(-1)[0]
|
45
|
-
return `bundle-${record.index}-${id}
|
38
|
+
return `bundle-${record.index}-${id}${extension}`
|
46
39
|
},
|
47
40
|
public: state.base + '/',
|
48
41
|
output: bundleDynamicBundle
|
@@ -55,33 +48,55 @@ function script (state, emit) {
|
|
55
48
|
var env = Object.assign({ NODE_ENV: state.env }, process.env)
|
56
49
|
|
57
50
|
if (state.env === 'development') {
|
58
|
-
b.transform(babelify, {
|
51
|
+
b.transform(tfilter(babelify, { filter: include }), {
|
52
|
+
plugins: ['dynamic-import-split-require']
|
53
|
+
})
|
59
54
|
b.transform(inject('source-map-support/register', state.entry))
|
60
|
-
b.transform(brfs
|
61
|
-
|
55
|
+
b.transform(tfilter(brfs, {
|
56
|
+
filter (file) {
|
57
|
+
return !file.includes('source-map-support') && include(file)
|
58
|
+
}
|
59
|
+
}), { global: true })
|
60
|
+
b.transform(tfilter(envify, { filter: include }), env)
|
62
61
|
} else {
|
63
|
-
let dir = path.dirname(state.entry)
|
64
|
-
let browsers = browserslist.loadConfig({ path: dir, env: env.NODE_ENV })
|
65
|
-
if (!browsers) browsers = DEFAULT_BROWSERS
|
66
|
-
|
67
62
|
// compile dynamic imports but nothing else to preserve template literals
|
68
|
-
b.transform(babelify, {
|
63
|
+
b.transform(tfilter(babelify, { filter: include }), {
|
64
|
+
plugins: ['dynamic-import-split-require']
|
65
|
+
})
|
69
66
|
|
70
67
|
// include regenerator runtime to support transpiled async/await
|
71
|
-
if (!caniuse.isSupported('async-functions', browsers.join(','))) {
|
72
|
-
|
68
|
+
if (!caniuse.isSupported('async-functions', state.browsers.join(','))) {
|
69
|
+
const regenerator = require.resolve('regenerator-runtime/runtime')
|
73
70
|
b.transform(inject(regenerator, state.entry))
|
74
71
|
}
|
75
72
|
|
76
|
-
b.transform(nanohtml)
|
77
|
-
b.transform(
|
73
|
+
b.transform(tfilter(nanohtml, { filter: include }))
|
74
|
+
b.transform(tfilter(nanohtml, {
|
75
|
+
filter (file) {
|
76
|
+
return file.includes('node_modules') && include(file)
|
77
|
+
}
|
78
|
+
}), { global: true })
|
79
|
+
b.transform(tfilter(babelify, {
|
80
|
+
filter (file) {
|
81
|
+
return file.includes('node_modules') && include(file)
|
82
|
+
}
|
83
|
+
}), {
|
84
|
+
global: true,
|
85
|
+
babelrc: false,
|
78
86
|
presets: [
|
79
87
|
[babelPresetEnv, {
|
80
|
-
targets: { browsers: browsers }
|
88
|
+
targets: { browsers: state.browsers }
|
81
89
|
}]
|
82
90
|
]
|
83
91
|
})
|
84
|
-
b.transform(
|
92
|
+
b.transform(tfilter(babelify, { filter: include }), {
|
93
|
+
presets: [
|
94
|
+
[babelPresetEnv, {
|
95
|
+
targets: { browsers: state.browsers }
|
96
|
+
}]
|
97
|
+
]
|
98
|
+
})
|
99
|
+
b.transform(tfilter(brfs, { filter: include }), { global: true })
|
85
100
|
b.plugin(tinyify, { env })
|
86
101
|
}
|
87
102
|
|
@@ -104,6 +119,12 @@ function script (state, emit) {
|
|
104
119
|
}))
|
105
120
|
}
|
106
121
|
|
122
|
+
// test if file should be included in transform
|
123
|
+
// str -> bool
|
124
|
+
function include (file) {
|
125
|
+
return !state.skip(file)
|
126
|
+
}
|
127
|
+
|
107
128
|
// emit progress on pipeline reset/pending
|
108
129
|
// () -> void
|
109
130
|
function onreset () {
|
@@ -125,7 +146,7 @@ function script (state, emit) {
|
|
125
146
|
// handle dynamic bundle
|
126
147
|
// str -> stream.Writable
|
127
148
|
function bundleDynamicBundle (name) {
|
128
|
-
|
149
|
+
const stream = concat({ encoding: 'buffer' }, function (bundle) {
|
129
150
|
onbundle(bundle, name)
|
130
151
|
var asset = state.assets.get(name)
|
131
152
|
stream.emit('name', asset.url)
|
@@ -141,9 +162,9 @@ function script (state, emit) {
|
|
141
162
|
mime: 'application/javascript'
|
142
163
|
})
|
143
164
|
} else {
|
144
|
-
|
145
|
-
|
146
|
-
|
165
|
+
const src = bundle.toString()
|
166
|
+
const map = sourcemap.fromSource(src)
|
167
|
+
const buff = Buffer.from(sourcemap.removeComments(src))
|
147
168
|
emit('asset', name, buff, {
|
148
169
|
mime: 'application/javascript',
|
149
170
|
map: Buffer.from(map.toJSON())
|
package/lib/service-worker.js
CHANGED
@@ -1,12 +1,13 @@
|
|
1
1
|
var path = require('path')
|
2
2
|
var brfs = require('brfs')
|
3
|
+
var tfilter = require('tfilter')
|
3
4
|
var tinyify = require('tinyify')
|
4
5
|
var through = require('through2')
|
5
6
|
var watchify = require('watchify')
|
6
7
|
var concat = require('concat-stream')
|
7
|
-
var envify = require('envify/custom')
|
8
8
|
var browserify = require('browserify')
|
9
9
|
var sourcemap = require('convert-source-map')
|
10
|
+
var envify = require('@goto-bus-stop/envify')
|
10
11
|
var inject = require('./inject')
|
11
12
|
|
12
13
|
module.exports = serviceWorker
|
@@ -28,8 +29,8 @@ function serviceWorker (state, emit) {
|
|
28
29
|
b.on('reset', capture)
|
29
30
|
|
30
31
|
// run envify regardless due to tinyify loosing the reference to env
|
31
|
-
b.transform(envify
|
32
|
-
b.transform(brfs)
|
32
|
+
b.transform(tfilter(envify, { filter: include }), env)
|
33
|
+
b.transform(tfilter(brfs, { filter: include }))
|
33
34
|
|
34
35
|
if (state.env === 'development') {
|
35
36
|
b.transform(inject('source-map-support/register', state.sw))
|
@@ -56,6 +57,12 @@ function serviceWorker (state, emit) {
|
|
56
57
|
}))
|
57
58
|
}
|
58
59
|
|
60
|
+
// test if file should be included in transform
|
61
|
+
// str -> bool
|
62
|
+
function include (file) {
|
63
|
+
return !state.skip(file)
|
64
|
+
}
|
65
|
+
|
59
66
|
// emit progress on pipeline reset/pending
|
60
67
|
// () -> void
|
61
68
|
function onreset () {
|
@@ -83,9 +90,9 @@ function serviceWorker (state, emit) {
|
|
83
90
|
mime: 'application/javascript'
|
84
91
|
})
|
85
92
|
} else {
|
86
|
-
|
87
|
-
|
88
|
-
|
93
|
+
const src = bundle.toString()
|
94
|
+
const map = sourcemap.fromSource(src)
|
95
|
+
const buff = Buffer.from(sourcemap.removeComments(src))
|
89
96
|
emit('asset', id, buff, {
|
90
97
|
static: true,
|
91
98
|
mime: 'application/javascript',
|
@@ -99,7 +106,7 @@ function serviceWorker (state, emit) {
|
|
99
106
|
function getEnv () {
|
100
107
|
var env = { NODE_ENV: state.env }
|
101
108
|
env.ASSET_LIST = []
|
102
|
-
for (
|
109
|
+
for (const [key, asset] of state.assets) {
|
103
110
|
if (key !== id) env.ASSET_LIST.push(asset.url)
|
104
111
|
}
|
105
112
|
return env
|
package/lib/style.js
CHANGED
@@ -59,7 +59,7 @@ function style (state, emit) {
|
|
59
59
|
|
60
60
|
var deps = []
|
61
61
|
var reg = /\.js$/
|
62
|
-
for (
|
62
|
+
for (const dep of state.deps) {
|
63
63
|
if (reg.test(dep)) deps.push(dep)
|
64
64
|
}
|
65
65
|
|
@@ -135,7 +135,12 @@ function style (state, emit) {
|
|
135
135
|
})
|
136
136
|
.then(function (result) {
|
137
137
|
// add optimizations
|
138
|
-
if (state.env !== 'development')
|
138
|
+
if (state.env !== 'development') {
|
139
|
+
result.plugins.push(
|
140
|
+
autoprefixer({ overrideBrowserslist: state.browsers }),
|
141
|
+
csso
|
142
|
+
)
|
143
|
+
}
|
139
144
|
// hook up watcher plugin
|
140
145
|
if (state.watch) result.plugins.push(watcher.plugin())
|
141
146
|
return result
|