├── .github
├── dependabot.yml
└── workflows
│ └── ci.yml
├── .gitignore
├── .npmignore
├── CHANGELOG.md
├── LICENSE
├── build.js
├── cli.js
├── example
├── out
│ ├── flat.html
│ ├── flat.js
│ ├── standard.html
│ └── standard.js
├── package.json
├── readme.md
└── src
│ ├── app.js
│ └── view.js
├── index.js
├── lib
├── createModuleFactory.js
└── exposedRequire.js
├── package.json
├── plugin.js
├── private_modules
└── identifierfy
│ ├── LICENSE
│ ├── README.md
│ ├── index.js
│ └── package.json
├── readme.md
└── test
├── bare-module
├── app.js
├── expected.js
└── wrapped.js
├── colliding-unused
├── app.js
├── expected.js
└── other.js
├── comment
├── app.js
├── expected.js
└── other.js
├── dedupe
├── a
│ ├── index.js
│ └── xyz.js
├── app.js
├── b
│ ├── index.js
│ └── xyz.js
└── expected.js
├── dep-order
├── app.js
├── expected.js
├── one.js
├── three.js
└── two.js
├── destructure
├── app.js
├── expected.js
└── greeting.js
├── dynamic-require
├── app.js
└── expected.js
├── eager-cycles
├── a.js
├── app.js
├── b.js
├── c.js
├── d.js
├── e.js
└── expected.js
├── exports-name
├── app.js
├── class.js
├── expected.js
├── fn.js
└── var.js
├── expose.js
├── expose
├── anotherLocalModule.js
├── externalModule.js
├── externalSeparator.js
├── index.js
└── localModule.js
├── globals
├── app.js
├── expected.js
├── fn.js
└── other.js
├── input-source-map
├── .babelrc
├── app.js
├── dep.js
├── expected.js
└── options.json
├── lazy-cycles
├── a.js
├── app.js
├── b.js
└── expected.js
├── lazy-expose
├── a.js
├── app.js
└── b.js
├── lazy-order
├── a.js
├── app.js
├── b.js
├── c.js
├── d.js
└── expected.js
├── module-parent
├── app.js
├── child.js
└── expected.js
├── order.js
├── parent-cycle
├── app.js
└── router.js
├── plugin.js
├── remove-decl
├── a.js
├── app.js
└── expected.js
├── self.js
├── set-exports
├── app.js
├── both.js
├── expected.js
├── exports-only.js
├── free-module.js
├── module-exports.js
└── quoted.js
├── shorthand
├── app.js
├── expected.js
└── importedModule.js
├── simplify
├── app.js
├── asi.js
├── expected.js
├── hello.js
└── world.js
├── source-map
├── app.js
├── b.js
├── expected.js
└── options.json
├── standalone
├── a.js
├── app.js
├── b.js
├── expected.js
└── options.json
├── test.js
├── typeof-require
├── app.js
└── expected.js
└── variable
├── app.js
├── expected.js
└── param.js
/.github/dependabot.yml:
--------------------------------------------------------------------------------
1 | version: 2
2 | updates:
3 | - package-ecosystem: npm
4 | directory: "/"
5 | schedule:
6 | interval: daily
7 | time: "04:00"
8 | open-pull-requests-limit: 10
9 | ignore:
10 | - dependency-name: nanohtml
11 | versions:
12 | - "> 1.6.1"
13 | - dependency-name: uglify-js
14 | versions:
15 | - "> 3.6.0"
16 |
--------------------------------------------------------------------------------
/.github/workflows/ci.yml:
--------------------------------------------------------------------------------
1 | name: Node CI
2 |
3 | on: [push, pull_request]
4 |
5 | jobs:
6 | test:
7 | runs-on: ubuntu-latest
8 |
9 | strategy:
10 | matrix:
11 | node-version:
12 | - 4.x
13 | - 6.x
14 | - 8.x
15 | - 9.x
16 | - 10.x
17 | - 11.x
18 | - 12.x
19 | - 13.x
20 | - 14.x
21 | - 15.x
22 | - 16.x
23 | - 17.x
24 | - 18.x
25 | - 19.x
26 | - 20.x
27 | - 21.x
28 | - 22.x
29 |
30 | steps:
31 | - uses: actions/checkout@v4
32 | - name: Use Node.js ${{ matrix.node-version }}
33 | uses: actions/setup-node@v4
34 | with:
35 | node-version: ${{ matrix.node-version }}
36 | - name: Install dependencies
37 | run: npm install
38 | - name: Run tests
39 | run: npm test
40 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | node_modules/
2 | test/self.*.expected.js
3 | test/self.*.actual.js
4 | actual.js
5 | package-lock.json
6 | /_*.js
7 |
--------------------------------------------------------------------------------
/.npmignore:
--------------------------------------------------------------------------------
1 | test/self.*.expected.js
2 | test/self.*.actual.js
3 | actual.js
4 | example/node_modules
5 |
--------------------------------------------------------------------------------
/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # browser-pack-flat change log
2 |
3 | All notable changes to this project will be documented in this file.
4 |
5 | This project adheres to [Semantic Versioning](http://semver.org/).
6 |
7 | ## 3.5.0
8 | * Expose `ecmaVersion` option. (@ralphtheninja)
9 |
10 | ## 3.4.2
11 | * Fix lazy exposed modules. (#41)
12 |
13 | ## 3.4.1
14 | * Inline result of `typeof require`, which is used by some UMD headers. (#38)
15 |
16 | ## 3.4.0
17 | * Sort dependencies by source order location, now execution order should be much more consistent between Node.js and browser-pack-flat
18 | * Prevent inlining conditional and lazy `require()` calls:
19 | ```js
20 | // this no longer evaluates 'a' if condition is false
21 | if (condition) require('a')
22 |
23 | // this now evaluates 'b' first, then console.log(), and then 'c' once lazy() is called,
24 | // instead of evaluating 'b' and 'c' before entering the module
25 | function lazy () { require('c') }
26 | require('b')
27 | console.log()
28 | lazy()
29 |
30 | // NOTE this *will* still cause out-of-order evaluation! 'b' will be evaluated before
31 | // console.log() is called.
32 | console.log()
33 | require('b')
34 | ```
35 |
36 | ## 3.3.0
37 | * Start changelog.
38 | * Add `iife: false` option to remove the outer `(function(){})` wrapper if you don't need it (@brechtcs)
39 | * Add `sourceType` option to not crash on `import` statements. (@brechtcs)
40 | Don't use this unless you are certain that you have a good use case for it.
41 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | The MIT License (MIT)
2 |
3 | Copyright (c) 2017 Renée Kooi
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/build.js:
--------------------------------------------------------------------------------
1 | var minify = require('uglify-js').minify
2 | var fs = require('fs')
3 |
4 | var createModuleFactory = minify(require('./lib/createModuleFactory').toString()).code
5 | var exposedRequire = minify(require('./lib/exposedRequire').toString()).code
6 |
7 | fs.writeFileSync('./_createModuleFactory.js', createModuleFactory)
8 | fs.writeFileSync('./_exposedRequire.js', exposedRequire)
9 |
--------------------------------------------------------------------------------
/cli.js:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env node
2 |
3 | var pack = require('./')
4 |
5 | process.stdin
6 | .pipe(pack())
7 | .pipe(process.stdout)
8 |
--------------------------------------------------------------------------------
/example/out/flat.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | browser-pack-flat
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
--------------------------------------------------------------------------------
/example/out/flat.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | assert.notEqual = notEqual
3 | assert.notOk = notOk
4 | assert.equal = equal
5 | assert.ok = assert
6 |
7 | var _$assert_3 = assert
8 |
9 | function equal (a, b, m) {
10 | assert(a == b, m) // eslint-disable-line eqeqeq
11 | }
12 |
13 | function notEqual (a, b, m) {
14 | assert(a != b, m) // eslint-disable-line eqeqeq
15 | }
16 |
17 | function notOk (t, m) {
18 | assert(!t, m)
19 | }
20 |
21 | function assert (t, m) {
22 | if (!t) throw new Error(m || 'AssertionError')
23 | }
24 |
25 | var _$events_10 = [
26 | // attribute events (can be set with attributes)
27 | 'onclick',
28 | 'ondblclick',
29 | 'onmousedown',
30 | 'onmouseup',
31 | 'onmouseover',
32 | 'onmousemove',
33 | 'onmouseout',
34 | 'onmouseenter',
35 | 'onmouseleave',
36 | 'ontouchcancel',
37 | 'ontouchend',
38 | 'ontouchmove',
39 | 'ontouchstart',
40 | 'ondragstart',
41 | 'ondrag',
42 | 'ondragenter',
43 | 'ondragleave',
44 | 'ondragover',
45 | 'ondrop',
46 | 'ondragend',
47 | 'onkeydown',
48 | 'onkeypress',
49 | 'onkeyup',
50 | 'onunload',
51 | 'onabort',
52 | 'onerror',
53 | 'onresize',
54 | 'onscroll',
55 | 'onselect',
56 | 'onchange',
57 | 'onsubmit',
58 | 'onreset',
59 | 'onfocus',
60 | 'onblur',
61 | 'oninput',
62 | // other common events
63 | 'oncontextmenu',
64 | 'onfocusin',
65 | 'onfocusout'
66 | ]
67 |
68 | /* removed: var _$events_10 = require('./events') */;
69 | var eventsLength = _$events_10.length
70 |
71 | var ELEMENT_NODE = 1
72 | var TEXT_NODE = 3
73 | var COMMENT_NODE = 8
74 |
75 | var _$morph_11 = morph
76 |
77 | // diff elements and apply the resulting patch to the old node
78 | // (obj, obj) -> null
79 | function morph (newNode, oldNode) {
80 | var nodeType = newNode.nodeType
81 | var nodeName = newNode.nodeName
82 |
83 | if (nodeType === ELEMENT_NODE) {
84 | copyAttrs(newNode, oldNode)
85 | }
86 |
87 | if (nodeType === TEXT_NODE || nodeType === COMMENT_NODE) {
88 | if (oldNode.nodeValue !== newNode.nodeValue) {
89 | oldNode.nodeValue = newNode.nodeValue
90 | }
91 | }
92 |
93 | // Some DOM nodes are weird
94 | // https://github.com/patrick-steele-idem/morphdom/blob/master/src/specialElHandlers.js
95 | if (nodeName === 'INPUT') updateInput(newNode, oldNode)
96 | else if (nodeName === 'OPTION') updateOption(newNode, oldNode)
97 | else if (nodeName === 'TEXTAREA') updateTextarea(newNode, oldNode)
98 |
99 | copyEvents(newNode, oldNode)
100 | }
101 |
102 | function copyAttrs (newNode, oldNode) {
103 | var oldAttrs = oldNode.attributes
104 | var newAttrs = newNode.attributes
105 | var attrNamespaceURI = null
106 | var attrValue = null
107 | var fromValue = null
108 | var attrName = null
109 | var attr = null
110 |
111 | for (var i = newAttrs.length - 1; i >= 0; --i) {
112 | attr = newAttrs[i]
113 | attrName = attr.name
114 | attrNamespaceURI = attr.namespaceURI
115 | attrValue = attr.value
116 | if (attrNamespaceURI) {
117 | attrName = attr.localName || attrName
118 | fromValue = oldNode.getAttributeNS(attrNamespaceURI, attrName)
119 | if (fromValue !== attrValue) {
120 | oldNode.setAttributeNS(attrNamespaceURI, attrName, attrValue)
121 | }
122 | } else {
123 | if (!oldNode.hasAttribute(attrName)) {
124 | oldNode.setAttribute(attrName, attrValue)
125 | } else {
126 | fromValue = oldNode.getAttribute(attrName)
127 | if (fromValue !== attrValue) {
128 | // apparently values are always cast to strings, ah well
129 | if (attrValue === 'null' || attrValue === 'undefined') {
130 | oldNode.removeAttribute(attrName)
131 | } else {
132 | oldNode.setAttribute(attrName, attrValue)
133 | }
134 | }
135 | }
136 | }
137 | }
138 |
139 | // Remove any extra attributes found on the original DOM element that
140 | // weren't found on the target element.
141 | for (var j = oldAttrs.length - 1; j >= 0; --j) {
142 | attr = oldAttrs[j]
143 | if (attr.specified !== false) {
144 | attrName = attr.name
145 | attrNamespaceURI = attr.namespaceURI
146 |
147 | if (attrNamespaceURI) {
148 | attrName = attr.localName || attrName
149 | if (!newNode.hasAttributeNS(attrNamespaceURI, attrName)) {
150 | oldNode.removeAttributeNS(attrNamespaceURI, attrName)
151 | }
152 | } else {
153 | if (!newNode.hasAttributeNS(null, attrName)) {
154 | oldNode.removeAttribute(attrName)
155 | }
156 | }
157 | }
158 | }
159 | }
160 |
161 | function copyEvents (newNode, oldNode) {
162 | for (var i = 0; i < eventsLength; i++) {
163 | var ev = _$events_10[i]
164 | if (newNode[ev]) { // if new element has a whitelisted attribute
165 | oldNode[ev] = newNode[ev] // update existing element
166 | } else if (oldNode[ev]) { // if existing element has it and new one doesnt
167 | oldNode[ev] = undefined // remove it from existing element
168 | }
169 | }
170 | }
171 |
172 | function updateOption (newNode, oldNode) {
173 | updateAttribute(newNode, oldNode, 'selected')
174 | }
175 |
176 | // The "value" attribute is special for the element since it sets the
177 | // initial value. Changing the "value" attribute without changing the "value"
178 | // property will have no effect since it is only used to the set the initial
179 | // value. Similar for the "checked" attribute, and "disabled".
180 | function updateInput (newNode, oldNode) {
181 | var newValue = newNode.value
182 | var oldValue = oldNode.value
183 |
184 | updateAttribute(newNode, oldNode, 'checked')
185 | updateAttribute(newNode, oldNode, 'disabled')
186 |
187 | if (newValue !== oldValue) {
188 | oldNode.setAttribute('value', newValue)
189 | oldNode.value = newValue
190 | }
191 |
192 | if (newValue === 'null') {
193 | oldNode.value = ''
194 | oldNode.removeAttribute('value')
195 | }
196 |
197 | if (!newNode.hasAttributeNS(null, 'value')) {
198 | oldNode.removeAttribute('value')
199 | } else if (oldNode.type === 'range') {
200 | // this is so elements like slider move their UI thingy
201 | oldNode.value = newValue
202 | }
203 | }
204 |
205 | function updateTextarea (newNode, oldNode) {
206 | var newValue = newNode.value
207 | if (newValue !== oldNode.value) {
208 | oldNode.value = newValue
209 | }
210 |
211 | if (oldNode.firstChild && oldNode.firstChild.nodeValue !== newValue) {
212 | // Needed for IE. Apparently IE sets the placeholder as the
213 | // node value and vise versa. This ignores an empty update.
214 | if (newValue === '' && oldNode.firstChild.nodeValue === oldNode.placeholder) {
215 | return
216 | }
217 |
218 | oldNode.firstChild.nodeValue = newValue
219 | }
220 | }
221 |
222 | function updateAttribute (newNode, oldNode, name) {
223 | if (newNode[name] !== oldNode[name]) {
224 | oldNode[name] = newNode[name]
225 | if (newNode[name]) {
226 | oldNode.setAttribute(name, '')
227 | } else {
228 | oldNode.removeAttribute(name)
229 | }
230 | }
231 | }
232 |
233 | /* removed: var _$assert_3 = require('assert') */;
234 | /* removed: var _$morph_11 = require('./lib/morph') */;
235 |
236 | var __TEXT_NODE_9 = 3
237 | // var DEBUG = false
238 |
239 | var _$nanomorph_9 = nanomorph
240 |
241 | // Morph one tree into another tree
242 | //
243 | // no parent
244 | // -> same: diff and walk children
245 | // -> not same: replace and return
246 | // old node doesn't exist
247 | // -> insert new node
248 | // new node doesn't exist
249 | // -> delete old node
250 | // nodes are not the same
251 | // -> diff nodes and apply patch to old node
252 | // nodes are the same
253 | // -> walk all child nodes and append to old node
254 | function nanomorph (oldTree, newTree) {
255 | // if (DEBUG) {
256 | // console.log(
257 | // 'nanomorph\nold\n %s\nnew\n %s',
258 | // oldTree && oldTree.outerHTML,
259 | // newTree && newTree.outerHTML
260 | // )
261 | // }
262 | _$assert_3.equal(typeof oldTree, 'object', 'nanomorph: oldTree should be an object')
263 | _$assert_3.equal(typeof newTree, 'object', 'nanomorph: newTree should be an object')
264 | var tree = walk(newTree, oldTree)
265 | // if (DEBUG) console.log('=> morphed\n %s', tree.outerHTML)
266 | return tree
267 | }
268 |
269 | // Walk and morph a dom tree
270 | function walk (newNode, oldNode) {
271 | // if (DEBUG) {
272 | // console.log(
273 | // 'walk\nold\n %s\nnew\n %s',
274 | // oldNode && oldNode.outerHTML,
275 | // newNode && newNode.outerHTML
276 | // )
277 | // }
278 | if (!oldNode) {
279 | return newNode
280 | } else if (!newNode) {
281 | return null
282 | } else if (newNode.isSameNode && newNode.isSameNode(oldNode)) {
283 | return oldNode
284 | } else if (newNode.tagName !== oldNode.tagName) {
285 | return newNode
286 | } else {
287 | _$morph_11(newNode, oldNode)
288 | updateChildren(newNode, oldNode)
289 | return oldNode
290 | }
291 | }
292 |
293 | // Update the children of elements
294 | // (obj, obj) -> null
295 | function updateChildren (newNode, oldNode) {
296 | // if (DEBUG) {
297 | // console.log(
298 | // 'updateChildren\nold\n %s\nnew\n %s',
299 | // oldNode && oldNode.outerHTML,
300 | // newNode && newNode.outerHTML
301 | // )
302 | // }
303 | var oldChild, newChild, morphed, oldMatch
304 |
305 | // The offset is only ever increased, and used for [i - offset] in the loop
306 | var offset = 0
307 |
308 | for (var i = 0; ; i++) {
309 | oldChild = oldNode.childNodes[i]
310 | newChild = newNode.childNodes[i - offset]
311 | // if (DEBUG) {
312 | // console.log(
313 | // '===\n- old\n %s\n- new\n %s',
314 | // oldChild && oldChild.outerHTML,
315 | // newChild && newChild.outerHTML
316 | // )
317 | // }
318 | // Both nodes are empty, do nothing
319 | if (!oldChild && !newChild) {
320 | break
321 |
322 | // There is no new child, remove old
323 | } else if (!newChild) {
324 | oldNode.removeChild(oldChild)
325 | i--
326 |
327 | // There is no old child, add new
328 | } else if (!oldChild) {
329 | oldNode.appendChild(newChild)
330 | offset++
331 |
332 | // Both nodes are the same, morph
333 | } else if (same(newChild, oldChild)) {
334 | morphed = walk(newChild, oldChild)
335 | if (morphed !== oldChild) {
336 | oldNode.replaceChild(morphed, oldChild)
337 | offset++
338 | }
339 |
340 | // Both nodes do not share an ID or a placeholder, try reorder
341 | } else {
342 | oldMatch = null
343 |
344 | // Try and find a similar node somewhere in the tree
345 | for (var j = i; j < oldNode.childNodes.length; j++) {
346 | if (same(oldNode.childNodes[j], newChild)) {
347 | oldMatch = oldNode.childNodes[j]
348 | break
349 | }
350 | }
351 |
352 | // If there was a node with the same ID or placeholder in the old list
353 | if (oldMatch) {
354 | morphed = walk(newChild, oldMatch)
355 | if (morphed !== oldMatch) offset++
356 | oldNode.insertBefore(morphed, oldChild)
357 |
358 | // It's safe to morph two nodes in-place if neither has an ID
359 | } else if (!newChild.id && !oldChild.id) {
360 | morphed = walk(newChild, oldChild)
361 | if (morphed !== oldChild) {
362 | oldNode.replaceChild(morphed, oldChild)
363 | offset++
364 | }
365 |
366 | // Insert the node at the index if we couldn't morph or find a matching node
367 | } else {
368 | oldNode.insertBefore(newChild, oldChild)
369 | offset++
370 | }
371 | }
372 | }
373 | }
374 |
375 | function same (a, b) {
376 | if (a.id) return a.id === b.id
377 | if (a.isSameNode) return a.isSameNode(b)
378 | if (a.tagName !== b.tagName) return false
379 | if (a.type === __TEXT_NODE_9) return a.nodeValue === b.nodeValue
380 | return false
381 | }
382 |
383 | var _$attributeToProperty_1 = attributeToProperty
384 |
385 | var transform = {
386 | 'class': 'className',
387 | 'for': 'htmlFor',
388 | 'http-equiv': 'httpEquiv'
389 | }
390 |
391 | function attributeToProperty (h) {
392 | return function (tagName, attrs, children) {
393 | for (var attr in attrs) {
394 | if (attr in transform) {
395 | attrs[transform[attr]] = attrs[attr]
396 | delete attrs[attr]
397 | }
398 | }
399 | return h(tagName, attrs, children)
400 | }
401 | }
402 |
403 | /* removed: var _$attributeToProperty_1 = require('hyperscript-attribute-to-property') */;
404 |
405 | var VAR = 0, TEXT = 1, OPEN = 2, CLOSE = 3, ATTR = 4
406 | var ATTR_KEY = 5, ATTR_KEY_W = 6
407 | var ATTR_VALUE_W = 7, ATTR_VALUE = 8
408 | var ATTR_VALUE_SQ = 9, ATTR_VALUE_DQ = 10
409 | var ATTR_EQ = 11, ATTR_BREAK = 12
410 | var COMMENT = 13
411 |
412 | var _$hyperx_2 = function (h, opts) {
413 | if (!opts) opts = {}
414 | var concat = opts.concat || function (a, b) {
415 | return String(a) + String(b)
416 | }
417 | if (opts.attrToProp !== false) {
418 | h = _$attributeToProperty_1(h)
419 | }
420 |
421 | return function (strings) {
422 | var state = TEXT, reg = ''
423 | var arglen = arguments.length
424 | var parts = []
425 |
426 | for (var i = 0; i < strings.length; i++) {
427 | if (i < arglen - 1) {
428 | var arg = arguments[i+1]
429 | var p = parse(strings[i])
430 | var xstate = state
431 | if (xstate === ATTR_VALUE_DQ) xstate = ATTR_VALUE
432 | if (xstate === ATTR_VALUE_SQ) xstate = ATTR_VALUE
433 | if (xstate === ATTR_VALUE_W) xstate = ATTR_VALUE
434 | if (xstate === ATTR) xstate = ATTR_KEY
435 | if (xstate === OPEN) {
436 | if (reg === '/') {
437 | p.push([ OPEN, '/', arg ])
438 | reg = ''
439 | } else {
440 | p.push([ OPEN, arg ])
441 | }
442 | } else {
443 | p.push([ VAR, xstate, arg ])
444 | }
445 | parts.push.apply(parts, p)
446 | } else parts.push.apply(parts, parse(strings[i]))
447 | }
448 |
449 | var tree = [null,{},[]]
450 | var stack = [[tree,-1]]
451 | for (var i = 0; i < parts.length; i++) {
452 | var cur = stack[stack.length-1][0]
453 | var p = parts[i], s = p[0]
454 | if (s === OPEN && /^\//.test(p[1])) {
455 | var ix = stack[stack.length-1][1]
456 | if (stack.length > 1) {
457 | stack.pop()
458 | stack[stack.length-1][0][2][ix] = h(
459 | cur[0], cur[1], cur[2].length ? cur[2] : undefined
460 | )
461 | }
462 | } else if (s === OPEN) {
463 | var c = [p[1],{},[]]
464 | cur[2].push(c)
465 | stack.push([c,cur[2].length-1])
466 | } else if (s === ATTR_KEY || (s === VAR && p[1] === ATTR_KEY)) {
467 | var key = ''
468 | var copyKey
469 | for (; i < parts.length; i++) {
470 | if (parts[i][0] === ATTR_KEY) {
471 | key = concat(key, parts[i][1])
472 | } else if (parts[i][0] === VAR && parts[i][1] === ATTR_KEY) {
473 | if (typeof parts[i][2] === 'object' && !key) {
474 | for (copyKey in parts[i][2]) {
475 | if (parts[i][2].hasOwnProperty(copyKey) && !cur[1][copyKey]) {
476 | cur[1][copyKey] = parts[i][2][copyKey]
477 | }
478 | }
479 | } else {
480 | key = concat(key, parts[i][2])
481 | }
482 | } else break
483 | }
484 | if (parts[i][0] === ATTR_EQ) i++
485 | var j = i
486 | for (; i < parts.length; i++) {
487 | if (parts[i][0] === ATTR_VALUE || parts[i][0] === ATTR_KEY) {
488 | if (!cur[1][key]) cur[1][key] = strfn(parts[i][1])
489 | else parts[i][1]==="" || (cur[1][key] = concat(cur[1][key], parts[i][1]));
490 | } else if (parts[i][0] === VAR
491 | && (parts[i][1] === ATTR_VALUE || parts[i][1] === ATTR_KEY)) {
492 | if (!cur[1][key]) cur[1][key] = strfn(parts[i][2])
493 | else parts[i][2]==="" || (cur[1][key] = concat(cur[1][key], parts[i][2]));
494 | } else {
495 | if (key.length && !cur[1][key] && i === j
496 | && (parts[i][0] === CLOSE || parts[i][0] === ATTR_BREAK)) {
497 | // https://html.spec.whatwg.org/multipage/infrastructure.html#boolean-attributes
498 | // empty string is falsy, not well behaved value in browser
499 | cur[1][key] = key.toLowerCase()
500 | }
501 | if (parts[i][0] === CLOSE) {
502 | i--
503 | }
504 | break
505 | }
506 | }
507 | } else if (s === ATTR_KEY) {
508 | cur[1][p[1]] = true
509 | } else if (s === VAR && p[1] === ATTR_KEY) {
510 | cur[1][p[2]] = true
511 | } else if (s === CLOSE) {
512 | if (selfClosing(cur[0]) && stack.length) {
513 | var ix = stack[stack.length-1][1]
514 | stack.pop()
515 | stack[stack.length-1][0][2][ix] = h(
516 | cur[0], cur[1], cur[2].length ? cur[2] : undefined
517 | )
518 | }
519 | } else if (s === VAR && p[1] === TEXT) {
520 | if (p[2] === undefined || p[2] === null) p[2] = ''
521 | else if (!p[2]) p[2] = concat('', p[2])
522 | if (Array.isArray(p[2][0])) {
523 | cur[2].push.apply(cur[2], p[2])
524 | } else {
525 | cur[2].push(p[2])
526 | }
527 | } else if (s === TEXT) {
528 | cur[2].push(p[1])
529 | } else if (s === ATTR_EQ || s === ATTR_BREAK) {
530 | // no-op
531 | } else {
532 | throw new Error('unhandled: ' + s)
533 | }
534 | }
535 |
536 | if (tree[2].length > 1 && /^\s*$/.test(tree[2][0])) {
537 | tree[2].shift()
538 | }
539 |
540 | if (tree[2].length > 2
541 | || (tree[2].length === 2 && /\S/.test(tree[2][1]))) {
542 | throw new Error(
543 | 'multiple root elements must be wrapped in an enclosing tag'
544 | )
545 | }
546 | if (Array.isArray(tree[2][0]) && typeof tree[2][0][0] === 'string'
547 | && Array.isArray(tree[2][0][2])) {
548 | tree[2][0] = h(tree[2][0][0], tree[2][0][1], tree[2][0][2])
549 | }
550 | return tree[2][0]
551 |
552 | function parse (str) {
553 | var res = []
554 | if (state === ATTR_VALUE_W) state = ATTR
555 | for (var i = 0; i < str.length; i++) {
556 | var c = str.charAt(i)
557 | if (state === TEXT && c === '<') {
558 | if (reg.length) res.push([TEXT, reg])
559 | reg = ''
560 | state = OPEN
561 | } else if (c === '>' && !quot(state) && state !== COMMENT) {
562 | if (state === OPEN && reg.length) {
563 | res.push([OPEN,reg])
564 | } else if (state === ATTR_KEY) {
565 | res.push([ATTR_KEY,reg])
566 | } else if (state === ATTR_VALUE && reg.length) {
567 | res.push([ATTR_VALUE,reg])
568 | }
569 | res.push([CLOSE])
570 | reg = ''
571 | state = TEXT
572 | } else if (state === COMMENT && /-$/.test(reg) && c === '-') {
573 | if (opts.comments) {
574 | res.push([ATTR_VALUE,reg.substr(0, reg.length - 1)],[CLOSE])
575 | }
576 | reg = ''
577 | state = TEXT
578 | } else if (state === OPEN && /^!--$/.test(reg)) {
579 | if (opts.comments) {
580 | res.push([OPEN, reg],[ATTR_KEY,'comment'],[ATTR_EQ])
581 | }
582 | reg = c
583 | state = COMMENT
584 | } else if (state === TEXT || state === COMMENT) {
585 | reg += c
586 | } else if (state === OPEN && c === '/' && reg.length) {
587 | // no-op, self closing tag without a space
588 | } else if (state === OPEN && /\s/.test(c)) {
589 | if (reg.length) {
590 | res.push([OPEN, reg])
591 | }
592 | reg = ''
593 | state = ATTR
594 | } else if (state === OPEN) {
595 | reg += c
596 | } else if (state === ATTR && /[^\s"'=/]/.test(c)) {
597 | state = ATTR_KEY
598 | reg = c
599 | } else if (state === ATTR && /\s/.test(c)) {
600 | if (reg.length) res.push([ATTR_KEY,reg])
601 | res.push([ATTR_BREAK])
602 | } else if (state === ATTR_KEY && /\s/.test(c)) {
603 | res.push([ATTR_KEY,reg])
604 | reg = ''
605 | state = ATTR_KEY_W
606 | } else if (state === ATTR_KEY && c === '=') {
607 | res.push([ATTR_KEY,reg],[ATTR_EQ])
608 | reg = ''
609 | state = ATTR_VALUE_W
610 | } else if (state === ATTR_KEY) {
611 | reg += c
612 | } else if ((state === ATTR_KEY_W || state === ATTR) && c === '=') {
613 | res.push([ATTR_EQ])
614 | state = ATTR_VALUE_W
615 | } else if ((state === ATTR_KEY_W || state === ATTR) && !/\s/.test(c)) {
616 | res.push([ATTR_BREAK])
617 | if (/[\w-]/.test(c)) {
618 | reg += c
619 | state = ATTR_KEY
620 | } else state = ATTR
621 | } else if (state === ATTR_VALUE_W && c === '"') {
622 | state = ATTR_VALUE_DQ
623 | } else if (state === ATTR_VALUE_W && c === "'") {
624 | state = ATTR_VALUE_SQ
625 | } else if (state === ATTR_VALUE_DQ && c === '"') {
626 | res.push([ATTR_VALUE,reg],[ATTR_BREAK])
627 | reg = ''
628 | state = ATTR
629 | } else if (state === ATTR_VALUE_SQ && c === "'") {
630 | res.push([ATTR_VALUE,reg],[ATTR_BREAK])
631 | reg = ''
632 | state = ATTR
633 | } else if (state === ATTR_VALUE_W && !/\s/.test(c)) {
634 | state = ATTR_VALUE
635 | i--
636 | } else if (state === ATTR_VALUE && /\s/.test(c)) {
637 | res.push([ATTR_VALUE,reg],[ATTR_BREAK])
638 | reg = ''
639 | state = ATTR
640 | } else if (state === ATTR_VALUE || state === ATTR_VALUE_SQ
641 | || state === ATTR_VALUE_DQ) {
642 | reg += c
643 | }
644 | }
645 | if (state === TEXT && reg.length) {
646 | res.push([TEXT,reg])
647 | reg = ''
648 | } else if (state === ATTR_VALUE && reg.length) {
649 | res.push([ATTR_VALUE,reg])
650 | reg = ''
651 | } else if (state === ATTR_VALUE_DQ && reg.length) {
652 | res.push([ATTR_VALUE,reg])
653 | reg = ''
654 | } else if (state === ATTR_VALUE_SQ && reg.length) {
655 | res.push([ATTR_VALUE,reg])
656 | reg = ''
657 | } else if (state === ATTR_KEY) {
658 | res.push([ATTR_KEY,reg])
659 | reg = ''
660 | }
661 | return res
662 | }
663 | }
664 |
665 | function strfn (x) {
666 | if (typeof x === 'function') return x
667 | else if (typeof x === 'string') return x
668 | else if (x && typeof x === 'object') return x
669 | else return concat('', x)
670 | }
671 | }
672 |
673 | function quot (state) {
674 | return state === ATTR_VALUE_SQ || state === ATTR_VALUE_DQ
675 | }
676 |
677 | var hasOwn = Object.prototype.hasOwnProperty
678 | function has (obj, key) { return hasOwn.call(obj, key) }
679 |
680 | var closeRE = RegExp('^(' + [
681 | 'area', 'base', 'basefont', 'bgsound', 'br', 'col', 'command', 'embed',
682 | 'frame', 'hr', 'img', 'input', 'isindex', 'keygen', 'link', 'meta', 'param',
683 | 'source', 'track', 'wbr', '!--',
684 | // SVG TAGS
685 | 'animate', 'animateTransform', 'circle', 'cursor', 'desc', 'ellipse',
686 | 'feBlend', 'feColorMatrix', 'feComposite',
687 | 'feConvolveMatrix', 'feDiffuseLighting', 'feDisplacementMap',
688 | 'feDistantLight', 'feFlood', 'feFuncA', 'feFuncB', 'feFuncG', 'feFuncR',
689 | 'feGaussianBlur', 'feImage', 'feMergeNode', 'feMorphology',
690 | 'feOffset', 'fePointLight', 'feSpecularLighting', 'feSpotLight', 'feTile',
691 | 'feTurbulence', 'font-face-format', 'font-face-name', 'font-face-uri',
692 | 'glyph', 'glyphRef', 'hkern', 'image', 'line', 'missing-glyph', 'mpath',
693 | 'path', 'polygon', 'polyline', 'rect', 'set', 'stop', 'tref', 'use', 'view',
694 | 'vkern'
695 | ].join('|') + ')(?:[\.#][a-zA-Z0-9\u007F-\uFFFF_:-]+)*$')
696 | function selfClosing (tag) { return closeRE.test(tag) }
697 |
698 | var trailingNewlineRegex = /\n[\s]+$/
699 | var leadingNewlineRegex = /^\n[\s]+/
700 | var trailingSpaceRegex = /[\s]+$/
701 | var leadingSpaceRegex = /^[\s]+/
702 | var multiSpaceRegex = /[\n\s]+/g
703 |
704 | var TEXT_TAGS = [
705 | 'a', 'abbr', 'b', 'bdi', 'bdo', 'br', 'cite', 'data', 'dfn', 'em', 'i',
706 | 'kbd', 'mark', 'q', 'rp', 'rt', 'rtc', 'ruby', 's', 'amp', 'small', 'span',
707 | 'strong', 'sub', 'sup', 'time', 'u', 'var', 'wbr'
708 | ]
709 |
710 | var VERBATIM_TAGS = [
711 | 'code', 'pre', 'textarea'
712 | ]
713 |
714 | var _$appendChild_4 = function appendChild (el, childs) {
715 | if (!Array.isArray(childs)) return
716 |
717 | var nodeName = el.nodeName.toLowerCase()
718 |
719 | var hadText = false
720 | var value, leader
721 |
722 | for (var i = 0, len = childs.length; i < len; i++) {
723 | var node = childs[i]
724 | if (Array.isArray(node)) {
725 | appendChild(el, node)
726 | continue
727 | }
728 |
729 | if (typeof node === 'number' ||
730 | typeof node === 'boolean' ||
731 | typeof node === 'function' ||
732 | node instanceof Date ||
733 | node instanceof RegExp) {
734 | node = node.toString()
735 | }
736 |
737 | var lastChild = el.childNodes[el.childNodes.length - 1]
738 |
739 | // Iterate over text nodes
740 | if (typeof node === 'string') {
741 | hadText = true
742 |
743 | // If we already had text, append to the existing text
744 | if (lastChild && lastChild.nodeName === '#text') {
745 | lastChild.nodeValue += node
746 |
747 | // We didn't have a text node yet, create one
748 | } else {
749 | node = document.createTextNode(node)
750 | el.appendChild(node)
751 | lastChild = node
752 | }
753 |
754 | // If this is the last of the child nodes, make sure we close it out
755 | // right
756 | if (i === len - 1) {
757 | hadText = false
758 | // Trim the child text nodes if the current node isn't a
759 | // node where whitespace matters.
760 | if (TEXT_TAGS.indexOf(nodeName) === -1 &&
761 | VERBATIM_TAGS.indexOf(nodeName) === -1) {
762 | value = lastChild.nodeValue
763 | .replace(leadingNewlineRegex, '')
764 | .replace(trailingSpaceRegex, '')
765 | .replace(trailingNewlineRegex, '')
766 | .replace(multiSpaceRegex, ' ')
767 | if (value === '') {
768 | el.removeChild(lastChild)
769 | } else {
770 | lastChild.nodeValue = value
771 | }
772 | } else if (VERBATIM_TAGS.indexOf(nodeName) === -1) {
773 | // The very first node in the list should not have leading
774 | // whitespace. Sibling text nodes should have whitespace if there
775 | // was any.
776 | leader = i === 0 ? '' : ' '
777 | value = lastChild.nodeValue
778 | .replace(leadingNewlineRegex, leader)
779 | .replace(leadingSpaceRegex, ' ')
780 | .replace(trailingSpaceRegex, '')
781 | .replace(trailingNewlineRegex, '')
782 | .replace(multiSpaceRegex, ' ')
783 | lastChild.nodeValue = value
784 | }
785 | }
786 |
787 | // Iterate over DOM nodes
788 | } else if (node && node.nodeType) {
789 | // If the last node was a text node, make sure it is properly closed out
790 | if (hadText) {
791 | hadText = false
792 |
793 | // Trim the child text nodes if the current node isn't a
794 | // text node or a code node
795 | if (TEXT_TAGS.indexOf(nodeName) === -1 &&
796 | VERBATIM_TAGS.indexOf(nodeName) === -1) {
797 | value = lastChild.nodeValue
798 | .replace(leadingNewlineRegex, '')
799 | .replace(trailingNewlineRegex, '')
800 | .replace(multiSpaceRegex, ' ')
801 |
802 | // Remove empty text nodes, append otherwise
803 | if (value === '') {
804 | el.removeChild(lastChild)
805 | } else {
806 | lastChild.nodeValue = value
807 | }
808 | // Trim the child nodes if the current node is not a node
809 | // where all whitespace must be preserved
810 | } else if (VERBATIM_TAGS.indexOf(nodeName) === -1) {
811 | value = lastChild.nodeValue
812 | .replace(leadingSpaceRegex, ' ')
813 | .replace(leadingNewlineRegex, '')
814 | .replace(trailingNewlineRegex, '')
815 | .replace(multiSpaceRegex, ' ')
816 | lastChild.nodeValue = value
817 | }
818 | }
819 |
820 | // Store the last nodename
821 | var _nodeName = node.nodeName
822 | if (_nodeName) nodeName = _nodeName.toLowerCase()
823 |
824 | // Append the node to the DOM
825 | el.appendChild(node)
826 | }
827 | }
828 | }
829 |
830 | var _$svgTags_8 = [
831 | 'svg', 'altGlyph', 'altGlyphDef', 'altGlyphItem', 'animate', 'animateColor',
832 | 'animateMotion', 'animateTransform', 'circle', 'clipPath', 'color-profile',
833 | 'cursor', 'defs', 'desc', 'ellipse', 'feBlend', 'feColorMatrix',
834 | 'feComponentTransfer', 'feComposite', 'feConvolveMatrix',
835 | 'feDiffuseLighting', 'feDisplacementMap', 'feDistantLight', 'feFlood',
836 | 'feFuncA', 'feFuncB', 'feFuncG', 'feFuncR', 'feGaussianBlur', 'feImage',
837 | 'feMerge', 'feMergeNode', 'feMorphology', 'feOffset', 'fePointLight',
838 | 'feSpecularLighting', 'feSpotLight', 'feTile', 'feTurbulence', 'filter',
839 | 'font', 'font-face', 'font-face-format', 'font-face-name', 'font-face-src',
840 | 'font-face-uri', 'foreignObject', 'g', 'glyph', 'glyphRef', 'hkern', 'image',
841 | 'line', 'linearGradient', 'marker', 'mask', 'metadata', 'missing-glyph',
842 | 'mpath', 'path', 'pattern', 'polygon', 'polyline', 'radialGradient', 'rect',
843 | 'set', 'stop', 'switch', 'symbol', 'text', 'textPath', 'title', 'tref',
844 | 'tspan', 'use', 'view', 'vkern'
845 | ]
846 |
847 | var _$boolProps_5 = [
848 | 'autofocus', 'checked', 'defaultchecked', 'disabled', 'formnovalidate',
849 | 'indeterminate', 'readonly', 'required', 'selected', 'willvalidate'
850 | ]
851 |
852 | var _$directProps_7 = [
853 | 'indeterminate'
854 | ]
855 |
856 | var _$browser_6 = {};
857 | /* removed: var _$hyperx_2 = require('hyperx') */;
858 | /* removed: var _$appendChild_4 = require('./append-child') */;
859 | /* removed: var _$svgTags_8 = require('./svg-tags') */;
860 | /* removed: var _$boolProps_5 = require('./bool-props') */;
861 | // Props that need to be set directly rather than with el.setAttribute()
862 | /* removed: var _$directProps_7 = require('./direct-props') */;
863 |
864 | var SVGNS = 'http://www.w3.org/2000/svg'
865 | var XLINKNS = 'http://www.w3.org/1999/xlink'
866 |
867 | var COMMENT_TAG = '!--'
868 |
869 | function nanoHtmlCreateElement (tag, props, children) {
870 | var el
871 |
872 | // If an svg tag, it needs a namespace
873 | if (_$svgTags_8.indexOf(tag) !== -1) {
874 | props.namespace = SVGNS
875 | }
876 |
877 | // If we are using a namespace
878 | var ns = false
879 | if (props.namespace) {
880 | ns = props.namespace
881 | delete props.namespace
882 | }
883 |
884 | // Create the element
885 | if (ns) {
886 | el = document.createElementNS(ns, tag)
887 | } else if (tag === COMMENT_TAG) {
888 | return document.createComment(props.comment)
889 | } else {
890 | el = document.createElement(tag)
891 | }
892 |
893 | // Create the properties
894 | for (var p in props) {
895 | if (props.hasOwnProperty(p)) {
896 | var key = p.toLowerCase()
897 | var val = props[p]
898 | // Normalize className
899 | if (key === 'classname') {
900 | key = 'class'
901 | p = 'class'
902 | }
903 | // The for attribute gets transformed to htmlFor, but we just set as for
904 | if (p === 'htmlFor') {
905 | p = 'for'
906 | }
907 | // If a property is boolean, set itself to the key
908 | if (_$boolProps_5.indexOf(key) !== -1) {
909 | if (val === 'true') val = key
910 | else if (val === 'false') continue
911 | }
912 | // If a property prefers being set directly vs setAttribute
913 | if (key.slice(0, 2) === 'on' || _$directProps_7.indexOf(key) !== -1) {
914 | el[p] = val
915 | } else {
916 | if (ns) {
917 | if (p === 'xlink:href') {
918 | el.setAttributeNS(XLINKNS, p, val)
919 | } else if (/^xmlns($|:)/i.test(p)) {
920 | // skip xmlns definitions
921 | } else {
922 | el.setAttributeNS(null, p, val)
923 | }
924 | } else {
925 | el.setAttribute(p, val)
926 | }
927 | }
928 | }
929 | }
930 |
931 | _$appendChild_4(el, children)
932 | return el
933 | }
934 |
935 | _$browser_6 = _$hyperx_2(nanoHtmlCreateElement, {comments: true})
936 | _$browser_6.default = _$browser_6
937 | _$browser_6.createElement = nanoHtmlCreateElement
938 |
939 | /* removed: var _$browser_6 = require('nanohtml') */;
940 |
941 | var _$render_13 = function render (props) {
942 | return _$browser_6`
943 |
944 | ${props.counter}
945 |
948 |
949 | `
950 |
951 | function onclick () {
952 | props.increment()
953 | }
954 | }
955 |
956 | var _$app_12 = {};
957 | /* removed: var _$nanomorph_9 = require('nanomorph') */;
958 | /* removed: var _$render_13 = require('./view') */;
959 | var counter = 0
960 |
961 | function render () {
962 | _$nanomorph_9(document.body, _$render_13({
963 | counter: counter,
964 | increment: function () {
965 | counter++
966 | render()
967 | }
968 | }))
969 | }
970 |
971 | render()
972 |
973 | }());
974 |
--------------------------------------------------------------------------------
/example/out/standard.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | browser-pack
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
--------------------------------------------------------------------------------
/example/out/standard.js:
--------------------------------------------------------------------------------
1 | (function(){function r(e,n,t){function o(i,f){if(!n[i]){if(!e[i]){var c="function"==typeof require&&require;if(!f&&c)return c(i,!0);if(u)return u(i,!0);var a=new Error("Cannot find module '"+i+"'");throw a.code="MODULE_NOT_FOUND",a}var p=n[i]={exports:{}};e[i][0].call(p.exports,function(r){var n=e[i][1][r];return o(n||r)},p,p.exports,r,e,n,t)}return n[i].exports}for(var u="function"==typeof require&&require,i=0;i 1) {
77 | stack.pop()
78 | stack[stack.length-1][0][2][ix] = h(
79 | cur[0], cur[1], cur[2].length ? cur[2] : undefined
80 | )
81 | }
82 | } else if (s === OPEN) {
83 | var c = [p[1],{},[]]
84 | cur[2].push(c)
85 | stack.push([c,cur[2].length-1])
86 | } else if (s === ATTR_KEY || (s === VAR && p[1] === ATTR_KEY)) {
87 | var key = ''
88 | var copyKey
89 | for (; i < parts.length; i++) {
90 | if (parts[i][0] === ATTR_KEY) {
91 | key = concat(key, parts[i][1])
92 | } else if (parts[i][0] === VAR && parts[i][1] === ATTR_KEY) {
93 | if (typeof parts[i][2] === 'object' && !key) {
94 | for (copyKey in parts[i][2]) {
95 | if (parts[i][2].hasOwnProperty(copyKey) && !cur[1][copyKey]) {
96 | cur[1][copyKey] = parts[i][2][copyKey]
97 | }
98 | }
99 | } else {
100 | key = concat(key, parts[i][2])
101 | }
102 | } else break
103 | }
104 | if (parts[i][0] === ATTR_EQ) i++
105 | var j = i
106 | for (; i < parts.length; i++) {
107 | if (parts[i][0] === ATTR_VALUE || parts[i][0] === ATTR_KEY) {
108 | if (!cur[1][key]) cur[1][key] = strfn(parts[i][1])
109 | else parts[i][1]==="" || (cur[1][key] = concat(cur[1][key], parts[i][1]));
110 | } else if (parts[i][0] === VAR
111 | && (parts[i][1] === ATTR_VALUE || parts[i][1] === ATTR_KEY)) {
112 | if (!cur[1][key]) cur[1][key] = strfn(parts[i][2])
113 | else parts[i][2]==="" || (cur[1][key] = concat(cur[1][key], parts[i][2]));
114 | } else {
115 | if (key.length && !cur[1][key] && i === j
116 | && (parts[i][0] === CLOSE || parts[i][0] === ATTR_BREAK)) {
117 | // https://html.spec.whatwg.org/multipage/infrastructure.html#boolean-attributes
118 | // empty string is falsy, not well behaved value in browser
119 | cur[1][key] = key.toLowerCase()
120 | }
121 | if (parts[i][0] === CLOSE) {
122 | i--
123 | }
124 | break
125 | }
126 | }
127 | } else if (s === ATTR_KEY) {
128 | cur[1][p[1]] = true
129 | } else if (s === VAR && p[1] === ATTR_KEY) {
130 | cur[1][p[2]] = true
131 | } else if (s === CLOSE) {
132 | if (selfClosing(cur[0]) && stack.length) {
133 | var ix = stack[stack.length-1][1]
134 | stack.pop()
135 | stack[stack.length-1][0][2][ix] = h(
136 | cur[0], cur[1], cur[2].length ? cur[2] : undefined
137 | )
138 | }
139 | } else if (s === VAR && p[1] === TEXT) {
140 | if (p[2] === undefined || p[2] === null) p[2] = ''
141 | else if (!p[2]) p[2] = concat('', p[2])
142 | if (Array.isArray(p[2][0])) {
143 | cur[2].push.apply(cur[2], p[2])
144 | } else {
145 | cur[2].push(p[2])
146 | }
147 | } else if (s === TEXT) {
148 | cur[2].push(p[1])
149 | } else if (s === ATTR_EQ || s === ATTR_BREAK) {
150 | // no-op
151 | } else {
152 | throw new Error('unhandled: ' + s)
153 | }
154 | }
155 |
156 | if (tree[2].length > 1 && /^\s*$/.test(tree[2][0])) {
157 | tree[2].shift()
158 | }
159 |
160 | if (tree[2].length > 2
161 | || (tree[2].length === 2 && /\S/.test(tree[2][1]))) {
162 | throw new Error(
163 | 'multiple root elements must be wrapped in an enclosing tag'
164 | )
165 | }
166 | if (Array.isArray(tree[2][0]) && typeof tree[2][0][0] === 'string'
167 | && Array.isArray(tree[2][0][2])) {
168 | tree[2][0] = h(tree[2][0][0], tree[2][0][1], tree[2][0][2])
169 | }
170 | return tree[2][0]
171 |
172 | function parse (str) {
173 | var res = []
174 | if (state === ATTR_VALUE_W) state = ATTR
175 | for (var i = 0; i < str.length; i++) {
176 | var c = str.charAt(i)
177 | if (state === TEXT && c === '<') {
178 | if (reg.length) res.push([TEXT, reg])
179 | reg = ''
180 | state = OPEN
181 | } else if (c === '>' && !quot(state) && state !== COMMENT) {
182 | if (state === OPEN && reg.length) {
183 | res.push([OPEN,reg])
184 | } else if (state === ATTR_KEY) {
185 | res.push([ATTR_KEY,reg])
186 | } else if (state === ATTR_VALUE && reg.length) {
187 | res.push([ATTR_VALUE,reg])
188 | }
189 | res.push([CLOSE])
190 | reg = ''
191 | state = TEXT
192 | } else if (state === COMMENT && /-$/.test(reg) && c === '-') {
193 | if (opts.comments) {
194 | res.push([ATTR_VALUE,reg.substr(0, reg.length - 1)],[CLOSE])
195 | }
196 | reg = ''
197 | state = TEXT
198 | } else if (state === OPEN && /^!--$/.test(reg)) {
199 | if (opts.comments) {
200 | res.push([OPEN, reg],[ATTR_KEY,'comment'],[ATTR_EQ])
201 | }
202 | reg = c
203 | state = COMMENT
204 | } else if (state === TEXT || state === COMMENT) {
205 | reg += c
206 | } else if (state === OPEN && c === '/' && reg.length) {
207 | // no-op, self closing tag without a space
208 | } else if (state === OPEN && /\s/.test(c)) {
209 | if (reg.length) {
210 | res.push([OPEN, reg])
211 | }
212 | reg = ''
213 | state = ATTR
214 | } else if (state === OPEN) {
215 | reg += c
216 | } else if (state === ATTR && /[^\s"'=/]/.test(c)) {
217 | state = ATTR_KEY
218 | reg = c
219 | } else if (state === ATTR && /\s/.test(c)) {
220 | if (reg.length) res.push([ATTR_KEY,reg])
221 | res.push([ATTR_BREAK])
222 | } else if (state === ATTR_KEY && /\s/.test(c)) {
223 | res.push([ATTR_KEY,reg])
224 | reg = ''
225 | state = ATTR_KEY_W
226 | } else if (state === ATTR_KEY && c === '=') {
227 | res.push([ATTR_KEY,reg],[ATTR_EQ])
228 | reg = ''
229 | state = ATTR_VALUE_W
230 | } else if (state === ATTR_KEY) {
231 | reg += c
232 | } else if ((state === ATTR_KEY_W || state === ATTR) && c === '=') {
233 | res.push([ATTR_EQ])
234 | state = ATTR_VALUE_W
235 | } else if ((state === ATTR_KEY_W || state === ATTR) && !/\s/.test(c)) {
236 | res.push([ATTR_BREAK])
237 | if (/[\w-]/.test(c)) {
238 | reg += c
239 | state = ATTR_KEY
240 | } else state = ATTR
241 | } else if (state === ATTR_VALUE_W && c === '"') {
242 | state = ATTR_VALUE_DQ
243 | } else if (state === ATTR_VALUE_W && c === "'") {
244 | state = ATTR_VALUE_SQ
245 | } else if (state === ATTR_VALUE_DQ && c === '"') {
246 | res.push([ATTR_VALUE,reg],[ATTR_BREAK])
247 | reg = ''
248 | state = ATTR
249 | } else if (state === ATTR_VALUE_SQ && c === "'") {
250 | res.push([ATTR_VALUE,reg],[ATTR_BREAK])
251 | reg = ''
252 | state = ATTR
253 | } else if (state === ATTR_VALUE_W && !/\s/.test(c)) {
254 | state = ATTR_VALUE
255 | i--
256 | } else if (state === ATTR_VALUE && /\s/.test(c)) {
257 | res.push([ATTR_VALUE,reg],[ATTR_BREAK])
258 | reg = ''
259 | state = ATTR
260 | } else if (state === ATTR_VALUE || state === ATTR_VALUE_SQ
261 | || state === ATTR_VALUE_DQ) {
262 | reg += c
263 | }
264 | }
265 | if (state === TEXT && reg.length) {
266 | res.push([TEXT,reg])
267 | reg = ''
268 | } else if (state === ATTR_VALUE && reg.length) {
269 | res.push([ATTR_VALUE,reg])
270 | reg = ''
271 | } else if (state === ATTR_VALUE_DQ && reg.length) {
272 | res.push([ATTR_VALUE,reg])
273 | reg = ''
274 | } else if (state === ATTR_VALUE_SQ && reg.length) {
275 | res.push([ATTR_VALUE,reg])
276 | reg = ''
277 | } else if (state === ATTR_KEY) {
278 | res.push([ATTR_KEY,reg])
279 | reg = ''
280 | }
281 | return res
282 | }
283 | }
284 |
285 | function strfn (x) {
286 | if (typeof x === 'function') return x
287 | else if (typeof x === 'string') return x
288 | else if (x && typeof x === 'object') return x
289 | else return concat('', x)
290 | }
291 | }
292 |
293 | function quot (state) {
294 | return state === ATTR_VALUE_SQ || state === ATTR_VALUE_DQ
295 | }
296 |
297 | var hasOwn = Object.prototype.hasOwnProperty
298 | function has (obj, key) { return hasOwn.call(obj, key) }
299 |
300 | var closeRE = RegExp('^(' + [
301 | 'area', 'base', 'basefont', 'bgsound', 'br', 'col', 'command', 'embed',
302 | 'frame', 'hr', 'img', 'input', 'isindex', 'keygen', 'link', 'meta', 'param',
303 | 'source', 'track', 'wbr', '!--',
304 | // SVG TAGS
305 | 'animate', 'animateTransform', 'circle', 'cursor', 'desc', 'ellipse',
306 | 'feBlend', 'feColorMatrix', 'feComposite',
307 | 'feConvolveMatrix', 'feDiffuseLighting', 'feDisplacementMap',
308 | 'feDistantLight', 'feFlood', 'feFuncA', 'feFuncB', 'feFuncG', 'feFuncR',
309 | 'feGaussianBlur', 'feImage', 'feMergeNode', 'feMorphology',
310 | 'feOffset', 'fePointLight', 'feSpecularLighting', 'feSpotLight', 'feTile',
311 | 'feTurbulence', 'font-face-format', 'font-face-name', 'font-face-uri',
312 | 'glyph', 'glyphRef', 'hkern', 'image', 'line', 'missing-glyph', 'mpath',
313 | 'path', 'polygon', 'polyline', 'rect', 'set', 'stop', 'tref', 'use', 'view',
314 | 'vkern'
315 | ].join('|') + ')(?:[\.#][a-zA-Z0-9\u007F-\uFFFF_:-]+)*$')
316 | function selfClosing (tag) { return closeRE.test(tag) }
317 |
318 | },{"hyperscript-attribute-to-property":1}],3:[function(require,module,exports){
319 | assert.notEqual = notEqual
320 | assert.notOk = notOk
321 | assert.equal = equal
322 | assert.ok = assert
323 |
324 | module.exports = assert
325 |
326 | function equal (a, b, m) {
327 | assert(a == b, m) // eslint-disable-line eqeqeq
328 | }
329 |
330 | function notEqual (a, b, m) {
331 | assert(a != b, m) // eslint-disable-line eqeqeq
332 | }
333 |
334 | function notOk (t, m) {
335 | assert(!t, m)
336 | }
337 |
338 | function assert (t, m) {
339 | if (!t) throw new Error(m || 'AssertionError')
340 | }
341 |
342 | },{}],4:[function(require,module,exports){
343 | var trailingNewlineRegex = /\n[\s]+$/
344 | var leadingNewlineRegex = /^\n[\s]+/
345 | var trailingSpaceRegex = /[\s]+$/
346 | var leadingSpaceRegex = /^[\s]+/
347 | var multiSpaceRegex = /[\n\s]+/g
348 |
349 | var TEXT_TAGS = [
350 | 'a', 'abbr', 'b', 'bdi', 'bdo', 'br', 'cite', 'data', 'dfn', 'em', 'i',
351 | 'kbd', 'mark', 'q', 'rp', 'rt', 'rtc', 'ruby', 's', 'amp', 'small', 'span',
352 | 'strong', 'sub', 'sup', 'time', 'u', 'var', 'wbr'
353 | ]
354 |
355 | var VERBATIM_TAGS = [
356 | 'code', 'pre', 'textarea'
357 | ]
358 |
359 | module.exports = function appendChild (el, childs) {
360 | if (!Array.isArray(childs)) return
361 |
362 | var nodeName = el.nodeName.toLowerCase()
363 |
364 | var hadText = false
365 | var value, leader
366 |
367 | for (var i = 0, len = childs.length; i < len; i++) {
368 | var node = childs[i]
369 | if (Array.isArray(node)) {
370 | appendChild(el, node)
371 | continue
372 | }
373 |
374 | if (typeof node === 'number' ||
375 | typeof node === 'boolean' ||
376 | typeof node === 'function' ||
377 | node instanceof Date ||
378 | node instanceof RegExp) {
379 | node = node.toString()
380 | }
381 |
382 | var lastChild = el.childNodes[el.childNodes.length - 1]
383 |
384 | // Iterate over text nodes
385 | if (typeof node === 'string') {
386 | hadText = true
387 |
388 | // If we already had text, append to the existing text
389 | if (lastChild && lastChild.nodeName === '#text') {
390 | lastChild.nodeValue += node
391 |
392 | // We didn't have a text node yet, create one
393 | } else {
394 | node = document.createTextNode(node)
395 | el.appendChild(node)
396 | lastChild = node
397 | }
398 |
399 | // If this is the last of the child nodes, make sure we close it out
400 | // right
401 | if (i === len - 1) {
402 | hadText = false
403 | // Trim the child text nodes if the current node isn't a
404 | // node where whitespace matters.
405 | if (TEXT_TAGS.indexOf(nodeName) === -1 &&
406 | VERBATIM_TAGS.indexOf(nodeName) === -1) {
407 | value = lastChild.nodeValue
408 | .replace(leadingNewlineRegex, '')
409 | .replace(trailingSpaceRegex, '')
410 | .replace(trailingNewlineRegex, '')
411 | .replace(multiSpaceRegex, ' ')
412 | if (value === '') {
413 | el.removeChild(lastChild)
414 | } else {
415 | lastChild.nodeValue = value
416 | }
417 | } else if (VERBATIM_TAGS.indexOf(nodeName) === -1) {
418 | // The very first node in the list should not have leading
419 | // whitespace. Sibling text nodes should have whitespace if there
420 | // was any.
421 | leader = i === 0 ? '' : ' '
422 | value = lastChild.nodeValue
423 | .replace(leadingNewlineRegex, leader)
424 | .replace(leadingSpaceRegex, ' ')
425 | .replace(trailingSpaceRegex, '')
426 | .replace(trailingNewlineRegex, '')
427 | .replace(multiSpaceRegex, ' ')
428 | lastChild.nodeValue = value
429 | }
430 | }
431 |
432 | // Iterate over DOM nodes
433 | } else if (node && node.nodeType) {
434 | // If the last node was a text node, make sure it is properly closed out
435 | if (hadText) {
436 | hadText = false
437 |
438 | // Trim the child text nodes if the current node isn't a
439 | // text node or a code node
440 | if (TEXT_TAGS.indexOf(nodeName) === -1 &&
441 | VERBATIM_TAGS.indexOf(nodeName) === -1) {
442 | value = lastChild.nodeValue
443 | .replace(leadingNewlineRegex, '')
444 | .replace(trailingNewlineRegex, '')
445 | .replace(multiSpaceRegex, ' ')
446 |
447 | // Remove empty text nodes, append otherwise
448 | if (value === '') {
449 | el.removeChild(lastChild)
450 | } else {
451 | lastChild.nodeValue = value
452 | }
453 | // Trim the child nodes if the current node is not a node
454 | // where all whitespace must be preserved
455 | } else if (VERBATIM_TAGS.indexOf(nodeName) === -1) {
456 | value = lastChild.nodeValue
457 | .replace(leadingSpaceRegex, ' ')
458 | .replace(leadingNewlineRegex, '')
459 | .replace(trailingNewlineRegex, '')
460 | .replace(multiSpaceRegex, ' ')
461 | lastChild.nodeValue = value
462 | }
463 | }
464 |
465 | // Store the last nodename
466 | var _nodeName = node.nodeName
467 | if (_nodeName) nodeName = _nodeName.toLowerCase()
468 |
469 | // Append the node to the DOM
470 | el.appendChild(node)
471 | }
472 | }
473 | }
474 |
475 | },{}],5:[function(require,module,exports){
476 | module.exports = [
477 | 'autofocus', 'checked', 'defaultchecked', 'disabled', 'formnovalidate',
478 | 'indeterminate', 'readonly', 'required', 'selected', 'willvalidate'
479 | ]
480 |
481 | },{}],6:[function(require,module,exports){
482 | var hyperx = require('hyperx')
483 | var appendChild = require('./append-child')
484 | var SVG_TAGS = require('./svg-tags')
485 | var BOOL_PROPS = require('./bool-props')
486 | // Props that need to be set directly rather than with el.setAttribute()
487 | var DIRECT_PROPS = require('./direct-props')
488 |
489 | var SVGNS = 'http://www.w3.org/2000/svg'
490 | var XLINKNS = 'http://www.w3.org/1999/xlink'
491 |
492 | var COMMENT_TAG = '!--'
493 |
494 | function nanoHtmlCreateElement (tag, props, children) {
495 | var el
496 |
497 | // If an svg tag, it needs a namespace
498 | if (SVG_TAGS.indexOf(tag) !== -1) {
499 | props.namespace = SVGNS
500 | }
501 |
502 | // If we are using a namespace
503 | var ns = false
504 | if (props.namespace) {
505 | ns = props.namespace
506 | delete props.namespace
507 | }
508 |
509 | // Create the element
510 | if (ns) {
511 | el = document.createElementNS(ns, tag)
512 | } else if (tag === COMMENT_TAG) {
513 | return document.createComment(props.comment)
514 | } else {
515 | el = document.createElement(tag)
516 | }
517 |
518 | // Create the properties
519 | for (var p in props) {
520 | if (props.hasOwnProperty(p)) {
521 | var key = p.toLowerCase()
522 | var val = props[p]
523 | // Normalize className
524 | if (key === 'classname') {
525 | key = 'class'
526 | p = 'class'
527 | }
528 | // The for attribute gets transformed to htmlFor, but we just set as for
529 | if (p === 'htmlFor') {
530 | p = 'for'
531 | }
532 | // If a property is boolean, set itself to the key
533 | if (BOOL_PROPS.indexOf(key) !== -1) {
534 | if (val === 'true') val = key
535 | else if (val === 'false') continue
536 | }
537 | // If a property prefers being set directly vs setAttribute
538 | if (key.slice(0, 2) === 'on' || DIRECT_PROPS.indexOf(key) !== -1) {
539 | el[p] = val
540 | } else {
541 | if (ns) {
542 | if (p === 'xlink:href') {
543 | el.setAttributeNS(XLINKNS, p, val)
544 | } else if (/^xmlns($|:)/i.test(p)) {
545 | // skip xmlns definitions
546 | } else {
547 | el.setAttributeNS(null, p, val)
548 | }
549 | } else {
550 | el.setAttribute(p, val)
551 | }
552 | }
553 | }
554 | }
555 |
556 | appendChild(el, children)
557 | return el
558 | }
559 |
560 | module.exports = hyperx(nanoHtmlCreateElement, {comments: true})
561 | module.exports.default = module.exports
562 | module.exports.createElement = nanoHtmlCreateElement
563 |
564 | },{"./append-child":4,"./bool-props":5,"./direct-props":7,"./svg-tags":8,"hyperx":2}],7:[function(require,module,exports){
565 | module.exports = [
566 | 'indeterminate'
567 | ]
568 |
569 | },{}],8:[function(require,module,exports){
570 | module.exports = [
571 | 'svg', 'altGlyph', 'altGlyphDef', 'altGlyphItem', 'animate', 'animateColor',
572 | 'animateMotion', 'animateTransform', 'circle', 'clipPath', 'color-profile',
573 | 'cursor', 'defs', 'desc', 'ellipse', 'feBlend', 'feColorMatrix',
574 | 'feComponentTransfer', 'feComposite', 'feConvolveMatrix',
575 | 'feDiffuseLighting', 'feDisplacementMap', 'feDistantLight', 'feFlood',
576 | 'feFuncA', 'feFuncB', 'feFuncG', 'feFuncR', 'feGaussianBlur', 'feImage',
577 | 'feMerge', 'feMergeNode', 'feMorphology', 'feOffset', 'fePointLight',
578 | 'feSpecularLighting', 'feSpotLight', 'feTile', 'feTurbulence', 'filter',
579 | 'font', 'font-face', 'font-face-format', 'font-face-name', 'font-face-src',
580 | 'font-face-uri', 'foreignObject', 'g', 'glyph', 'glyphRef', 'hkern', 'image',
581 | 'line', 'linearGradient', 'marker', 'mask', 'metadata', 'missing-glyph',
582 | 'mpath', 'path', 'pattern', 'polygon', 'polyline', 'radialGradient', 'rect',
583 | 'set', 'stop', 'switch', 'symbol', 'text', 'textPath', 'title', 'tref',
584 | 'tspan', 'use', 'view', 'vkern'
585 | ]
586 |
587 | },{}],9:[function(require,module,exports){
588 | var assert = require('assert')
589 | var morph = require('./lib/morph')
590 |
591 | var TEXT_NODE = 3
592 | // var DEBUG = false
593 |
594 | module.exports = nanomorph
595 |
596 | // Morph one tree into another tree
597 | //
598 | // no parent
599 | // -> same: diff and walk children
600 | // -> not same: replace and return
601 | // old node doesn't exist
602 | // -> insert new node
603 | // new node doesn't exist
604 | // -> delete old node
605 | // nodes are not the same
606 | // -> diff nodes and apply patch to old node
607 | // nodes are the same
608 | // -> walk all child nodes and append to old node
609 | function nanomorph (oldTree, newTree) {
610 | // if (DEBUG) {
611 | // console.log(
612 | // 'nanomorph\nold\n %s\nnew\n %s',
613 | // oldTree && oldTree.outerHTML,
614 | // newTree && newTree.outerHTML
615 | // )
616 | // }
617 | assert.equal(typeof oldTree, 'object', 'nanomorph: oldTree should be an object')
618 | assert.equal(typeof newTree, 'object', 'nanomorph: newTree should be an object')
619 | var tree = walk(newTree, oldTree)
620 | // if (DEBUG) console.log('=> morphed\n %s', tree.outerHTML)
621 | return tree
622 | }
623 |
624 | // Walk and morph a dom tree
625 | function walk (newNode, oldNode) {
626 | // if (DEBUG) {
627 | // console.log(
628 | // 'walk\nold\n %s\nnew\n %s',
629 | // oldNode && oldNode.outerHTML,
630 | // newNode && newNode.outerHTML
631 | // )
632 | // }
633 | if (!oldNode) {
634 | return newNode
635 | } else if (!newNode) {
636 | return null
637 | } else if (newNode.isSameNode && newNode.isSameNode(oldNode)) {
638 | return oldNode
639 | } else if (newNode.tagName !== oldNode.tagName) {
640 | return newNode
641 | } else {
642 | morph(newNode, oldNode)
643 | updateChildren(newNode, oldNode)
644 | return oldNode
645 | }
646 | }
647 |
648 | // Update the children of elements
649 | // (obj, obj) -> null
650 | function updateChildren (newNode, oldNode) {
651 | // if (DEBUG) {
652 | // console.log(
653 | // 'updateChildren\nold\n %s\nnew\n %s',
654 | // oldNode && oldNode.outerHTML,
655 | // newNode && newNode.outerHTML
656 | // )
657 | // }
658 | var oldChild, newChild, morphed, oldMatch
659 |
660 | // The offset is only ever increased, and used for [i - offset] in the loop
661 | var offset = 0
662 |
663 | for (var i = 0; ; i++) {
664 | oldChild = oldNode.childNodes[i]
665 | newChild = newNode.childNodes[i - offset]
666 | // if (DEBUG) {
667 | // console.log(
668 | // '===\n- old\n %s\n- new\n %s',
669 | // oldChild && oldChild.outerHTML,
670 | // newChild && newChild.outerHTML
671 | // )
672 | // }
673 | // Both nodes are empty, do nothing
674 | if (!oldChild && !newChild) {
675 | break
676 |
677 | // There is no new child, remove old
678 | } else if (!newChild) {
679 | oldNode.removeChild(oldChild)
680 | i--
681 |
682 | // There is no old child, add new
683 | } else if (!oldChild) {
684 | oldNode.appendChild(newChild)
685 | offset++
686 |
687 | // Both nodes are the same, morph
688 | } else if (same(newChild, oldChild)) {
689 | morphed = walk(newChild, oldChild)
690 | if (morphed !== oldChild) {
691 | oldNode.replaceChild(morphed, oldChild)
692 | offset++
693 | }
694 |
695 | // Both nodes do not share an ID or a placeholder, try reorder
696 | } else {
697 | oldMatch = null
698 |
699 | // Try and find a similar node somewhere in the tree
700 | for (var j = i; j < oldNode.childNodes.length; j++) {
701 | if (same(oldNode.childNodes[j], newChild)) {
702 | oldMatch = oldNode.childNodes[j]
703 | break
704 | }
705 | }
706 |
707 | // If there was a node with the same ID or placeholder in the old list
708 | if (oldMatch) {
709 | morphed = walk(newChild, oldMatch)
710 | if (morphed !== oldMatch) offset++
711 | oldNode.insertBefore(morphed, oldChild)
712 |
713 | // It's safe to morph two nodes in-place if neither has an ID
714 | } else if (!newChild.id && !oldChild.id) {
715 | morphed = walk(newChild, oldChild)
716 | if (morphed !== oldChild) {
717 | oldNode.replaceChild(morphed, oldChild)
718 | offset++
719 | }
720 |
721 | // Insert the node at the index if we couldn't morph or find a matching node
722 | } else {
723 | oldNode.insertBefore(newChild, oldChild)
724 | offset++
725 | }
726 | }
727 | }
728 | }
729 |
730 | function same (a, b) {
731 | if (a.id) return a.id === b.id
732 | if (a.isSameNode) return a.isSameNode(b)
733 | if (a.tagName !== b.tagName) return false
734 | if (a.type === TEXT_NODE) return a.nodeValue === b.nodeValue
735 | return false
736 | }
737 |
738 | },{"./lib/morph":11,"assert":3}],10:[function(require,module,exports){
739 | module.exports = [
740 | // attribute events (can be set with attributes)
741 | 'onclick',
742 | 'ondblclick',
743 | 'onmousedown',
744 | 'onmouseup',
745 | 'onmouseover',
746 | 'onmousemove',
747 | 'onmouseout',
748 | 'onmouseenter',
749 | 'onmouseleave',
750 | 'ontouchcancel',
751 | 'ontouchend',
752 | 'ontouchmove',
753 | 'ontouchstart',
754 | 'ondragstart',
755 | 'ondrag',
756 | 'ondragenter',
757 | 'ondragleave',
758 | 'ondragover',
759 | 'ondrop',
760 | 'ondragend',
761 | 'onkeydown',
762 | 'onkeypress',
763 | 'onkeyup',
764 | 'onunload',
765 | 'onabort',
766 | 'onerror',
767 | 'onresize',
768 | 'onscroll',
769 | 'onselect',
770 | 'onchange',
771 | 'onsubmit',
772 | 'onreset',
773 | 'onfocus',
774 | 'onblur',
775 | 'oninput',
776 | // other common events
777 | 'oncontextmenu',
778 | 'onfocusin',
779 | 'onfocusout'
780 | ]
781 |
782 | },{}],11:[function(require,module,exports){
783 | var events = require('./events')
784 | var eventsLength = events.length
785 |
786 | var ELEMENT_NODE = 1
787 | var TEXT_NODE = 3
788 | var COMMENT_NODE = 8
789 |
790 | module.exports = morph
791 |
792 | // diff elements and apply the resulting patch to the old node
793 | // (obj, obj) -> null
794 | function morph (newNode, oldNode) {
795 | var nodeType = newNode.nodeType
796 | var nodeName = newNode.nodeName
797 |
798 | if (nodeType === ELEMENT_NODE) {
799 | copyAttrs(newNode, oldNode)
800 | }
801 |
802 | if (nodeType === TEXT_NODE || nodeType === COMMENT_NODE) {
803 | if (oldNode.nodeValue !== newNode.nodeValue) {
804 | oldNode.nodeValue = newNode.nodeValue
805 | }
806 | }
807 |
808 | // Some DOM nodes are weird
809 | // https://github.com/patrick-steele-idem/morphdom/blob/master/src/specialElHandlers.js
810 | if (nodeName === 'INPUT') updateInput(newNode, oldNode)
811 | else if (nodeName === 'OPTION') updateOption(newNode, oldNode)
812 | else if (nodeName === 'TEXTAREA') updateTextarea(newNode, oldNode)
813 |
814 | copyEvents(newNode, oldNode)
815 | }
816 |
817 | function copyAttrs (newNode, oldNode) {
818 | var oldAttrs = oldNode.attributes
819 | var newAttrs = newNode.attributes
820 | var attrNamespaceURI = null
821 | var attrValue = null
822 | var fromValue = null
823 | var attrName = null
824 | var attr = null
825 |
826 | for (var i = newAttrs.length - 1; i >= 0; --i) {
827 | attr = newAttrs[i]
828 | attrName = attr.name
829 | attrNamespaceURI = attr.namespaceURI
830 | attrValue = attr.value
831 | if (attrNamespaceURI) {
832 | attrName = attr.localName || attrName
833 | fromValue = oldNode.getAttributeNS(attrNamespaceURI, attrName)
834 | if (fromValue !== attrValue) {
835 | oldNode.setAttributeNS(attrNamespaceURI, attrName, attrValue)
836 | }
837 | } else {
838 | if (!oldNode.hasAttribute(attrName)) {
839 | oldNode.setAttribute(attrName, attrValue)
840 | } else {
841 | fromValue = oldNode.getAttribute(attrName)
842 | if (fromValue !== attrValue) {
843 | // apparently values are always cast to strings, ah well
844 | if (attrValue === 'null' || attrValue === 'undefined') {
845 | oldNode.removeAttribute(attrName)
846 | } else {
847 | oldNode.setAttribute(attrName, attrValue)
848 | }
849 | }
850 | }
851 | }
852 | }
853 |
854 | // Remove any extra attributes found on the original DOM element that
855 | // weren't found on the target element.
856 | for (var j = oldAttrs.length - 1; j >= 0; --j) {
857 | attr = oldAttrs[j]
858 | if (attr.specified !== false) {
859 | attrName = attr.name
860 | attrNamespaceURI = attr.namespaceURI
861 |
862 | if (attrNamespaceURI) {
863 | attrName = attr.localName || attrName
864 | if (!newNode.hasAttributeNS(attrNamespaceURI, attrName)) {
865 | oldNode.removeAttributeNS(attrNamespaceURI, attrName)
866 | }
867 | } else {
868 | if (!newNode.hasAttributeNS(null, attrName)) {
869 | oldNode.removeAttribute(attrName)
870 | }
871 | }
872 | }
873 | }
874 | }
875 |
876 | function copyEvents (newNode, oldNode) {
877 | for (var i = 0; i < eventsLength; i++) {
878 | var ev = events[i]
879 | if (newNode[ev]) { // if new element has a whitelisted attribute
880 | oldNode[ev] = newNode[ev] // update existing element
881 | } else if (oldNode[ev]) { // if existing element has it and new one doesnt
882 | oldNode[ev] = undefined // remove it from existing element
883 | }
884 | }
885 | }
886 |
887 | function updateOption (newNode, oldNode) {
888 | updateAttribute(newNode, oldNode, 'selected')
889 | }
890 |
891 | // The "value" attribute is special for the element since it sets the
892 | // initial value. Changing the "value" attribute without changing the "value"
893 | // property will have no effect since it is only used to the set the initial
894 | // value. Similar for the "checked" attribute, and "disabled".
895 | function updateInput (newNode, oldNode) {
896 | var newValue = newNode.value
897 | var oldValue = oldNode.value
898 |
899 | updateAttribute(newNode, oldNode, 'checked')
900 | updateAttribute(newNode, oldNode, 'disabled')
901 |
902 | if (newValue !== oldValue) {
903 | oldNode.setAttribute('value', newValue)
904 | oldNode.value = newValue
905 | }
906 |
907 | if (newValue === 'null') {
908 | oldNode.value = ''
909 | oldNode.removeAttribute('value')
910 | }
911 |
912 | if (!newNode.hasAttributeNS(null, 'value')) {
913 | oldNode.removeAttribute('value')
914 | } else if (oldNode.type === 'range') {
915 | // this is so elements like slider move their UI thingy
916 | oldNode.value = newValue
917 | }
918 | }
919 |
920 | function updateTextarea (newNode, oldNode) {
921 | var newValue = newNode.value
922 | if (newValue !== oldNode.value) {
923 | oldNode.value = newValue
924 | }
925 |
926 | if (oldNode.firstChild && oldNode.firstChild.nodeValue !== newValue) {
927 | // Needed for IE. Apparently IE sets the placeholder as the
928 | // node value and vise versa. This ignores an empty update.
929 | if (newValue === '' && oldNode.firstChild.nodeValue === oldNode.placeholder) {
930 | return
931 | }
932 |
933 | oldNode.firstChild.nodeValue = newValue
934 | }
935 | }
936 |
937 | function updateAttribute (newNode, oldNode, name) {
938 | if (newNode[name] !== oldNode[name]) {
939 | oldNode[name] = newNode[name]
940 | if (newNode[name]) {
941 | oldNode.setAttribute(name, '')
942 | } else {
943 | oldNode.removeAttribute(name)
944 | }
945 | }
946 | }
947 |
948 | },{"./events":10}],12:[function(require,module,exports){
949 | var morph = require('nanomorph')
950 | var view = require('./view')
951 | var counter = 0
952 |
953 | function render () {
954 | morph(document.body, view({
955 | counter: counter,
956 | increment: function () {
957 | counter++
958 | render()
959 | }
960 | }))
961 | }
962 |
963 | render()
964 |
965 | },{"./view":13,"nanomorph":9}],13:[function(require,module,exports){
966 | var html = require('nanohtml')
967 |
968 | module.exports = function render (props) {
969 | return html`
970 |
971 | ${props.counter}
972 |
975 |
976 | `
977 |
978 | function onclick () {
979 | props.increment()
980 | }
981 | }
982 |
983 | },{"nanohtml":6}]},{},[12]);
984 |
--------------------------------------------------------------------------------
/example/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "browser-pack-flat-example",
3 | "private": true,
4 | "dependencies": {
5 | "nanohtml": "^1.2.4",
6 | "nanomorph": "^5.1.3"
7 | },
8 | "devDependencies": {
9 | "browserify": "^16.2.2",
10 | "create-html": "^3.1.0"
11 | },
12 | "scripts": {
13 | "build:standard": "browserify src/app.js > out/standard.js && create-html -s standard.js -t browser-pack > out/standard.html",
14 | "build:flat": "browserify -p ../ src/app.js > out/flat.js && create-html -s flat.js -t browser-pack-flat > out/flat.html",
15 | "build": "npm run build:standard && npm run build:flat"
16 | }
17 | }
18 |
--------------------------------------------------------------------------------
/example/readme.md:
--------------------------------------------------------------------------------
1 | # example
2 |
3 | A small counter app to show the difference in output between the default browser-pack and browser-pack-flat.
4 |
5 | - [Normal output](./out/standard.js)
6 | - ["Flat" output](./out/flat.js)
7 |
8 | ## Try it
9 |
10 | ```bash
11 | cd example/
12 | npm run build
13 | ecstatic out/
14 | ```
15 |
16 | Then visit `localhost:8000`.
17 |
--------------------------------------------------------------------------------
/example/src/app.js:
--------------------------------------------------------------------------------
1 | var morph = require('nanomorph')
2 | var view = require('./view')
3 | var counter = 0
4 |
5 | function render () {
6 | morph(document.body, view({
7 | counter: counter,
8 | increment: function () {
9 | counter++
10 | render()
11 | }
12 | }))
13 | }
14 |
15 | render()
16 |
--------------------------------------------------------------------------------
/example/src/view.js:
--------------------------------------------------------------------------------
1 | var html = require('nanohtml')
2 |
3 | module.exports = function render (props) {
4 | return html`
5 |
6 | ${props.counter}
7 |
10 |
11 | `
12 |
13 | function onclick () {
14 | props.increment()
15 | }
16 | }
17 |
--------------------------------------------------------------------------------
/index.js:
--------------------------------------------------------------------------------
1 | var pathParse = require('path-parse')
2 | var path = require('path')
3 | var fs = require('fs')
4 | var transformAst = require('transform-ast')
5 | var countLines = require('count-lines')
6 | var convertSourceMap = require('convert-source-map')
7 | var combineSourceMap = require('combine-source-map')
8 | var through = require('through2')
9 | var umd = require('umd')
10 | var dedent = require('dedent')
11 | var json = require('JSONStream')
12 | var combiner = require('stream-combiner')
13 | var scan = require('scope-analyzer')
14 | var toIdentifier = require('./private_modules/identifierfy')
15 | var wrapComment = require('wrap-comment')
16 | var isRequire = require('estree-is-require')
17 | var isMemberExpression = require('estree-is-member-expression')
18 |
19 | var dedupedRx = /^arguments\[4\]\[(\d+)\]/
20 |
21 | var kEvaluateOnDemand = Symbol('evaluate on demand')
22 | var kAst = Symbol('ast')
23 | var kIsSimpleExport = Symbol('is simple export')
24 | var kExportsName = Symbol('exports variable name')
25 | var kRequireCalls = Symbol('require calls')
26 | var kDependencyOrder = Symbol('dependency order of execution sort value')
27 | var kReferences = Symbol('module/exports references')
28 | var kMagicString = Symbol('magic string')
29 | var kSourceMap = Symbol('source map')
30 | var kDummyVars = Symbol('dummy replacement variables')
31 | var kShouldRename = Symbol('should rename binding')
32 |
33 | var createModuleFactoryCode = fs.readFileSync(require.resolve('./_createModuleFactory'), 'utf8')
34 | var exposedRequireCode = fs.readFileSync(require.resolve('./_exposedRequire'), 'utf8')
35 |
36 | // Parse the module and collect require() calls and exports assignments.
37 | function parseModule (row, index, rows, opts) {
38 | // Holds the `module.exports` variable name.
39 | var moduleExportsName = toIdentifier('_$' + getModuleName(row.file || '') + '_' + row.id)
40 |
41 | // browserify is clever about deduping modules with the same source code,
42 | // but it needs the browser-pack runtime in order to do so.
43 | // we don't have that runtime so this … re-dupes those modules.
44 | if (dedupedRx.test(row.source)) {
45 | var n = row.source.match(dedupedRx)[1]
46 | var dedup = rows.filter(function (other) {
47 | return String(other.id) === n
48 | })[0]
49 | row.source = dedup.source
50 | }
51 |
52 | var requireCalls = []
53 | var orderOfExecution = new Map()
54 |
55 | var ast
56 | // hack to keep track of `module`/`exports` references correctly.
57 | // in node.js they're defined by a function wrapper, so their scope is
58 | // one level higher-ish than the module scope. this emulates that.
59 | var globalScope = {
60 | type: 'BrowserPackFlatWrapper',
61 | parent: null
62 | }
63 | scan.createScope(globalScope, ['require', 'module', 'exports'])
64 |
65 | var source = row.source
66 |
67 | // Determine if a require() call may not be evaluated according to its linear source position
68 | // This happens primarily if the call is inside a function, or inside a conditional branch
69 | function isOrderUnpredictable (node) {
70 | while ((node = node.parent)) {
71 | // Special-case for IIFE, behaviour is the same as evaluating inline
72 | if (node.type === 'FunctionExpression' || node.type === 'ArrowFunctionExpression') {
73 | // (() => {})()
74 | if (node.parent && node.parent.type === 'CallExpression' && node.parent.callee === node) {
75 | continue
76 | }
77 | // (function(){}).call(null)
78 | // this form is added by browserify to inject globals
79 | if (node.parent && node.parent.type === 'MemberExpression' &&
80 | node.parent.object === node &&
81 | (node.parent.property.name === 'call' || node.parent.property.name === 'apply') &&
82 | node.parent.parent && node.parent.parent.type === 'CallExpression') {
83 | continue
84 | }
85 | }
86 |
87 | // if(require('d')) is still in-order
88 | // the same is technically true for while(require()) and for(require();;) but those are more rare
89 | if (node.parent && node.parent.type === 'IfStatement' && node.parent.test === node) {
90 | // Skip the IfStatement
91 | node = node.parent
92 | continue
93 | }
94 |
95 | if (node.type === 'IfStatement' || // if(false) require()
96 | node.type === 'WhileStatement' || // while(false) require()
97 | node.type === 'ForStatement' || // for(;false;) require()
98 | node.type === 'ForInStatement' || // for(x in []) require()
99 | node.type === 'FunctionExpression' || // setTimeout(function(){ require() })
100 | node.type === 'FunctionDeclaration' || // function neverCalled(){ require() }
101 | node.type === 'ArrowFunctionExpression' // setTimeout(()=> require())
102 | ) {
103 | return true
104 | }
105 | }
106 | return false
107 | }
108 |
109 | // Keep track of modules that were already evaluated in a predictable order so that multiple
110 | // require('a') occurences don't force 'a' to become on-demand
111 | var alreadyPredictablyEvaluated = new Set()
112 | // we'll do two walks along the AST in order to detect variables and their references.
113 | // we initialise the scopes and declarations in the first one here, and then collect
114 | // references in the second.
115 | var magicString = transformAst(source, {
116 | ecmaVersion: opts.ecmaVersion !== undefined ? opts.ecmaVersion : 10,
117 | inputFilename: row.sourceFile,
118 | sourceType: opts.sourceType || 'script'
119 | }, function (node) {
120 | if (node.type === 'Program') ast = node
121 | scan.visitScope(node)
122 |
123 | // also collect requires while we're here
124 | if (isRequire(node)) {
125 | var argument = node.arguments[0]
126 | var required = argument.type === 'Literal' ? argument.value : null
127 |
128 | if (required !== null && moduleExists(row.deps[required])) {
129 | var other = rows.byId[row.deps[required]]
130 | if (isOrderUnpredictable(node)) {
131 | if (!alreadyPredictablyEvaluated.has(other)) {
132 | other[kEvaluateOnDemand] = true
133 | }
134 | } else {
135 | alreadyPredictablyEvaluated.add(other)
136 | }
137 | requireCalls.push({
138 | id: row.deps[required],
139 | node: node,
140 | requiredModule: other
141 | })
142 | } else if (required !== null) {
143 | requireCalls.push({
144 | external: true,
145 | id: row.deps[required] || required,
146 | node: node
147 | })
148 | }
149 |
150 | if (required !== null) {
151 | orderOfExecution.set(row.deps[required] || required, node.end)
152 | }
153 |
154 | function moduleExists (id) {
155 | return id != null && !!rows.byId[id]
156 | }
157 | }
158 | })
159 | magicString.walk(function (node) {
160 | // transform-ast has set this to `undefined`
161 | ast.parent = globalScope
162 | scan.visitBinding(node)
163 | })
164 |
165 | var requireList = scan.scope(globalScope).getReferences('require')
166 | var moduleExportsList = scan.scope(globalScope).getReferences('module')
167 | .map(function (node) { return node.parent })
168 | .filter(isModuleExports)
169 | var exportsList = scan.scope(globalScope).getReferences('exports')
170 | var moduleList = scan.scope(globalScope).getReferences('module')
171 | .filter(function (node) { return !isModuleExports(node.parent) })
172 |
173 | // Detect simple exports that are just `module.exports = xyz`, we can compile them to a single
174 | // variable assignment.
175 | var isSimpleExport = false
176 | if (moduleExportsList.length === 1 && exportsList.length === 0 && moduleList.length === 0) {
177 | var node = moduleExportsList[0]
178 | if (node.parent.type === 'AssignmentExpression' && node.parent.left === node &&
179 | node.parent.parent.type === 'ExpressionStatement') {
180 | isSimpleExport = scan.nearestScope(node.object, false) === ast
181 |
182 | var name = getNodeName(node.parent.right)
183 | if (name) {
184 | moduleExportsName = toIdentifier('_$' + name + '_' + row.id)
185 | }
186 | }
187 | }
188 |
189 | row[kAst] = ast
190 | row[kIsSimpleExport] = isSimpleExport
191 | row[kExportsName] = moduleExportsName
192 | row.hasExports = (moduleExportsList.length + exportsList.length) > 0
193 | row[kRequireCalls] = requireCalls
194 | row[kDependencyOrder] = orderOfExecution
195 | row[kReferences] = {
196 | require: requireList,
197 | module: moduleList,
198 | exports: exportsList,
199 | 'module.exports': moduleExportsList
200 | }
201 | row[kMagicString] = magicString
202 | }
203 |
204 | function sortModules (rows) {
205 | var index = new Map()
206 | var mod
207 | while ((mod = rows.pop())) {
208 | index.set(mod.id, mod)
209 | }
210 |
211 | function compareDependencySortOrder (a, b) {
212 | // Sort dependencies by the order of their require() calls
213 | var ao = typeof a.dependencyOrder === 'number'
214 | var bo = typeof b.dependencyOrder === 'number'
215 | if (ao && bo) {
216 | return a.dependencyOrder < b.dependencyOrder ? -1 : 1
217 | }
218 | if (ao && !bo) return -1
219 | if (!ao && bo) return 1
220 |
221 | return compareModuleSortOrder(a.module, b.module)
222 | }
223 |
224 | var modules = Array.from(index.values()).sort(compareModuleSortOrder)
225 | var seen = new Set()
226 |
227 | function visit (mod) {
228 | if (seen.has(mod.id)) return
229 | seen.add(mod.id)
230 | if (hasDeps(mod)) {
231 | values(mod.deps)
232 | .map(function attachSortOrder (id) {
233 | var dep = index.get(id)
234 | if (dep) {
235 | return {
236 | module: dep,
237 | dependencyOrder: mod[kDependencyOrder] ? mod[kDependencyOrder].get(id) : undefined
238 | }
239 | }
240 | })
241 | .filter(Boolean)
242 | .sort(compareDependencySortOrder)
243 | .forEach(function (dep) { visit(dep.module) })
244 | }
245 | rows.push(mod)
246 | }
247 |
248 | modules.forEach(visit)
249 | }
250 |
251 | function values (obj) {
252 | var result = []
253 | for (var k in obj) { result.push(obj[k]) }
254 | return result
255 | }
256 |
257 | function hasDeps (mod) {
258 | return mod.deps && Object.keys(mod.deps).length > 0
259 | }
260 |
261 | function compareModuleSortOrder (a, b) {
262 | // Float entry modules to the top.
263 | if (a.entry && !b.entry) return -1
264 | if (!a.entry && b.entry) return 1
265 | // Sort entry modules by their `.order`.
266 | var ao = typeof a.order === 'number'
267 | var bo = typeof b.order === 'number'
268 | if (ao && bo) {
269 | return a.order < b.order ? -1 : 1
270 | }
271 | // Modules that have an `.order` go before modules that do not.
272 | if (ao && !bo) return -1
273 | if (!ao && bo) return 1
274 |
275 | // Else sort by ID, so that output is stable.
276 | return a.id < b.id ? -1 : 1
277 | }
278 |
279 | // Collect all global variables that are used in any module.
280 | // This is done separately from the next step (markDuplicateVariableNames)
281 | // so that global variables used in "later" modules, when colliding
282 | // with a module variable name in an "earlier" module, are correctly
283 | // deduped. See https://github.com/browserify/tinyify/issues/10
284 | function identifyGlobals (row, i, rows) {
285 | var ast = row[kAst]
286 | var globalScope = ast.parent
287 |
288 | var scope = scan.scope(ast)
289 | if (scope) {
290 | scan.scope(globalScope).getUndeclaredNames().forEach(function (name) {
291 | rows.usedGlobalVariables.add(name)
292 | })
293 | }
294 | }
295 |
296 | // Mark module variables that collide with variable names from other modules so we can rewrite them.
297 | function markDuplicateVariableNames (row, i, rows) {
298 | var ast = row[kAst]
299 |
300 | var scope = scan.scope(ast)
301 | if (scope) {
302 | scope.forEach(function (binding, name) {
303 | binding[kShouldRename] = rows.usedGlobalVariables.has(name)
304 | rows.usedGlobalVariables.add(name)
305 | })
306 | }
307 | }
308 |
309 | function rewriteModule (row, i, rows) {
310 | var moduleExportsName = row[kExportsName]
311 | var moduleBaseName
312 |
313 | var ast = row[kAst]
314 | var magicString = row[kMagicString]
315 | var moduleList = row[kReferences].module
316 | var moduleExportsList = row[kReferences]['module.exports']
317 | var exportsList = row[kReferences].exports
318 | var requireList = row[kReferences].require
319 |
320 | // If `module` is used as a free variable we need to turn it into an object with an `.exports`
321 | // property, to deal with situations like:
322 | //
323 | // var a = module;
324 | // a.exports = 'hello'
325 | //
326 | // Not too common, but it happens…
327 | if (moduleList.length > 0) {
328 | moduleBaseName = moduleExportsName
329 | moduleExportsName += '.exports'
330 | }
331 |
332 | // inline "typeof require", because it will usually not be available at runtime
333 | requireList.forEach(function (node) {
334 | if (node.parent.type === 'UnaryExpression' && node.parent.operator === 'typeof') {
335 | node.parent.edit.update('"function"')
336 | }
337 | })
338 |
339 | if (!row[kEvaluateOnDemand]) { // on-demand modules have a function wrapper and don't need to be rewritten
340 | moduleExportsList.concat(exportsList).forEach(function (node) {
341 | if (row[kIsSimpleExport]) {
342 | // var $moduleExportsName = xyz
343 | node.edit.update('var ' + moduleExportsName)
344 | } else {
345 | renameIdentifier(node, moduleExportsName)
346 | }
347 | })
348 | moduleList.forEach(function (node) {
349 | // rewrite `typeof module` to `"object"`
350 | if (node.parent.type === 'UnaryExpression' && node.parent.operator === 'typeof') {
351 | node.parent.edit.update('"object"')
352 | } else if (isModuleParent(node.parent)) {
353 | if (row.entry) {
354 | node.parent.edit.update('null')
355 | } else {
356 | node.parent.edit.update('({})')
357 | }
358 | } else {
359 | renameIdentifier(node, moduleBaseName)
360 | }
361 | })
362 | if (scan.scope(ast)) {
363 | // rename colliding global variable names
364 | scan.scope(ast).forEach(function (binding, name) {
365 | if (binding[kShouldRename]) {
366 | renameBinding(binding, toIdentifier('__' + name + '_' + row.id))
367 | }
368 | })
369 | }
370 | }
371 |
372 | row[kRequireCalls].forEach(function (req) {
373 | var node = req.node
374 | var other = req.requiredModule
375 | if (req.external) {
376 | node.edit.update('require(' + JSON.stringify(req.id) + ')')
377 | } else if (other && other[kEvaluateOnDemand]) {
378 | node.edit.update(other[kExportsName] + '({})') // `module.parent` value = {}
379 | } else if (other && other[kExportsName]) {
380 | renameImport(row, node, other[kExportsName])
381 | } else {
382 | // TODO this is an unknown module, so probably something went wrong and we should throw an error?
383 | node.edit.update(toIdentifier('_$module_' + req.id))
384 | }
385 | })
386 |
387 | if (row[kEvaluateOnDemand]) {
388 | magicString.prepend('var ' + row[kExportsName] + ' = ' + rows.createModuleFactoryName + '(function (module, exports) {\n')
389 | magicString.append('\n});')
390 | } else if (moduleBaseName) {
391 | magicString
392 | .prepend('var ' + moduleBaseName + ' = { exports: {} };\n')
393 | .append('\n' + moduleBaseName + ' = ' + moduleExportsName)
394 | moduleExportsName = moduleBaseName
395 | } else if (!row[kIsSimpleExport]) {
396 | magicString.prepend('var ' + moduleExportsName + ' = {};\n')
397 | }
398 |
399 | row[kSourceMap] = magicString.map
400 | row.source = magicString.toString()
401 | }
402 |
403 | function flatten (rows, opts, stream) {
404 | rows.byId = Object.create(null)
405 | rows.forEach(function (row) { rows.byId[row.id] = row })
406 |
407 | var containsCycles = detectCycles(rows)
408 |
409 | var combiner = opts.debug ? combineSourceMap.create() : null
410 |
411 | var intro = ''
412 | var outro = ''
413 |
414 | rows.usedGlobalVariables = new Set()
415 | rows.exposeName = generateName(rows, 'exposedRequire')
416 | rows.createModuleFactoryName = generateName(rows, 'createModuleFactory')
417 | rows.forEach(function (row, index, rows) {
418 | parseModule(row, index, rows, opts)
419 | })
420 | sortModules(rows)
421 | rows.forEach(identifyGlobals)
422 | rows.forEach(markDuplicateVariableNames)
423 | rows.forEach(rewriteModule)
424 | moveOnDemandModulesToStart(rows)
425 |
426 | // Initialize entry modules that are marked as on-demand (because of a dependency cycle
427 | // or a conditional require() call)
428 | for (var i = 0; i < rows.length; i++) {
429 | if (rows[i].entry && rows[i][kEvaluateOnDemand]) {
430 | outro += '\n' + rows[i][kExportsName] + '();'
431 | }
432 | }
433 |
434 | // Expose modules on the global `require` function, or standalone as UMD
435 | var exposesModules = false
436 | for (var i = 0; i < rows.length; i++) {
437 | if (rows[i].expose && !opts.standalone) {
438 | exposesModules = true
439 | if (rows[i][kEvaluateOnDemand]) {
440 | // If the module is evaluated on demand, using a function, define
441 | // a getter so the function will be called.
442 | outro += '\nObject.defineProperty(' + rows.exposeName + '.m, ' + JSON.stringify(rows[i].id) + ', { get: function() { return ' + rows[i][kExportsName] + '({}); }});'
443 | } else {
444 | outro += '\n' + rows.exposeName + '.m[' + JSON.stringify(rows[i].id) + '] = ' + rows[i][kExportsName] + ';'
445 | }
446 | }
447 |
448 | var isEntryModule = rows[i].entry && rows[i].hasExports && opts.standalone
449 | // Need this for:
450 | // https://github.com/browserify/browserify/blob/0305b703b226878f3acb5b8f2ff9451c87cd3991/test/debug_standalone.js#L44-L64
451 | var isStandaloneModule = opts.standalone && rows[i].id === stream.standaloneModule
452 | if (isEntryModule || isStandaloneModule) {
453 | outro += '\nreturn ' + rows[i][kExportsName] + ';\n'
454 | }
455 | }
456 |
457 | if (opts.standalone) {
458 | intro += umd.prelude(opts.standalone)
459 | outro += umd.postlude(opts.standalone)
460 | } else if (exposesModules) {
461 | intro += dedent`
462 | require = (function (require) {
463 | var ${rows.exposeName} = ${exposedRequireCode};
464 | ${rows.exposeName}.m = {};
465 | ${rows.exposeName}.r = require;
466 | `
467 | outro += '\n' + dedent`
468 | return ${rows.exposeName};
469 | }(typeof require === 'function' ? require : void 0));
470 | `
471 | } else if (opts.iife || opts.iife == undefined) {
472 | intro += '(function(){\n'
473 | outro += '\n}());'
474 | }
475 |
476 | // Add the circular dependency/on-demand runtime if necessary.
477 | if (rows.some(function (mod) { return mod[kEvaluateOnDemand] })) {
478 | intro += 'var ' + rows.createModuleFactoryName + ' = ' + createModuleFactoryCode + ';\n'
479 | }
480 |
481 | var result = ''
482 | var line = 0
483 |
484 | var preludePath = path.relative(
485 | opts.basedir || process.cwd(),
486 | path.join(__dirname, '_prelude')
487 | )
488 | var postludePath = path.relative(
489 | opts.basedir || process.cwd(),
490 | path.join(__dirname, '_postlude')
491 | )
492 |
493 | result += intro
494 | if (opts.debug) {
495 | combiner.addFile({
496 | sourceFile: preludePath,
497 | source: intro
498 | }, { line: line })
499 | }
500 |
501 | line += countLines(intro) - 1
502 |
503 | rows.forEach(function (row, i) {
504 | if (i > 0) {
505 | result += '\n'
506 | line += 1
507 | }
508 | result += row.source
509 | if (opts.debug && row.sourceFile && !row.nomap) {
510 | combiner.addFile({
511 | sourceFile: row.sourceFile,
512 | source: row.source + '\n' + convertSourceMap.fromObject(row[kSourceMap]).toComment()
513 | }, { line: line })
514 | }
515 |
516 | line += countLines(row.source) - 1
517 | })
518 |
519 | result += outro
520 | if (opts.debug) {
521 | combiner.addFile({
522 | sourceFile: postludePath,
523 | source: outro
524 | }, { line: line })
525 | }
526 |
527 | if (opts.debug) {
528 | result += '\n' + combiner.comment()
529 | }
530 |
531 | result += '\n'
532 |
533 | return Buffer.from(result)
534 | }
535 |
536 | module.exports = function browserPackFlat(opts) {
537 | // When used as a transform
538 | if (typeof opts === 'string' && typeof arguments[1] === 'object') {
539 | throw new Error('browser-pack-flat: must be used as a plugin through `browser-pack-flat/plugin`')
540 | }
541 | // When used as a plugin
542 | if (opts && typeof opts.plugin === 'function') {
543 | // Doing 'plu' + 'gin' so browserify doesn't detect this require() call
544 | // when running the self-test. Workaround for this bug:
545 | // https://github.com/browserify/browserify/issues/1260
546 | return require('./plu' + 'gin').apply(null, arguments)
547 | }
548 |
549 | opts = opts || {}
550 |
551 | var rows = []
552 |
553 | var packer = through.obj(onwrite, onend)
554 | var stream = opts.raw ? packer : combiner([
555 | json.parse([ true ]),
556 | packer
557 | ])
558 |
559 | return stream
560 |
561 | function onwrite (row, enc, cb) {
562 | rows.push(row)
563 | cb(null)
564 | }
565 | function onend (cb) {
566 | try {
567 | packer.push(flatten(rows, opts || {}, stream))
568 | packer.push(null)
569 | cb(null)
570 | } catch (err) {
571 | cb(err)
572 | }
573 | }
574 | }
575 |
576 | /**
577 | * Detect cyclical dependencies in the bundle. All modules in a dependency cycle
578 | * are moved to the top of the bundle and wrapped in functions so they're not
579 | * evaluated immediately. When other modules need a module that's in a dependency
580 | * cycle, instead of using the module's exportName, it'll call the `createModuleFactory` runtime
581 | * function, which will execute the requested module and return its exports.
582 | */
583 | function detectCycles (rows) {
584 | var cyclicalModules = new Set()
585 | var checked = new Set()
586 | rows.forEach(function (module) {
587 | var visited = []
588 |
589 | check(module)
590 |
591 | function check (row) {
592 | var i = visited.indexOf(row)
593 | if (i !== -1) {
594 | checked.add(row)
595 | for (; i < visited.length; i++) {
596 | cyclicalModules.add(visited[i])
597 | }
598 | return
599 | }
600 | if (checked.has(row)) return
601 | visited.push(row)
602 | Object.keys(row.deps).forEach(function (k) {
603 | var dep = row.deps[k]
604 | var other = rows.byId[dep]
605 | if (other) check(other, visited)
606 | })
607 | visited.pop()
608 | }
609 | })
610 |
611 | // mark cyclical dependencies
612 | for (var i = 0; i < rows.length; i++) {
613 | rows[i][kEvaluateOnDemand] = cyclicalModules.has(rows[i])
614 | }
615 | return cyclicalModules.size > 0
616 | }
617 |
618 | function moveOnDemandModulesToStart (rows) {
619 | for (var i = 0; i < rows.length; i++) {
620 | if (rows[i][kEvaluateOnDemand]) {
621 | var row = rows.splice(i, 1)[0]
622 | rows.unshift(row)
623 | }
624 | }
625 | }
626 |
627 | function getNodeName (node) {
628 | if (node.type === 'FunctionExpression') node = node.id
629 | else if (node.type === 'ClassExpression') node = node.id
630 | if (node && node.type === 'Identifier') {
631 | return node.name
632 | }
633 | }
634 |
635 | function isModuleExports (node) {
636 | return isMemberExpression(node, 'module.exports')
637 | }
638 | function isModuleParent (node) {
639 | return isMemberExpression(node, 'module.parent')
640 | }
641 |
642 | function isObjectKey (node) {
643 | return node.parent.type === 'Property' && node.parent.key === node
644 | }
645 | function isShorthandProperty (node) {
646 | return node.type === 'Identifier' && isObjectKey(node) && node.parent.shorthand
647 | }
648 |
649 | function renameIdentifier (node, name) {
650 | if (isShorthandProperty(node)) {
651 | node.edit.update(node.name + ': ' + name)
652 | } else {
653 | node.edit.update(name)
654 | }
655 | }
656 |
657 | function renameImport (row, node, name) {
658 | if (node.parent.type === 'VariableDeclarator' && node.parent.id.type === 'Identifier') {
659 | var binding = scan.getBinding(node.parent.id)
660 | if (binding) {
661 | renameBinding(binding, name)
662 | removeVariableDeclarator(row, node.parent)
663 | return
664 | }
665 | }
666 | node.edit.update(name)
667 | }
668 |
669 | function renameBinding (binding, newName) {
670 | binding.each(function (node) {
671 | renameIdentifier(node, newName)
672 | })
673 | }
674 |
675 | // Remove a variable declarator -- remove the declaration entirely if it is the only one,
676 | // otherwise replace with a dummy declarator
677 | function removeVariableDeclarator (row, decl) {
678 | if (decl.parent.type === 'VariableDeclaration') {
679 | var i = decl.parent.declarations.indexOf(decl)
680 | if (decl.parent.declarations.length === 1) {
681 | var removed = decl.parent.getSource()
682 | decl.parent.edit.update(wrapComment('removed: ' + removed) + ';')
683 | } else if (i === decl.parent.declarations.length - 1) {
684 | // Remove ", a = 1"
685 | row[kMagicString].overwrite(decl.parent.declarations[i - 1].end, decl.end, '')
686 | } else {
687 | // Remove "a = 1, "
688 | row[kMagicString].overwrite(decl.start, decl.parent.declarations[i + 1].start, '')
689 | }
690 | decl.parent.declarations.splice(i, 1)
691 | } else {
692 | if (!row[kDummyVars]) row[kDummyVars] = 0
693 | var id = '__dummy_' + row.index + '$' + row[kDummyVars]
694 | row[kDummyVars]++
695 | decl.edit.update(toIdentifier(id) + ' = 0')
696 | }
697 | }
698 |
699 | function getModuleName (file) {
700 | var parts = pathParse(file)
701 | var name = parts.base === 'index.js'
702 | ? path.basename(parts.dir)
703 | : parts.name
704 | return name || 'module'
705 | }
706 |
707 | function generateName (rows, base) {
708 | var dedupe = ''
709 | var i = 0
710 | while (true) {
711 | var inUse = rows.some(function (row) {
712 | return row.source.indexOf(base + dedupe) !== -1
713 | })
714 | if (!inUse) {
715 | return base + dedupe
716 | }
717 | dedupe = '_' + (i++)
718 | }
719 | }
720 |
--------------------------------------------------------------------------------
/lib/createModuleFactory.js:
--------------------------------------------------------------------------------
1 | /**
2 | * Helper used in the output bundle to resolve dependency cycles.
3 | * This helper wraps a module factory and lazily executes it.
4 | * Imports of a circular module will call the factory returned by this function.
5 | */
6 | module.exports = function createModuleFactory (factory) {
7 | var module
8 | return function (parent) {
9 | if (!module) {
10 | module = { exports: {}, parent: parent }
11 | factory(module, module.exports)
12 | }
13 | return module.exports
14 | }
15 | }
16 |
--------------------------------------------------------------------------------
/lib/exposedRequire.js:
--------------------------------------------------------------------------------
1 | // Helper to expose a module.
2 | module.exports = function exposedRequire (m, jumped) {
3 | // A locally exposed module
4 | if (exposedRequire.m.hasOwnProperty(m)) {
5 | return exposedRequire.m[m]
6 | }
7 | // A module exposed on a later chunk
8 | if (typeof require === 'function' && !jumped) {
9 | return require(m, 1)
10 | }
11 | // A module exposed on a previous chunk
12 | if (typeof exposedRequire.r === 'function') {
13 | return exposedRequire.r(m, 1)
14 | }
15 | }
16 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "browser-pack-flat",
3 | "version": "3.5.0",
4 | "description": "bundle browserify modules into a single scope, a la rollup",
5 | "main": "index.js",
6 | "bin": {
7 | "browser-pack-flat": "cli.js"
8 | },
9 | "scripts": {
10 | "build": "node build",
11 | "prepare": "node build",
12 | "test": "node build && tape test/test.js test/expose.js test/order.js test/self.js"
13 | },
14 | "keywords": [],
15 | "author": "Renée Kooi ",
16 | "license": "MIT",
17 | "dependencies": {
18 | "JSONStream": "^1.3.2",
19 | "combine-source-map": "^0.8.0",
20 | "convert-source-map": "^1.5.1",
21 | "count-lines": "^0.1.2",
22 | "dedent": "^0.7.0",
23 | "estree-is-member-expression": "^1.0.0",
24 | "estree-is-require": "^1.0.0",
25 | "esutils": "^2.0.2",
26 | "path-parse": "^1.0.5",
27 | "scope-analyzer": "^2.0.0",
28 | "stream-combiner": "^0.2.2",
29 | "through2": "^3.0.2",
30 | "transform-ast": "^2.4.2",
31 | "umd": "^3.0.3",
32 | "wrap-comment": "^1.0.0"
33 | },
34 | "devDependencies": {
35 | "@babel/core": "^7.5.4",
36 | "@babel/plugin-transform-modules-commonjs": "^7.5.0",
37 | "babelify": "^10.0.0",
38 | "brfs": "^2.0.2",
39 | "browser-unpack": "^1.2.0",
40 | "browserify": "^17.0.0",
41 | "concat-stream": "^2.0.0",
42 | "nanohtml": "1.6.1",
43 | "sliced": "^1.0.1",
44 | "tape": "^5.0.0",
45 | "uglify-js": "3.6.0"
46 | },
47 | "directories": {
48 | "test": "test"
49 | },
50 | "repository": {
51 | "type": "git",
52 | "url": "git+https://github.com/goto-bus-stop/browser-pack-flat.git"
53 | },
54 | "bugs": {
55 | "url": "https://github.com/goto-bus-stop/browser-pack-flat/issues"
56 | },
57 | "homepage": "https://github.com/goto-bus-stop/browser-pack-flat#readme"
58 | }
59 |
--------------------------------------------------------------------------------
/plugin.js:
--------------------------------------------------------------------------------
1 | var pack = require('./index')
2 |
3 | module.exports = function apply (b, opts) {
4 | // When used as a transform
5 | if (typeof b !== 'object') {
6 | throw new Error('browser-pack-flat: must be used as a plugin, not a transform')
7 | }
8 |
9 | opts = Object.assign({}, opts || {}, {
10 | raw: true,
11 | debug: opts.debug || b._options.debug,
12 | basedir: b._options.basedir || process.cwd()
13 | })
14 |
15 | function addHooks () {
16 | var streams = b.pipeline.get('pack')
17 | var index = streams.indexOf(b._bpack)
18 |
19 | streams.splice(index, 1,
20 | pack(Object.assign({}, opts, {
21 | standalone: b._options.standalone,
22 | standaloneModule: b._options.standaloneModule
23 | }))
24 | )
25 | }
26 |
27 | addHooks()
28 | b.on('reset', addHooks)
29 | }
30 |
--------------------------------------------------------------------------------
/private_modules/identifierfy/LICENSE:
--------------------------------------------------------------------------------
1 | ISC License (ISC)
2 | Copyright (c) 2016, Mark Wubben
3 |
4 | Permission to use, copy, modify, and/or distribute this software for any purpose
5 | with or without fee is hereby granted, provided that the above copyright notice
6 | and this permission notice appear in all copies.
7 |
8 | THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
9 | REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
10 | FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
11 | INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
12 | OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
13 | TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
14 | THIS SOFTWARE.
15 |
--------------------------------------------------------------------------------
/private_modules/identifierfy/README.md:
--------------------------------------------------------------------------------
1 | # identifierfy
2 |
3 | Rewrites an identifier string so it's valid according to ES2015. Works in
4 | Node.js 6 and above.
5 |
6 | Please see [this awesome article by Mathias
7 | Bynens](https://mathiasbynens.be/notes/javascript-identifiers-es6) for
8 | background.
9 |
10 | ## Installation
11 |
12 | ```
13 | npm install identifierfy
14 | ```
15 |
16 | ## Usage
17 |
18 | The module has one default export, the `identifierfy` function:
19 |
20 | ```js
21 | const identifierfy = require('identifierfy')
22 | ```
23 |
24 | Call `identifierfy()` with an identifier string. It'll return a string that can
25 | be used as an identifier, which is useful when [writing Babel
26 | plugins](https://github.com/thejameskyle/babel-plugin-handbook).
27 |
28 | Characters that are not allowed in identifiers are dropped. Any character that
29 | follows a removed character is uppercased, except if the dropped character was
30 | at the front of the string.
31 |
32 | If necessary the resulting identifier is prefixed with an underscore. This will
33 | happen if the string is a reserved word or if the first character cannot be used
34 | as the first character (but is fine as the second character).
35 |
36 | This behavior can be overridden by passing a second `options` argument. This
37 | should be an object. Set `prefixReservedWords` to `false` to avoid reserved
38 | words being prefixed. Set `prefixInvalidIdentifiers` to `false` to avoid
39 | prefixing identifiers where the first character cannot be used. These options
40 | are useful if the resulting value is concatenated with other characters, making
41 | it valid after all.
42 |
43 | Note that `null` is returned if all characters from the original string are
44 | dropped.
45 |
46 | ## Examples
47 |
48 | ```js
49 | identifierfy(input)
50 | ```
51 |
52 | Input|Resulting identifier|Reason
53 | :---|:---|:---
54 | `'class`|`'_class'`|Reserved word
55 | `'42'`|`'_42'`|Identifiers cannot start with a number
56 | `'-foo'`|`'foo'`|The `-` is dropped, but since it's as the front `f` is not uppercased
57 | `'foo-bar🙊baz'`|`'fooBarBaz'`|The `-` and `🙊` characters are dropped, and the following characters uppercased
58 | `'foo-9'`|`foo9`|`9` can't be uppercased of course 😉
59 | `'💩'`|`null`|Sadly emojis cannot be used as identifiers 😢
60 |
61 | ```js
62 | identifierfy(input, {prefixReservedWords: false})
63 | ```
64 | Input|Resulting identifier|Reason
65 | :---|:---|:---
66 | `'class`|`'class'`|Reserved word, but prefixing is disabled
67 | `'42'`|`'_42'`|Identifiers cannot start with a number
68 |
69 | ```js
70 | identifierfy(input, {prefixInvalidIdentifiers: false})
71 | ```
72 | Input|Resulting identifier|Reason
73 | :---|:---|:---
74 | `'class`|`'_class'`|Reserved word
75 | `'42'`|`'42'`|Identifiers cannot start with a number, however prefixing is disabled so it's OK
76 |
77 | ```js
78 | identifierfy(input, {prefixInvalidIdentifiers: false, prefixReservedWords: false})
79 | ```
80 | Input|Resulting identifier|Reason
81 | :---|:---|:---
82 | `'class`|`'class'`|Reserved word, but prefixing is disabled
83 | `'42'`|`'42'`|Identifiers cannot start with a number, however prefixing is disabled so it's OK
84 |
--------------------------------------------------------------------------------
/private_modules/identifierfy/index.js:
--------------------------------------------------------------------------------
1 | /**
2 | * https://github.com/novemberborn/identifierfy, compiled to support Node 4
3 | */
4 |
5 | 'use strict'
6 | var keyword = require('esutils').keyword
7 |
8 | // Follow Babel's implementation:
9 | //
10 | function isValidIdentifier (name) {
11 | return !keyword.isReservedWordES6(name, true) && keyword.isIdentifierNameES6(name)
12 | }
13 |
14 | // Rewrite the name until it forms a valid identifier.
15 | module.exports = function identifierfy (name, options) {
16 | var prefixInvalidIdentifiers = options && options.prefixInvalidIdentifiers !== undefined ? options.prefixInvalidIdentifiers : true
17 | var prefixReservedWords = options && options.prefixReservedWords !== undefined ? options.prefixReservedWords : true
18 | // Start with a valid character. This way if the first character in the name
19 | // is not allowed to be used as the first character it can be prefixed with
20 | // an underscore, without having to be dropped. The same goes for if the name
21 | // is a reserved word.
22 | var intermediate = '_'
23 |
24 | // Flag whether the previous character was invalid (and thus dropped).
25 | var prevWasInvalid = false
26 |
27 | // Use for/of to iterate over the code points. This way surrogate pairs can
28 | // be avoided.
29 | for (var char of name) {
30 | // Try to uppercase the immediately following (not all characters have an
31 | // case equivalent though). Ignore if the dropped character was at the front
32 | // of the name.
33 | if (prevWasInvalid && intermediate !== '_') {
34 | char = char.toUpperCase()
35 | }
36 |
37 | // Only include characters if the name remains valid.
38 | if (isValidIdentifier(intermediate + char)) {
39 | intermediate += char
40 | prevWasInvalid = false
41 | } else {
42 | prevWasInvalid = true
43 | }
44 | }
45 |
46 | // Return `null` if no characters from the original name survive the process.
47 | if (intermediate === '_') return null
48 |
49 | // If the name is valid without the underscore prefix return it as such,
50 | // otherwise retain it, unless directed otherwise.
51 | var withoutPrefix = intermediate.slice(1)
52 | if (isValidIdentifier(withoutPrefix)) {
53 | return withoutPrefix
54 | } else if (prefixInvalidIdentifiers && prefixReservedWords) {
55 | return intermediate
56 | } else {
57 | var isIdentifierName = keyword.isIdentifierNameES6(withoutPrefix)
58 | var isReservedWord = keyword.isReservedWordES6(withoutPrefix, true)
59 | if ((!isIdentifierName && !prefixInvalidIdentifiers) ||
60 | (isReservedWord && !prefixReservedWords)) {
61 | return withoutPrefix
62 | } else {
63 | return intermediate
64 | }
65 | }
66 | }
67 |
--------------------------------------------------------------------------------
/private_modules/identifierfy/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "_from": "identifierfy@latest",
3 | "_id": "identifierfy@2.0.0",
4 | "_inBundle": false,
5 | "_integrity": "sha512-Gx1CmO0DbL5aECe3kclZNNDsGPIRo9NThTSTAeS3U8Pn58OsadGpU6ByxFriVHT8HQtGO9WErxZOfrXcx3yHOw==",
6 | "_location": "/identifierfy",
7 | "_phantomChildren": {},
8 | "_requested": {
9 | "type": "tag",
10 | "registry": true,
11 | "raw": "identifierfy@latest",
12 | "name": "identifierfy",
13 | "escapedName": "identifierfy",
14 | "rawSpec": "latest",
15 | "saveSpec": null,
16 | "fetchSpec": "latest"
17 | },
18 | "_requiredBy": [
19 | "#USER",
20 | "/"
21 | ],
22 | "_resolved": "https://registry.npmjs.org/identifierfy/-/identifierfy-2.0.0.tgz",
23 | "_shasum": "82922a33791e28b4e4d119dd1bc4a20c9a69c9c0",
24 | "_spec": "identifierfy@latest",
25 | "_where": "/home/goto-bus-stop/Code/goto-bus-stop/browser-pack-flat",
26 | "author": {
27 | "name": "Mark Wubben",
28 | "url": "https://novemberborn.net/"
29 | },
30 | "bugs": {
31 | "url": "https://github.com/novemberborn/identifierfy/issues"
32 | },
33 | "bundleDependencies": false,
34 | "dependencies": {
35 | "esutils": "^2.0.2"
36 | },
37 | "deprecated": false,
38 | "description": "Rewrites an identifier string so its valid according to ES2015",
39 | "devDependencies": {
40 | "@novemberborn/as-i-preach": "^11.0.0",
41 | "ava": "^1.0.0-beta.8",
42 | "nyc": "^13.0.1"
43 | },
44 | "engines": {
45 | "node": ">= 6"
46 | },
47 | "files": [
48 | "index.js"
49 | ],
50 | "homepage": "https://github.com/novemberborn/identifierfy#readme",
51 | "keywords": [
52 | "es6",
53 | "es2015",
54 | "identifier"
55 | ],
56 | "license": "ISC",
57 | "main": "index.js",
58 | "name": "identifierfy",
59 | "nyc": {
60 | "reporter": [
61 | "lcov",
62 | "html",
63 | "text"
64 | ]
65 | },
66 | "repository": {
67 | "type": "git",
68 | "url": "git+https://github.com/novemberborn/identifierfy.git"
69 | },
70 | "scripts": {
71 | "lint": "as-i-preach",
72 | "test": "as-i-preach && nyc ava"
73 | },
74 | "version": "2.0.0"
75 | }
76 |
--------------------------------------------------------------------------------
/readme.md:
--------------------------------------------------------------------------------
1 | # browser-pack-flat
2 |
3 | Bundle browserify modules into a single scope, a la rollup.
4 |
5 | Caveats:
6 |
7 | - Modules are executed fully, one after another, instead of inline.
8 | This is a potential difference from Node.js and the default browserify behaviour.
9 | Usually this does not matter, but rarely the order that some things are executed in may change.
10 | - This rewrites `require()` calls to simple variable assignments.
11 | If a module wraps `require()` somehow it probably will not work.
12 | In practice this is quite rare.
13 | - Using `factor-bundle` to split output code into separate files will not work with this plugin.
14 |
15 | ## Install
16 |
17 | ```bash
18 | npm install --save-dev browser-pack-flat
19 | ```
20 |
21 | ## Usage
22 |
23 | ```bash
24 | browserify /path/to/app.js | browser-unpack | browser-pack-flat
25 | ```
26 |
27 | Or as a plugin:
28 |
29 | ```bash
30 | browserify /path/to/app.js -p browser-pack-flat
31 | ```
32 |
33 | The plugin replaces the `browser-pack` module used by default by browserify.
34 |
35 | With the Node API:
36 |
37 | ```js
38 | var browserify = require('browserify')
39 | var packFlat = require('browser-pack-flat')
40 |
41 | browserify({ entries: './src/app.js' })
42 | .plugin(packFlat, { /* options */ })
43 | .bundle()
44 | .pipe(fs.createWriteStream('bundle.js'))
45 | ```
46 |
47 | ## What exactly?
48 |
49 | browserify uses [browser-pack](https://github.com/browserify/browser-pack) to output a bundle.
50 | browser-pack uses a small `require`-like runtime and wraps modules in functions to get a module loading behaviour that's almost identical to Node.js.
51 | However this resolution can take a few milliseconds across an entire bundle.
52 |
53 | Input:
54 |
55 | ```js
56 | var unique = require('uniq');
57 |
58 | var data = [1, 2, 2, 3, 4, 5, 5, 5, 6];
59 |
60 | console.log(unique(data));
61 | ```
62 |
63 | With browser-pack, this bundle would output:
64 |
65 | ```js
66 | (function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o
6 | News
7 |
8 |
9 |
10 |
${dep('title')}
11 |
12 | ${dep('excerpt')}
13 |
14 |
15 |
16 |

17 |
18 |
19 | By ${dep('author')}
20 |
21 |
22 |
23 | `)
24 |
--------------------------------------------------------------------------------
/test/input-source-map/dep.js:
--------------------------------------------------------------------------------
1 | export default function whatever (xyz) {
2 | return xyz.toUpperCase()
3 | }
4 |
--------------------------------------------------------------------------------
/test/input-source-map/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var _$dep_3 = {};
3 | "use strict";
4 |
5 | Object.defineProperty(_$dep_3, "__esModule", {
6 | value: true
7 | });
8 | _$dep_3.default = whatever;
9 | function whatever(xyz) {
10 | return xyz.toUpperCase();
11 | }
12 |
13 | var trailingNewlineRegex = /\n[\s]+$/
14 | var leadingNewlineRegex = /^\n[\s]+/
15 | var trailingSpaceRegex = /[\s]+$/
16 | var leadingSpaceRegex = /^[\s]+/
17 | var multiSpaceRegex = /[\n\s]+/g
18 |
19 | var TEXT_TAGS = [
20 | 'a', 'abbr', 'b', 'bdi', 'bdo', 'br', 'cite', 'data', 'dfn', 'em', 'i',
21 | 'kbd', 'mark', 'q', 'rp', 'rt', 'rtc', 'ruby', 's', 'amp', 'small', 'span',
22 | 'strong', 'sub', 'sup', 'time', 'u', 'var', 'wbr'
23 | ]
24 |
25 | var VERBATIM_TAGS = [
26 | 'code', 'pre', 'textarea'
27 | ]
28 |
29 | var _$appendChild_1 = function appendChild (el, childs) {
30 | if (!Array.isArray(childs)) return
31 |
32 | var nodeName = el.nodeName.toLowerCase()
33 |
34 | var hadText = false
35 | var value, leader
36 |
37 | for (var i = 0, len = childs.length; i < len; i++) {
38 | var node = childs[i]
39 | if (Array.isArray(node)) {
40 | appendChild(el, node)
41 | continue
42 | }
43 |
44 | if (typeof node === 'number' ||
45 | typeof node === 'boolean' ||
46 | typeof node === 'function' ||
47 | node instanceof Date ||
48 | node instanceof RegExp) {
49 | node = node.toString()
50 | }
51 |
52 | var lastChild = el.childNodes[el.childNodes.length - 1]
53 |
54 | // Iterate over text nodes
55 | if (typeof node === 'string') {
56 | hadText = true
57 |
58 | // If we already had text, append to the existing text
59 | if (lastChild && lastChild.nodeName === '#text') {
60 | lastChild.nodeValue += node
61 |
62 | // We didn't have a text node yet, create one
63 | } else {
64 | node = document.createTextNode(node)
65 | el.appendChild(node)
66 | lastChild = node
67 | }
68 |
69 | // If this is the last of the child nodes, make sure we close it out
70 | // right
71 | if (i === len - 1) {
72 | hadText = false
73 | // Trim the child text nodes if the current node isn't a
74 | // node where whitespace matters.
75 | if (TEXT_TAGS.indexOf(nodeName) === -1 &&
76 | VERBATIM_TAGS.indexOf(nodeName) === -1) {
77 | value = lastChild.nodeValue
78 | .replace(leadingNewlineRegex, '')
79 | .replace(trailingSpaceRegex, '')
80 | .replace(trailingNewlineRegex, '')
81 | .replace(multiSpaceRegex, ' ')
82 | if (value === '') {
83 | el.removeChild(lastChild)
84 | } else {
85 | lastChild.nodeValue = value
86 | }
87 | } else if (VERBATIM_TAGS.indexOf(nodeName) === -1) {
88 | // The very first node in the list should not have leading
89 | // whitespace. Sibling text nodes should have whitespace if there
90 | // was any.
91 | leader = i === 0 ? '' : ' '
92 | value = lastChild.nodeValue
93 | .replace(leadingNewlineRegex, leader)
94 | .replace(leadingSpaceRegex, ' ')
95 | .replace(trailingSpaceRegex, '')
96 | .replace(trailingNewlineRegex, '')
97 | .replace(multiSpaceRegex, ' ')
98 | lastChild.nodeValue = value
99 | }
100 | }
101 |
102 | // Iterate over DOM nodes
103 | } else if (node && node.nodeType) {
104 | // If the last node was a text node, make sure it is properly closed out
105 | if (hadText) {
106 | hadText = false
107 |
108 | // Trim the child text nodes if the current node isn't a
109 | // text node or a code node
110 | if (TEXT_TAGS.indexOf(nodeName) === -1 &&
111 | VERBATIM_TAGS.indexOf(nodeName) === -1) {
112 | value = lastChild.nodeValue
113 | .replace(leadingNewlineRegex, '')
114 | .replace(trailingNewlineRegex, '')
115 | .replace(multiSpaceRegex, ' ')
116 |
117 | // Remove empty text nodes, append otherwise
118 | if (value === '') {
119 | el.removeChild(lastChild)
120 | } else {
121 | lastChild.nodeValue = value
122 | }
123 | // Trim the child nodes if the current node is not a node
124 | // where all whitespace must be preserved
125 | } else if (VERBATIM_TAGS.indexOf(nodeName) === -1) {
126 | value = lastChild.nodeValue
127 | .replace(leadingSpaceRegex, ' ')
128 | .replace(leadingNewlineRegex, '')
129 | .replace(trailingNewlineRegex, '')
130 | .replace(multiSpaceRegex, ' ')
131 | lastChild.nodeValue = value
132 | }
133 | }
134 |
135 | // Store the last nodename
136 | var _nodeName = node.nodeName
137 | if (_nodeName) nodeName = _nodeName.toLowerCase()
138 |
139 | // Append the node to the DOM
140 | el.appendChild(node)
141 | }
142 | }
143 | }
144 |
145 | var _$app_2 = {};
146 | "use strict";
147 |
148 | var _dep = _interopRequireDefault(_$dep_3);
149 | var _athelas,
150 | _f,
151 | _f2,
152 | _w_,
153 | _db,
154 | _pl3Ns,
155 | _flex,
156 | _ttu,
157 | _f3,
158 | _f4,
159 | _pv,
160 | _mw;
161 | function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
162 | document.body.appendChild((_mw = document.createElement("section"), _mw.setAttribute("class", "mw7 center"), _$appendChild_1(_mw, ["\n\t ", (_athelas = document.createElement("h2"), _athelas.setAttribute("class", "athelas ph3 ph0-l"), _$appendChild_1(_athelas, ["News"]), _athelas), "\n\t ", (_pv = document.createElement("article"), _pv.setAttribute("class", "pv4 bt bb b--black-10 ph3 ph0-l"), _$appendChild_1(_pv, ["\n\t\t", (_flex = document.createElement("div"), _flex.setAttribute("class", "flex flex-column flex-row-ns"), _$appendChild_1(_flex, ["\n\t\t ", (_w_ = document.createElement("div"), _w_.setAttribute("class", "w-100 w-60-ns pr3-ns order-2 order-1-ns"), _$appendChild_1(_w_, ["\n\t\t\t ", (_f = document.createElement("h1"), _f.setAttribute("class", "f3 athelas mt0 lh-title"), _$appendChild_1(_f, [(0, _dep.default)('title')]), _f), "\n\t\t\t ", (_f2 = document.createElement("p"), _f2.setAttribute("class", "f5 f4-l lh-copy athelas"), _$appendChild_1(_f2, ["\n\t\t\t\t", (0, _dep.default)('excerpt'), "\n\t\t\t "]), _f2), "\n\t\t "]), _w_), "\n\t\t ", (_pl3Ns = document.createElement("div"), _pl3Ns.setAttribute("class", "pl3-ns order-1 order-2-ns mb4 mb0-ns w-100 w-40-ns"), _$appendChild_1(_pl3Ns, ["\n\t\t\t ", (_db = document.createElement("img"), _db.setAttribute("src", "http://mrmrs.github.io/photos/cpu.jpg"), _db.setAttribute("alt", "Photo of a dimly lit room with a computer interface terminal."), _db.setAttribute("class", "db"), _db), "\n\t\t "]), _pl3Ns), "\n\t\t"]), _flex), "\n\t\t", (_f3 = document.createElement("p"), _f3.setAttribute("class", "f6 lh-copy gray mv0"), _$appendChild_1(_f3, ["By ", (_ttu = document.createElement("span"), _ttu.setAttribute("class", "ttu"), _$appendChild_1(_ttu, [(0, _dep.default)('author')]), _ttu)]), _f3), "\n\t\t", (_f4 = document.createElement("time"), _f4.setAttribute("class", "f6 db gray"), _$appendChild_1(_f4, [(0, _dep.default)('timestamp')]), _f4), "\n\t "]), _pv), "\n "]), _mw));
163 |
164 | }());
165 | //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIl9wcmVsdWRlIiwidGVzdC9pbnB1dC1zb3VyY2UtbWFwL2RlcC5qcyIsIm5vZGVfbW9kdWxlcy9uYW5vaHRtbC9saWIvYXBwZW5kLWNoaWxkLmpzIiwidGVzdC9pbnB1dC1zb3VyY2UtbWFwL2FwcC5qcyIsIl9wb3N0bHVkZSJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTtBQUNBOzs7Ozs7O0FDRGUsU0FBUyxRQUFRLENBQUUsR0FBRyxFQUFFO0VBQ3JDLE9BQU8sR0FBRyxDQUFDLFdBQVcsRUFBRSxDQUFBO0NBQzFCOztBQ0ZBLElBQUksb0JBQW9CLEdBQUcsVUFBVTtBQUNyQyxJQUFJLG1CQUFtQixHQUFHLFVBQVU7QUFDcEMsSUFBSSxrQkFBa0IsR0FBRyxRQUFRO0FBQ2pDLElBQUksaUJBQWlCLEdBQUcsUUFBUTtBQUNoQyxJQUFJLGVBQWUsR0FBRyxVQUFVOztBQUVoQyxJQUFJLFNBQVMsR0FBRztFQUNkLEdBQUcsRUFBRSxNQUFNLEVBQUUsR0FBRyxFQUFFLEtBQUssRUFBRSxLQUFLLEVBQUUsSUFBSSxFQUFFLE1BQU0sRUFBRSxNQUFNLEVBQUUsS0FBSyxFQUFFLElBQUksRUFBRSxHQUFHO0VBQ3RFLEtBQUssRUFBRSxNQUFNLEVBQUUsR0FBRyxFQUFFLElBQUksRUFBRSxJQUFJLEVBQUUsS0FBSyxFQUFFLE1BQU0sRUFBRSxHQUFHLEVBQUUsS0FBSyxFQUFFLE9BQU8sRUFBRSxNQUFNO0VBQzFFLFFBQVEsRUFBRSxLQUFLLEVBQUUsS0FBSyxFQUFFLE1BQU0sRUFBRSxHQUFHLEVBQUUsS0FBSyxFQUFFLEtBQUs7Q0FDbEQ7O0FBRUQsSUFBSSxhQUFhLEdBQUc7RUFDbEIsTUFBTSxFQUFFLEtBQUssRUFBRSxVQUFVO0NBQzFCOztBQUVELG1CQUFjLEdBQUcsU0FBUyxXQUFXLEVBQUUsRUFBRSxFQUFFLE1BQU0sRUFBRTtFQUNqRCxJQUFJLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxNQUFNLENBQUMsRUFBRSxNQUFNOztFQUVsQyxJQUFJLFFBQVEsR0FBRyxFQUFFLENBQUMsUUFBUSxDQUFDLFdBQVcsRUFBRTs7RUFFeEMsSUFBSSxPQUFPLEdBQUcsS0FBSztFQUNuQixJQUFJLEtBQUssRUFBRSxNQUFNOztFQUVqQixLQUFLLElBQUksQ0FBQyxHQUFHLENBQUMsRUFBRSxHQUFHLEdBQUcsTUFBTSxDQUFDLE1BQU0sRUFBRSxDQUFDLEdBQUcsR0FBRyxFQUFFLENBQUMsRUFBRSxFQUFFO0lBQ2pELElBQUksSUFBSSxHQUFHLE1BQU0sQ0FBQyxDQUFDLENBQUM7SUFDcEIsSUFBSSxLQUFLLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyxFQUFFO01BQ3ZCLFdBQVcsQ0FBQyxFQUFFLEVBQUUsSUFBSSxDQUFDO01BQ3JCLFFBQVE7S0FDVDs7SUFFRCxJQUFJLE9BQU8sSUFBSSxLQUFLLFFBQVE7TUFDMUIsT0FBTyxJQUFJLEtBQUssU0FBUztNQUN6QixPQUFPLElBQUksS0FBSyxVQUFVO01BQzFCLElBQUksWUFBWSxJQUFJO01BQ3BCLElBQUksWUFBWSxNQUFNLEVBQUU7TUFDeEIsSUFBSSxHQUFHLElBQUksQ0FBQyxRQUFRLEVBQUU7S0FDdkI7O0lBRUQsSUFBSSxTQUFTLEdBQUcsRUFBRSxDQUFDLFVBQVUsQ0FBQyxFQUFFLENBQUMsVUFBVSxDQUFDLE1BQU0sR0FBRyxDQUFDLENBQUM7OztJQUd2RCxJQUFJLE9BQU8sSUFBSSxLQUFLLFFBQVEsRUFBRTtNQUM1QixPQUFPLEdBQUcsSUFBSTs7O01BR2QsSUFBSSxTQUFTLElBQUksU0FBUyxDQUFDLFFBQVEsS0FBSyxPQUFPLEVBQUU7UUFDL0MsU0FBUyxDQUFDLFNBQVMsSUFBSSxJQUFJOzs7T0FHNUIsTUFBTTtRQUNMLElBQUksR0FBRyxRQUFRLENBQUMsY0FBYyxDQUFDLElBQUksQ0FBQztRQUNwQyxFQUFFLENBQUMsV0FBVyxDQUFDLElBQUksQ0FBQztRQUNwQixTQUFTLEdBQUcsSUFBSTtPQUNqQjs7OztNQUlELElBQUksQ0FBQyxLQUFLLEdBQUcsR0FBRyxDQUFDLEVBQUU7UUFDakIsT0FBTyxHQUFHLEtBQUs7OztRQUdmLElBQUksU0FBUyxDQUFDLE9BQU8sQ0FBQyxRQUFRLENBQUMsS0FBSyxDQUFDLENBQUM7VUFDcEMsYUFBYSxDQUFDLE9BQU8sQ0FBQyxRQUFRLENBQUMsS0FBSyxDQUFDLENBQUMsRUFBRTtVQUN4QyxLQUFLLEdBQUcsU0FBUyxDQUFDLFNBQVM7YUFDeEIsT0FBTyxDQUFDLG1CQUFtQixFQUFFLEVBQUUsQ0FBQzthQUNoQyxPQUFPLENBQUMsa0JBQWtCLEVBQUUsRUFBRSxDQUFDO2FBQy9CLE9BQU8sQ0FBQyxvQkFBb0IsRUFBRSxFQUFFLENBQUM7YUFDakMsT0FBTyxDQUFDLGVBQWUsRUFBRSxHQUFHLENBQUM7VUFDaEMsSUFBSSxLQUFLLEtBQUssRUFBRSxFQUFFO1lBQ2hCLEVBQUUsQ0FBQyxXQUFXLENBQUMsU0FBUyxDQUFDO1dBQzFCLE1BQU07WUFDTCxTQUFTLENBQUMsU0FBUyxHQUFHLEtBQUs7V0FDNUI7U0FDRixNQUFNLElBQUksYUFBYSxDQUFDLE9BQU8sQ0FBQyxRQUFRLENBQUMsS0FBSyxDQUFDLENBQUMsRUFBRTs7OztVQUlqRCxNQUFNLEdBQUcsQ0FBQyxLQUFLLENBQUMsR0FBRyxFQUFFLEdBQUcsR0FBRztVQUMzQixLQUFLLEdBQUcsU0FBUyxDQUFDLFNBQVM7YUFDeEIsT0FBTyxDQUFDLG1CQUFtQixFQUFFLE1BQU0sQ0FBQzthQUNwQyxPQUFPLENBQUMsaUJBQWlCLEVBQUUsR0FBRyxDQUFDO2FBQy9CLE9BQU8sQ0FBQyxrQkFBa0IsRUFBRSxFQUFFLENBQUM7YUFDL0IsT0FBTyxDQUFDLG9CQUFvQixFQUFFLEVBQUUsQ0FBQzthQUNqQyxPQUFPLENBQUMsZUFBZSxFQUFFLEdBQUcsQ0FBQztVQUNoQyxTQUFTLENBQUMsU0FBUyxHQUFHLEtBQUs7U0FDNUI7T0FDRjs7O0tBR0YsTUFBTSxJQUFJLElBQUksSUFBSSxJQUFJLENBQUMsUUFBUSxFQUFFOztNQUVoQyxJQUFJLE9BQU8sRUFBRTtRQUNYLE9BQU8sR0FBRyxLQUFLOzs7O1FBSWYsSUFBSSxTQUFTLENBQUMsT0FBTyxDQUFDLFFBQVEsQ0FBQyxLQUFLLENBQUMsQ0FBQztVQUNwQyxhQUFhLENBQUMsT0FBTyxDQUFDLFFBQVEsQ0FBQyxLQUFLLENBQUMsQ0FBQyxFQUFFO1VBQ3hDLEtBQUssR0FBRyxTQUFTLENBQUMsU0FBUzthQUN4QixPQUFPLENBQUMsbUJBQW1CLEVBQUUsRUFBRSxDQUFDO2FBQ2hDLE9BQU8sQ0FBQyxvQkFBb0IsRUFBRSxFQUFFLENBQUM7YUFDakMsT0FBTyxDQUFDLGVBQWUsRUFBRSxHQUFHLENBQUM7OztVQUdoQyxJQUFJLEtBQUssS0FBSyxFQUFFLEVBQUU7WUFDaEIsRUFBRSxDQUFDLFdBQVcsQ0FBQyxTQUFTLENBQUM7V0FDMUIsTUFBTTtZQUNMLFNBQVMsQ0FBQyxTQUFTLEdBQUcsS0FBSztXQUM1Qjs7O1NBR0YsTUFBTSxJQUFJLGFBQWEsQ0FBQyxPQUFPLENBQUMsUUFBUSxDQUFDLEtBQUssQ0FBQyxDQUFDLEVBQUU7VUFDakQsS0FBSyxHQUFHLFNBQVMsQ0FBQyxTQUFTO2FBQ3hCLE9BQU8sQ0FBQyxpQkFBaUIsRUFBRSxHQUFHLENBQUM7YUFDL0IsT0FBTyxDQUFDLG1CQUFtQixFQUFFLEVBQUUsQ0FBQzthQUNoQyxPQUFPLENBQUMsb0JBQW9CLEVBQUUsRUFBRSxDQUFDO2FBQ2pDLE9BQU8sQ0FBQyxlQUFlLEVBQUUsR0FBRyxDQUFDO1VBQ2hDLFNBQVMsQ0FBQyxTQUFTLEdBQUcsS0FBSztTQUM1QjtPQUNGOzs7TUFHRCxJQUFJLFNBQVMsR0FBRyxJQUFJLENBQUMsUUFBUTtNQUM3QixJQUFJLFNBQVMsRUFBRSxRQUFRLEdBQUcsU0FBUyxDQUFDLFdBQVcsRUFBRTs7O01BR2pELEVBQUUsQ0FBQyxXQUFXLENBQUMsSUFBSSxDQUFDO0tBQ3JCO0dBQ0Y7Q0FDRjs7Ozs7QUNsSUQsSUFBQSxJQUFBLEdBQUEsc0JBQUEsQ0FBQSxPQUFBLENBQUEsQ0FBQTtBQUF1QixJQUFBLFFBQUE7RUFBQSxFQUFBO0VBQUEsR0FBQTtFQUFBLEdBQUE7RUFBQSxHQUFBO0VBQUEsTUFBQTtFQUFBLEtBQUE7RUFBQSxJQUFBO0VBQUEsR0FBQTtFQUFBLEdBQUE7RUFBQSxHQUFBO0VBQUEsR0FBQSxDQUFBO0FBQUEsU0FBQSxzQkFBQSxDQUFBLENBQUEsRUFBQSxFQUFBLE9BQUEsQ0FBQSxJQUFBLENBQUEsQ0FBQSxVQUFBLEdBQUEsQ0FBQSxHQUFBLEVBQUEsT0FBQSxFQUFBLENBQUEsRUFBQSxDQUFBLEVBQUE7QUFHdkIsUUFBUSxDQUFDLElBQUksQ0FBQyxXQUFXLEVBQUEsR0FBQSxHQUFBLFFBQUEsQ0FBQSxhQUFBLENBQUEsU0FBQSxDQUFBLEVBQUEsR0FBQSxDQUFBLFlBQUEsQ0FBQSxPQUFBLEVBQUEsWUFBQSxDQUFBLEVBQUEsZUFBQSxDQUFBLEdBQUEsRUFBQSxDQUFBLE9BQUEsR0FBQSxRQUFBLEdBQUEsUUFBQSxDQUFBLGFBQUEsQ0FBQSxJQUFBLENBQUEsRUFBQSxRQUFBLENBQUEsWUFBQSxDQUFBLE9BQUEsRUFBQSxtQkFBQSxDQUFBLEVBQUEsZUFBQSxDQUFBLFFBQUEsRUFBQSxDQUFBLE1BQUEsQ0FBQSxDQUFBLEVBQUEsUUFBQSxHQUFBLE9BQUEsR0FBQSxHQUFBLEdBQUEsUUFBQSxDQUFBLGFBQUEsQ0FBQSxTQUFBLENBQUEsRUFBQSxHQUFBLENBQUEsWUFBQSxDQUFBLE9BQUEsRUFBQSxpQ0FBQSxDQUFBLEVBQUEsZUFBQSxDQUFBLEdBQUEsRUFBQSxDQUFBLFFBQUEsR0FBQSxLQUFBLEdBQUEsUUFBQSxDQUFBLGFBQUEsQ0FBQSxLQUFBLENBQUEsRUFBQSxLQUFBLENBQUEsWUFBQSxDQUFBLE9BQUEsRUFBQSw4QkFBQSxDQUFBLEVBQUEsZUFBQSxDQUFBLEtBQUEsRUFBQSxDQUFBLFVBQUEsR0FBQSxHQUFBLEdBQUEsUUFBQSxDQUFBLGFBQUEsQ0FBQSxLQUFBLENBQUEsRUFBQSxHQUFBLENBQUEsWUFBQSxDQUFBLE9BQUEsRUFBQSx5Q0FBQSxDQUFBLEVBQUEsZUFBQSxDQUFBLEdBQUEsRUFBQSxDQUFBLFdBQUEsR0FBQSxFQUFBLEdBQUEsUUFBQSxDQUFBLGFBQUEsQ0FBQSxJQUFBLENBQUEsRUFBQSxFQUFBLENBQUEsWUFBQSxDQUFBLE9BQUEsRUFBQSx5QkFBQSxDQUFBLEVBQUEsZUFBQSxDQUFBLEVBQUEsRUFBQSxDQU1pQixDQUFBLENBQUEsRUFBQSxJQUFBLENBQUEsT0FBRyxFQUFDLE9BQU8sQ0FBQyxDQUFBLENBQUEsRUFBQSxFQUFBLEdBQUEsV0FBQSxHQUFBLEdBQUEsR0FBQSxRQUFBLENBQUEsYUFBQSxDQUFBLEdBQUEsQ0FBQSxFQUFBLEdBQUEsQ0FBQSxZQUFBLENBQUEsT0FBQSxFQUFBLHlCQUFBLENBQUEsRUFBQSxlQUFBLENBQUEsR0FBQSxFQUFBLENBQUEsWUFBQSxFQUVoRCxDQUFBLENBQUEsRUFBQSxJQUFBLENBQUEsT0FBRyxFQUFDLFNBQVMsQ0FBQyxFQUFBLFdBQUEsQ0FBQSxDQUFBLEVBQUEsR0FBQSxHQUFBLFVBQUEsQ0FBQSxDQUFBLEVBQUEsR0FBQSxHQUFBLFVBQUEsR0FBQSxNQUFBLEdBQUEsUUFBQSxDQUFBLGFBQUEsQ0FBQSxLQUFBLENBQUEsRUFBQSxNQUFBLENBQUEsWUFBQSxDQUFBLE9BQUEsRUFBQSxvREFBQSxDQUFBLEVBQUEsZUFBQSxDQUFBLE1BQUEsRUFBQSxDQUFBLFdBQUEsR0FBQSxHQUFBLEdBQUEsUUFBQSxDQUFBLGFBQUEsQ0FBQSxLQUFBLENBQUEsRUFBQSxHQUFBLENBQUEsWUFBQSxDQUFBLEtBQUEsRUFBQSx1Q0FBQSxDQUFBLEVBQUEsR0FBQSxDQUFBLFlBQUEsQ0FBQSxLQUFBLEVBQUEsK0RBQUEsQ0FBQSxFQUFBLEdBQUEsQ0FBQSxZQUFBLENBQUEsT0FBQSxFQUFBLElBQUEsQ0FBQSxFQUFBLEdBQUEsR0FBQSxVQUFBLENBQUEsQ0FBQSxFQUFBLE1BQUEsR0FBQSxRQUFBLENBQUEsQ0FBQSxFQUFBLEtBQUEsR0FBQSxRQUFBLEdBQUEsR0FBQSxHQUFBLFFBQUEsQ0FBQSxhQUFBLENBQUEsR0FBQSxDQUFBLEVBQUEsR0FBQSxDQUFBLFlBQUEsQ0FBQSxPQUFBLEVBQUEscUJBQUEsQ0FBQSxFQUFBLGVBQUEsQ0FBQSxHQUFBLEVBQUEsQ0FBQSxLQUFBLEdBQUEsSUFBQSxHQUFBLFFBQUEsQ0FBQSxhQUFBLENBQUEsTUFBQSxDQUFBLEVBQUEsSUFBQSxDQUFBLFlBQUEsQ0FBQSxPQUFBLEVBQUEsS0FBQSxDQUFBLEVBQUEsZUFBQSxDQUFBLElBQUEsRUFBQSxDQU9vQyxDQUFBLENBQUEsRUFBQSxJQUFBLENBQUEsT0FBRyxFQUFDLFFBQVEsQ0FBQyxDQUFBLENBQUEsRUFBQSxJQUFBLEVBQUEsQ0FBQSxFQUFBLEdBQUEsR0FBQSxRQUFBLEdBQUEsR0FBQSxHQUFBLFFBQUEsQ0FBQSxhQUFBLENBQUEsTUFBQSxDQUFBLEVBQUEsR0FBQSxDQUFBLFlBQUEsQ0FBQSxPQUFBLEVBQUEsWUFBQSxDQUFBLEVBQUEsZUFBQSxDQUFBLEdBQUEsRUFBQSxDQUN4QyxDQUFBLENBQUEsRUFBQSxJQUFBLENBQUEsT0FBRyxFQUFDLFdBQVcsQ0FBQyxDQUFBLENBQUEsRUFBQSxHQUFBLEdBQUEsT0FBQSxDQUFBLENBQUEsRUFBQSxHQUFBLEdBQUEsTUFBQSxDQUFBLENBQUEsRUFBQSxHQUFBLEVBRzNDLENBQUE7QUN0QkY7QUFDQSIsImZpbGUiOiJnZW5lcmF0ZWQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlc0NvbnRlbnQiOlsiKGZ1bmN0aW9uKCl7XG4iLCJleHBvcnQgZGVmYXVsdCBmdW5jdGlvbiB3aGF0ZXZlciAoeHl6KSB7XG4gIHJldHVybiB4eXoudG9VcHBlckNhc2UoKVxufVxuIiwidmFyIHRyYWlsaW5nTmV3bGluZVJlZ2V4ID0gL1xcbltcXHNdKyQvXG52YXIgbGVhZGluZ05ld2xpbmVSZWdleCA9IC9eXFxuW1xcc10rL1xudmFyIHRyYWlsaW5nU3BhY2VSZWdleCA9IC9bXFxzXSskL1xudmFyIGxlYWRpbmdTcGFjZVJlZ2V4ID0gL15bXFxzXSsvXG52YXIgbXVsdGlTcGFjZVJlZ2V4ID0gL1tcXG5cXHNdKy9nXG5cbnZhciBURVhUX1RBR1MgPSBbXG4gICdhJywgJ2FiYnInLCAnYicsICdiZGknLCAnYmRvJywgJ2JyJywgJ2NpdGUnLCAnZGF0YScsICdkZm4nLCAnZW0nLCAnaScsXG4gICdrYmQnLCAnbWFyaycsICdxJywgJ3JwJywgJ3J0JywgJ3J0YycsICdydWJ5JywgJ3MnLCAnYW1wJywgJ3NtYWxsJywgJ3NwYW4nLFxuICAnc3Ryb25nJywgJ3N1YicsICdzdXAnLCAndGltZScsICd1JywgJ3ZhcicsICd3YnInXG5dXG5cbnZhciBWRVJCQVRJTV9UQUdTID0gW1xuICAnY29kZScsICdwcmUnLCAndGV4dGFyZWEnXG5dXG5cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gYXBwZW5kQ2hpbGQgKGVsLCBjaGlsZHMpIHtcbiAgaWYgKCFBcnJheS5pc0FycmF5KGNoaWxkcykpIHJldHVyblxuXG4gIHZhciBub2RlTmFtZSA9IGVsLm5vZGVOYW1lLnRvTG93ZXJDYXNlKClcblxuICB2YXIgaGFkVGV4dCA9IGZhbHNlXG4gIHZhciB2YWx1ZSwgbGVhZGVyXG5cbiAgZm9yICh2YXIgaSA9IDAsIGxlbiA9IGNoaWxkcy5sZW5ndGg7IGkgPCBsZW47IGkrKykge1xuICAgIHZhciBub2RlID0gY2hpbGRzW2ldXG4gICAgaWYgKEFycmF5LmlzQXJyYXkobm9kZSkpIHtcbiAgICAgIGFwcGVuZENoaWxkKGVsLCBub2RlKVxuICAgICAgY29udGludWVcbiAgICB9XG5cbiAgICBpZiAodHlwZW9mIG5vZGUgPT09ICdudW1iZXInIHx8XG4gICAgICB0eXBlb2Ygbm9kZSA9PT0gJ2Jvb2xlYW4nIHx8XG4gICAgICB0eXBlb2Ygbm9kZSA9PT0gJ2Z1bmN0aW9uJyB8fFxuICAgICAgbm9kZSBpbnN0YW5jZW9mIERhdGUgfHxcbiAgICAgIG5vZGUgaW5zdGFuY2VvZiBSZWdFeHApIHtcbiAgICAgIG5vZGUgPSBub2RlLnRvU3RyaW5nKClcbiAgICB9XG5cbiAgICB2YXIgbGFzdENoaWxkID0gZWwuY2hpbGROb2Rlc1tlbC5jaGlsZE5vZGVzLmxlbmd0aCAtIDFdXG5cbiAgICAvLyBJdGVyYXRlIG92ZXIgdGV4dCBub2Rlc1xuICAgIGlmICh0eXBlb2Ygbm9kZSA9PT0gJ3N0cmluZycpIHtcbiAgICAgIGhhZFRleHQgPSB0cnVlXG5cbiAgICAgIC8vIElmIHdlIGFscmVhZHkgaGFkIHRleHQsIGFwcGVuZCB0byB0aGUgZXhpc3RpbmcgdGV4dFxuICAgICAgaWYgKGxhc3RDaGlsZCAmJiBsYXN0Q2hpbGQubm9kZU5hbWUgPT09ICcjdGV4dCcpIHtcbiAgICAgICAgbGFzdENoaWxkLm5vZGVWYWx1ZSArPSBub2RlXG5cbiAgICAgIC8vIFdlIGRpZG4ndCBoYXZlIGEgdGV4dCBub2RlIHlldCwgY3JlYXRlIG9uZVxuICAgICAgfSBlbHNlIHtcbiAgICAgICAgbm9kZSA9IGRvY3VtZW50LmNyZWF0ZVRleHROb2RlKG5vZGUpXG4gICAgICAgIGVsLmFwcGVuZENoaWxkKG5vZGUpXG4gICAgICAgIGxhc3RDaGlsZCA9IG5vZGVcbiAgICAgIH1cblxuICAgICAgLy8gSWYgdGhpcyBpcyB0aGUgbGFzdCBvZiB0aGUgY2hpbGQgbm9kZXMsIG1ha2Ugc3VyZSB3ZSBjbG9zZSBpdCBvdXRcbiAgICAgIC8vIHJpZ2h0XG4gICAgICBpZiAoaSA9PT0gbGVuIC0gMSkge1xuICAgICAgICBoYWRUZXh0ID0gZmFsc2VcbiAgICAgICAgLy8gVHJpbSB0aGUgY2hpbGQgdGV4dCBub2RlcyBpZiB0aGUgY3VycmVudCBub2RlIGlzbid0IGFcbiAgICAgICAgLy8gbm9kZSB3aGVyZSB3aGl0ZXNwYWNlIG1hdHRlcnMuXG4gICAgICAgIGlmIChURVhUX1RBR1MuaW5kZXhPZihub2RlTmFtZSkgPT09IC0xICYmXG4gICAgICAgICAgVkVSQkFUSU1fVEFHUy5pbmRleE9mKG5vZGVOYW1lKSA9PT0gLTEpIHtcbiAgICAgICAgICB2YWx1ZSA9IGxhc3RDaGlsZC5ub2RlVmFsdWVcbiAgICAgICAgICAgIC5yZXBsYWNlKGxlYWRpbmdOZXdsaW5lUmVnZXgsICcnKVxuICAgICAgICAgICAgLnJlcGxhY2UodHJhaWxpbmdTcGFjZVJlZ2V4LCAnJylcbiAgICAgICAgICAgIC5yZXBsYWNlKHRyYWlsaW5nTmV3bGluZVJlZ2V4LCAnJylcbiAgICAgICAgICAgIC5yZXBsYWNlKG11bHRpU3BhY2VSZWdleCwgJyAnKVxuICAgICAgICAgIGlmICh2YWx1ZSA9PT0gJycpIHtcbiAgICAgICAgICAgIGVsLnJlbW92ZUNoaWxkKGxhc3RDaGlsZClcbiAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgbGFzdENoaWxkLm5vZGVWYWx1ZSA9IHZhbHVlXG4gICAgICAgICAgfVxuICAgICAgICB9IGVsc2UgaWYgKFZFUkJBVElNX1RBR1MuaW5kZXhPZihub2RlTmFtZSkgPT09IC0xKSB7XG4gICAgICAgICAgLy8gVGhlIHZlcnkgZmlyc3Qgbm9kZSBpbiB0aGUgbGlzdCBzaG91bGQgbm90IGhhdmUgbGVhZGluZ1xuICAgICAgICAgIC8vIHdoaXRlc3BhY2UuIFNpYmxpbmcgdGV4dCBub2RlcyBzaG91bGQgaGF2ZSB3aGl0ZXNwYWNlIGlmIHRoZXJlXG4gICAgICAgICAgLy8gd2FzIGFueS5cbiAgICAgICAgICBsZWFkZXIgPSBpID09PSAwID8gJycgOiAnICdcbiAgICAgICAgICB2YWx1ZSA9IGxhc3RDaGlsZC5ub2RlVmFsdWVcbiAgICAgICAgICAgIC5yZXBsYWNlKGxlYWRpbmdOZXdsaW5lUmVnZXgsIGxlYWRlcilcbiAgICAgICAgICAgIC5yZXBsYWNlKGxlYWRpbmdTcGFjZVJlZ2V4LCAnICcpXG4gICAgICAgICAgICAucmVwbGFjZSh0cmFpbGluZ1NwYWNlUmVnZXgsICcnKVxuICAgICAgICAgICAgLnJlcGxhY2UodHJhaWxpbmdOZXdsaW5lUmVnZXgsICcnKVxuICAgICAgICAgICAgLnJlcGxhY2UobXVsdGlTcGFjZVJlZ2V4LCAnICcpXG4gICAgICAgICAgbGFzdENoaWxkLm5vZGVWYWx1ZSA9IHZhbHVlXG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgIC8vIEl0ZXJhdGUgb3ZlciBET00gbm9kZXNcbiAgICB9IGVsc2UgaWYgKG5vZGUgJiYgbm9kZS5ub2RlVHlwZSkge1xuICAgICAgLy8gSWYgdGhlIGxhc3Qgbm9kZSB3YXMgYSB0ZXh0IG5vZGUsIG1ha2Ugc3VyZSBpdCBpcyBwcm9wZXJseSBjbG9zZWQgb3V0XG4gICAgICBpZiAoaGFkVGV4dCkge1xuICAgICAgICBoYWRUZXh0ID0gZmFsc2VcblxuICAgICAgICAvLyBUcmltIHRoZSBjaGlsZCB0ZXh0IG5vZGVzIGlmIHRoZSBjdXJyZW50IG5vZGUgaXNuJ3QgYVxuICAgICAgICAvLyB0ZXh0IG5vZGUgb3IgYSBjb2RlIG5vZGVcbiAgICAgICAgaWYgKFRFWFRfVEFHUy5pbmRleE9mKG5vZGVOYW1lKSA9PT0gLTEgJiZcbiAgICAgICAgICBWRVJCQVRJTV9UQUdTLmluZGV4T2Yobm9kZU5hbWUpID09PSAtMSkge1xuICAgICAgICAgIHZhbHVlID0gbGFzdENoaWxkLm5vZGVWYWx1ZVxuICAgICAgICAgICAgLnJlcGxhY2UobGVhZGluZ05ld2xpbmVSZWdleCwgJycpXG4gICAgICAgICAgICAucmVwbGFjZSh0cmFpbGluZ05ld2xpbmVSZWdleCwgJycpXG4gICAgICAgICAgICAucmVwbGFjZShtdWx0aVNwYWNlUmVnZXgsICcgJylcblxuICAgICAgICAgIC8vIFJlbW92ZSBlbXB0eSB0ZXh0IG5vZGVzLCBhcHBlbmQgb3RoZXJ3aXNlXG4gICAgICAgICAgaWYgKHZhbHVlID09PSAnJykge1xuICAgICAgICAgICAgZWwucmVtb3ZlQ2hpbGQobGFzdENoaWxkKVxuICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICBsYXN0Q2hpbGQubm9kZVZhbHVlID0gdmFsdWVcbiAgICAgICAgICB9XG4gICAgICAgIC8vIFRyaW0gdGhlIGNoaWxkIG5vZGVzIGlmIHRoZSBjdXJyZW50IG5vZGUgaXMgbm90IGEgbm9kZVxuICAgICAgICAvLyB3aGVyZSBhbGwgd2hpdGVzcGFjZSBtdXN0IGJlIHByZXNlcnZlZFxuICAgICAgICB9IGVsc2UgaWYgKFZFUkJBVElNX1RBR1MuaW5kZXhPZihub2RlTmFtZSkgPT09IC0xKSB7XG4gICAgICAgICAgdmFsdWUgPSBsYXN0Q2hpbGQubm9kZVZhbHVlXG4gICAgICAgICAgICAucmVwbGFjZShsZWFkaW5nU3BhY2VSZWdleCwgJyAnKVxuICAgICAgICAgICAgLnJlcGxhY2UobGVhZGluZ05ld2xpbmVSZWdleCwgJycpXG4gICAgICAgICAgICAucmVwbGFjZSh0cmFpbGluZ05ld2xpbmVSZWdleCwgJycpXG4gICAgICAgICAgICAucmVwbGFjZShtdWx0aVNwYWNlUmVnZXgsICcgJylcbiAgICAgICAgICBsYXN0Q2hpbGQubm9kZVZhbHVlID0gdmFsdWVcbiAgICAgICAgfVxuICAgICAgfVxuXG4gICAgICAvLyBTdG9yZSB0aGUgbGFzdCBub2RlbmFtZVxuICAgICAgdmFyIF9ub2RlTmFtZSA9IG5vZGUubm9kZU5hbWVcbiAgICAgIGlmIChfbm9kZU5hbWUpIG5vZGVOYW1lID0gX25vZGVOYW1lLnRvTG93ZXJDYXNlKClcblxuICAgICAgLy8gQXBwZW5kIHRoZSBub2RlIHRvIHRoZSBET01cbiAgICAgIGVsLmFwcGVuZENoaWxkKG5vZGUpXG4gICAgfVxuICB9XG59XG4iLCJpbXBvcnQgZGVwIGZyb20gXCIuL2RlcFwiXG5pbXBvcnQgaHRtbCBmcm9tICdiZWwnXG5cbmRvY3VtZW50LmJvZHkuYXBwZW5kQ2hpbGQoaHRtbGBcbiAgPHNlY3Rpb24gY2xhc3M9XCJtdzcgY2VudGVyXCI+XG5cdCA8aDIgY2xhc3M9XCJhdGhlbGFzIHBoMyBwaDAtbFwiPk5ld3M8L2gyPlxuXHQgPGFydGljbGUgY2xhc3M9XCJwdjQgYnQgYmIgYi0tYmxhY2stMTAgcGgzIHBoMC1sXCI+XG5cdFx0PGRpdiBjbGFzcz1cImZsZXggZmxleC1jb2x1bW4gZmxleC1yb3ctbnNcIj5cblx0XHQgIDxkaXYgY2xhc3M9XCJ3LTEwMCB3LTYwLW5zIHByMy1ucyBvcmRlci0yIG9yZGVyLTEtbnNcIj5cblx0XHRcdCA8aDEgY2xhc3M9XCJmMyBhdGhlbGFzIG10MCBsaC10aXRsZVwiPiR7ZGVwKCd0aXRsZScpfTwvaDE+XG5cdFx0XHQgPHAgY2xhc3M9XCJmNSBmNC1sIGxoLWNvcHkgYXRoZWxhc1wiPlxuXHRcdFx0XHQke2RlcCgnZXhjZXJwdCcpfVxuXHRcdFx0IDwvcD5cblx0XHQgIDwvZGl2PlxuXHRcdCAgPGRpdiBjbGFzcz1cInBsMy1ucyBvcmRlci0xIG9yZGVyLTItbnMgbWI0IG1iMC1ucyB3LTEwMCB3LTQwLW5zXCI+XG5cdFx0XHQgPGltZyBzcmM9XCJodHRwOi8vbXJtcnMuZ2l0aHViLmlvL3Bob3Rvcy9jcHUuanBnXCIgY2xhc3M9XCJkYlwiIGFsdD1cIlBob3RvIG9mIGEgZGltbHkgbGl0IHJvb20gd2l0aCBhIGNvbXB1dGVyIGludGVyZmFjZSB0ZXJtaW5hbC5cIj5cblx0XHQgIDwvZGl2PlxuXHRcdDwvZGl2PlxuXHRcdDxwIGNsYXNzPVwiZjYgbGgtY29weSBncmF5IG12MFwiPkJ5IDxzcGFuIGNsYXNzPVwidHR1XCI+JHtkZXAoJ2F1dGhvcicpfTwvc3Bhbj48L3A+XG5cdFx0PHRpbWUgY2xhc3M9XCJmNiBkYiBncmF5XCI+JHtkZXAoJ3RpbWVzdGFtcCcpfTwvdGltZT5cblx0IDwvYXJ0aWNsZT5cbiAgPC9zZWN0aW9uPlxuYClcbiIsIlxufSgpKTsiXX0=
166 |
--------------------------------------------------------------------------------
/test/input-source-map/options.json:
--------------------------------------------------------------------------------
1 | {
2 | "debug": true,
3 | "preludePath": "node_modules/browserify/_prelude.js",
4 | "transform": "babelify"
5 | }
6 |
--------------------------------------------------------------------------------
/test/lazy-cycles/a.js:
--------------------------------------------------------------------------------
1 | var b = require('./b')
2 | module.exports = function () {
3 | return b()
4 | }
5 |
--------------------------------------------------------------------------------
/test/lazy-cycles/app.js:
--------------------------------------------------------------------------------
1 | console.log(
2 | require('./a')()
3 | )
4 |
--------------------------------------------------------------------------------
/test/lazy-cycles/b.js:
--------------------------------------------------------------------------------
1 | module.exports = function () {
2 | return require('./a').toString()
3 | }
4 |
--------------------------------------------------------------------------------
/test/lazy-cycles/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var createModuleFactory = function createModuleFactory(t){var e;return function(r){return e||t(e={exports:{},parent:r},e.exports),e.exports}};
3 | var _$a_1 = createModuleFactory(function (module, exports) {
4 | var b = _$b_3({})
5 | module.exports = function () {
6 | return b()
7 | }
8 |
9 | });
10 | var _$b_3 = createModuleFactory(function (module, exports) {
11 | module.exports = function () {
12 | return _$a_1({}).toString()
13 | }
14 |
15 | });
16 | var _$app_2 = {};
17 | console.log(
18 | _$a_1({})()
19 | )
20 |
21 | }());
22 |
--------------------------------------------------------------------------------
/test/lazy-expose/a.js:
--------------------------------------------------------------------------------
1 | var b = require('./b')
2 | module.exports = function () {
3 | return b()
4 | }
5 |
--------------------------------------------------------------------------------
/test/lazy-expose/app.js:
--------------------------------------------------------------------------------
1 | module.exports = require('./a')()
2 |
--------------------------------------------------------------------------------
/test/lazy-expose/b.js:
--------------------------------------------------------------------------------
1 | module.exports = function () {
2 | return require('./a').toString()
3 | }
4 |
--------------------------------------------------------------------------------
/test/lazy-order/a.js:
--------------------------------------------------------------------------------
1 | console.log('always')
2 |
--------------------------------------------------------------------------------
/test/lazy-order/app.js:
--------------------------------------------------------------------------------
1 | require('./a')
2 | global.later = function () {
3 | require('./b') // should not run immediately
4 | }
5 | if (require('./d')>0.5) {
6 | require('./c') // should not always run
7 | }
8 |
--------------------------------------------------------------------------------
/test/lazy-order/b.js:
--------------------------------------------------------------------------------
1 | console.log('later')
2 |
--------------------------------------------------------------------------------
/test/lazy-order/c.js:
--------------------------------------------------------------------------------
1 | console.log('conditionally')
2 |
--------------------------------------------------------------------------------
/test/lazy-order/d.js:
--------------------------------------------------------------------------------
1 | module.exports = Math.random()
2 |
--------------------------------------------------------------------------------
/test/lazy-order/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var createModuleFactory = function createModuleFactory(t){var e;return function(r){return e||t(e={exports:{},parent:r},e.exports),e.exports}};
3 | var _$c_4 = createModuleFactory(function (module, exports) {
4 | console.log('conditionally')
5 |
6 | });
7 | var _$b_3 = createModuleFactory(function (module, exports) {
8 | console.log('later')
9 |
10 | });
11 | var _$a_1 = {};
12 | console.log('always')
13 |
14 | var _$d_5 = Math.random()
15 |
16 | var _$app_2 = {};
17 | (function (global){(function (){
18 | _$a_1
19 | global.later = function () {
20 | _$b_3({}) // should not run immediately
21 | }
22 | if (_$d_5>0.5) {
23 | _$c_4({}) // should not always run
24 | }
25 |
26 | }).call(this)}).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
27 | }());
28 |
--------------------------------------------------------------------------------
/test/module-parent/app.js:
--------------------------------------------------------------------------------
1 | require('./child')
2 |
3 | if (module.parent) {
4 | throw Error('should be entry point')
5 | }
6 |
--------------------------------------------------------------------------------
/test/module-parent/child.js:
--------------------------------------------------------------------------------
1 | if (module.parent) {
2 | module.exports = 'required'
3 | } else {
4 | module.exports = 'entry point'
5 | }
6 |
--------------------------------------------------------------------------------
/test/module-parent/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var _$child_2 = { exports: {} };
3 | if (({})) {
4 | _$child_2.exports = 'required'
5 | } else {
6 | _$child_2.exports = 'entry point'
7 | }
8 |
9 | _$child_2 = _$child_2.exports
10 | var _$app_1 = { exports: {} };
11 | _$child_2
12 |
13 | if (null) {
14 | throw Error('should be entry point')
15 | }
16 |
17 | _$app_1 = _$app_1.exports
18 | }());
19 |
--------------------------------------------------------------------------------
/test/order.js:
--------------------------------------------------------------------------------
1 | var test = require('tape')
2 | var vm = require('vm')
3 | var concat = require('concat-stream')
4 | var pack = require('../')
5 |
6 | test('should evaluate entry modules by their `.order` property', function (t) {
7 | t.plan(1)
8 | var p = pack({ raw: true })
9 |
10 | p.pipe(concat(onbundle))
11 |
12 | p.write({
13 | id: 4, index: 4,
14 | deps: {},
15 | source: 'module.exports="hello"'
16 | })
17 | p.write({
18 | id: 0, index: 0,
19 | entry: true,
20 | order: 1,
21 | deps: {},
22 | source: 'console.log(1)'
23 | })
24 | p.write({
25 | id: 2, index: 2,
26 | entry: true,
27 | order: 2,
28 | deps: {},
29 | source: 'console.log(2)'
30 | })
31 | p.write({
32 | id: 1, index: 3,
33 | entry: true,
34 | order: 0,
35 | deps: { x: 4 },
36 | source: 'console.log(require("x"))'
37 | })
38 | p.end()
39 |
40 | function onbundle (code) {
41 | var result = []
42 | vm.runInNewContext(code, {
43 | console: {
44 | log: function (text) { result.push(text) }
45 | }
46 | })
47 | t.equal(result.join('\n'), 'hello\n1\n2')
48 | }
49 | })
50 |
--------------------------------------------------------------------------------
/test/parent-cycle/app.js:
--------------------------------------------------------------------------------
1 | exports.a = 1
2 | exports.b = 2
3 |
4 | require('./router')
5 |
6 | if (!module.parent) {
7 | console.log(exports.a + exports.b)
8 | }
9 |
--------------------------------------------------------------------------------
/test/parent-cycle/router.js:
--------------------------------------------------------------------------------
1 | if (module.parent) {
2 | require('./app').a = 3
3 | }
4 |
--------------------------------------------------------------------------------
/test/plugin.js:
--------------------------------------------------------------------------------
1 | var test = require('tape')
2 | var through = require('through2')
3 | var fromString = require('from2-string')
4 | var browserify = require('browserify')
5 | var packFlat = require('../plugin')
6 |
7 | test('plugin should replace browser-pack', function (t) {
8 | t.plan(1)
9 |
10 | var input = fromString('module.exports = "whatever"')
11 | var b = browserify(input)
12 | // Add some streams around the browser-pack stream
13 | b.pipeline.get('pack').unshift(through.obj())
14 | b.pipeline.get('pack').push(through.obj())
15 |
16 | b.plugin(packFlat)
17 | b.bundle(onbundle)
18 |
19 | function onbundle (err) {
20 | t.ifError(err)
21 | }
22 | })
23 |
--------------------------------------------------------------------------------
/test/remove-decl/a.js:
--------------------------------------------------------------------------------
1 | module.exports = function test_module_please_ignore () {
2 | }
3 |
--------------------------------------------------------------------------------
/test/remove-decl/app.js:
--------------------------------------------------------------------------------
1 | var a = require('./a')
2 | const __dummy = 'whatever'
3 | var b, c = require('./a')
4 | let d; const e = require('./a')
5 | const f = require('./a'), g = null
6 |
7 | c(a(f))
8 |
--------------------------------------------------------------------------------
/test/remove-decl/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var _$test_module_please_ignore_1 = function test_module_please_ignore () {
3 | }
4 |
5 | var _$app_2 = {};
6 | /* removed: var _$test_module_please_ignore_1 = require('./a') */;
7 | const __dummy = 'whatever'
8 | var b
9 | let d; /* removed: const _$test_module_please_ignore_1 = require('./a') */;
10 | const g = null
11 |
12 | _$test_module_please_ignore_1(_$test_module_please_ignore_1(_$test_module_please_ignore_1))
13 |
14 | }());
15 |
--------------------------------------------------------------------------------
/test/self.js:
--------------------------------------------------------------------------------
1 | var test = require('tape')
2 | var fs = require('fs')
3 | var path = require('path')
4 | var assert = require('assert')
5 | var browserify = require('browserify')
6 | var through = require('through2')
7 | var unpack = require('browser-unpack')
8 |
9 | function unpackStream () {
10 | var d = ''
11 | return through({ objectMode: true }, function (chunk, enc, cb) {
12 | d += chunk
13 | cb()
14 | }, function (cb) {
15 | unpack(d).forEach(this.push, this)
16 | cb(null)
17 | })
18 | }
19 |
20 | function runBundleUnpack (packer) {
21 | var b = browserify({
22 | entries: path.join(__dirname, '../index'),
23 | node: true,
24 | transform: 'brfs'
25 | })
26 |
27 | return b.bundle()
28 | .pipe(unpackStream())
29 | .pipe(packer({ raw: true, standalone: 'packFlat' }))
30 | }
31 |
32 | function runBundlePlugin (packer) {
33 | var b = browserify({
34 | entries: path.join(__dirname, '../plugin'),
35 | node: true,
36 | standalone: 'packFlat',
37 | transform: 'brfs'
38 | })
39 | b.plugin(packer)
40 |
41 | return b.bundle()
42 | }
43 |
44 | test('bundling itself with itself: plugin edition', function (t) {
45 | t.plan(1)
46 | runBundlePlugin(require('../plugin'))
47 | .pipe(fs.createWriteStream(path.join(__dirname, './self.plugin.expected.js')))
48 | .on('finish', onbundle)
49 |
50 | function onbundle () {
51 | runBundlePlugin(require('./self.plugin.expected'))
52 | .pipe(fs.createWriteStream(path.join(__dirname, './self.plugin.actual.js')))
53 | .on('finish', oncompare)
54 | }
55 |
56 | function oncompare () {
57 | t.is(
58 | fs.readFileSync(path.join(__dirname, './self.plugin.expected.js'), 'utf8'),
59 | fs.readFileSync(path.join(__dirname, './self.plugin.actual.js'), 'utf8'),
60 | 'flattened browserified code should have the same output as the commonjs version'
61 | )
62 | t.end()
63 | }
64 | })
65 |
66 | test('bundling itself with itself: repack edition', function (t) {
67 | t.plan(1)
68 | runBundleUnpack(require('../index'))
69 | .pipe(fs.createWriteStream(path.join(__dirname, './self.unpack.expected.js')))
70 | .on('finish', onbundle)
71 |
72 | function onbundle () {
73 | runBundleUnpack(require('./self.unpack.expected'))
74 | .pipe(fs.createWriteStream(path.join(__dirname, './self.unpack.actual.js')))
75 | .on('finish', oncompare)
76 | }
77 |
78 | function oncompare () {
79 | t.is(
80 | fs.readFileSync(path.join(__dirname, './self.unpack.expected.js'), 'utf8'),
81 | fs.readFileSync(path.join(__dirname, './self.unpack.actual.js'), 'utf8'),
82 | 'flattened browserified code should have the same output as the commonjs version'
83 | )
84 | t.end()
85 | }
86 | })
87 |
--------------------------------------------------------------------------------
/test/set-exports/app.js:
--------------------------------------------------------------------------------
1 | exports.moduleExports = require('./module-exports')
2 | exports.both = require('./both')
3 | exports.exportsOnly = require('./exports-only')
4 | exports.quoted = require('./quoted')
5 | exports.free = require('./free-module')
6 |
--------------------------------------------------------------------------------
/test/set-exports/both.js:
--------------------------------------------------------------------------------
1 | module.exports = exports = 2
2 |
--------------------------------------------------------------------------------
/test/set-exports/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var _$moduleExports_5 = 1
3 |
4 | var _$both_2 = {};
5 | _$both_2 = _$both_2 = 2
6 |
7 | var _$exportsOnly_3 = {};
8 | _$exportsOnly_3 = 3
9 |
10 | var _$quoted_6 = 4
11 |
12 | var _$freeModule_4 = { exports: {} };
13 | var something = function () {
14 | return _$freeModule_4
15 | }
16 | something().exports = 5
17 |
18 | _$freeModule_4 = _$freeModule_4.exports
19 | var _$app_1 = {};
20 | _$app_1.moduleExports = _$moduleExports_5
21 | _$app_1.both = _$both_2
22 | _$app_1.exportsOnly = _$exportsOnly_3
23 | _$app_1.quoted = _$quoted_6
24 | _$app_1.free = _$freeModule_4
25 |
26 | }());
27 |
--------------------------------------------------------------------------------
/test/set-exports/exports-only.js:
--------------------------------------------------------------------------------
1 | exports = 3
2 |
--------------------------------------------------------------------------------
/test/set-exports/free-module.js:
--------------------------------------------------------------------------------
1 | var something = function () {
2 | return module
3 | }
4 | something().exports = 5
5 |
--------------------------------------------------------------------------------
/test/set-exports/module-exports.js:
--------------------------------------------------------------------------------
1 | module.exports = 1
2 |
--------------------------------------------------------------------------------
/test/set-exports/quoted.js:
--------------------------------------------------------------------------------
1 | module["exports"] = 4
2 |
--------------------------------------------------------------------------------
/test/shorthand/app.js:
--------------------------------------------------------------------------------
1 | var globalVar = 0
2 | var importedModule = require('./importedModule')
3 |
4 | function setExports (argument) {
5 | var localVar = 1
6 | module.exports = {
7 | globalVar,
8 | importedModule,
9 | localVar,
10 | argument
11 | }
12 | }
13 |
14 | setExports(10)
15 |
--------------------------------------------------------------------------------
/test/shorthand/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var globalVar = 1
3 |
4 | var _$globalVar_2 = globalVar
5 |
6 | var _$app_1 = {};
7 | var __globalVar_1 = 0
8 | /* removed: var _$globalVar_2 = require('./importedModule') */;
9 |
10 | function setExports (argument) {
11 | var localVar = 1
12 | _$app_1 = {
13 | globalVar: __globalVar_1,
14 | importedModule: _$globalVar_2,
15 | localVar,
16 | argument
17 | }
18 | }
19 |
20 | setExports(10)
21 |
22 | }());
23 |
--------------------------------------------------------------------------------
/test/shorthand/importedModule.js:
--------------------------------------------------------------------------------
1 | var globalVar = 1
2 |
3 | module.exports = globalVar
4 |
--------------------------------------------------------------------------------
/test/simplify/app.js:
--------------------------------------------------------------------------------
1 | var hello = require('./hello')
2 | var world = require('./world' /* comment */)
3 |
4 | require('./asi'), console.log(hello, world)
5 |
--------------------------------------------------------------------------------
/test/simplify/asi.js:
--------------------------------------------------------------------------------
1 | // If the `test` import is removed naively, the result will be alert(test), which is incorrect.
2 | alert
3 | var test = require('./hello');
4 | (test)
5 |
--------------------------------------------------------------------------------
/test/simplify/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var _$hello_3 = 'hello'
3 |
4 | var _$world_4 = {};
5 | var world = _$world_4 = 'world'
6 |
7 | var _$asi_2 = {};
8 | // If the `test` import is removed naively, the result will be alert(test), which is incorrect.
9 | alert
10 | /* removed: var _$hello_3 = require('./hello'); */;
11 | (_$hello_3)
12 |
13 | var _$app_1 = {};
14 | /* removed: var _$hello_3 = require('./hello') */;
15 | /* removed: var _$world_4 = require('./world' /* comment *\/) */;
16 |
17 | _$asi_2, console.log(_$hello_3, _$world_4)
18 |
19 | }());
20 |
--------------------------------------------------------------------------------
/test/simplify/hello.js:
--------------------------------------------------------------------------------
1 | module.exports = 'hello'
2 |
--------------------------------------------------------------------------------
/test/simplify/world.js:
--------------------------------------------------------------------------------
1 | var world = module.exports = 'world'
2 |
--------------------------------------------------------------------------------
/test/source-map/app.js:
--------------------------------------------------------------------------------
1 | module.exports = require('./b')
2 |
--------------------------------------------------------------------------------
/test/source-map/b.js:
--------------------------------------------------------------------------------
1 | module.exports = 10
2 |
--------------------------------------------------------------------------------
/test/source-map/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var _$b_2 = 10
3 |
4 | var _$app_1 = _$b_2
5 |
6 | }());
7 | //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIl9wcmVsdWRlIiwidGVzdC9zb3VyY2UtbWFwL2IuanMiLCJ0ZXN0L3NvdXJjZS1tYXAvYXBwLmpzIiwiX3Bvc3RsdWRlIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBO0FBQ0EsQUNEQSxTQUFjLEdBQUcsRUFBRTs7QUNBbkIsV0FBYyxHQUFHLEtBQWM7QUNBL0I7QUFDQSIsImZpbGUiOiJnZW5lcmF0ZWQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlc0NvbnRlbnQiOlsiKGZ1bmN0aW9uKCl7XG4iLCJtb2R1bGUuZXhwb3J0cyA9IDEwXG4iLCJtb2R1bGUuZXhwb3J0cyA9IHJlcXVpcmUoJy4vYicpXG4iLCJcbn0oKSk7Il19
8 |
--------------------------------------------------------------------------------
/test/source-map/options.json:
--------------------------------------------------------------------------------
1 | {
2 | "debug": true,
3 | "preludePath": "node_modules/browserify/_prelude.js"
4 | }
5 |
--------------------------------------------------------------------------------
/test/standalone/a.js:
--------------------------------------------------------------------------------
1 | module.exports = function a() {
2 | return 'A'
3 | }
4 |
--------------------------------------------------------------------------------
/test/standalone/app.js:
--------------------------------------------------------------------------------
1 | exports.a = require('./a')
2 | exports.b = require('./b')
3 |
--------------------------------------------------------------------------------
/test/standalone/b.js:
--------------------------------------------------------------------------------
1 | module.exports = function b() {
2 | return 'B'
3 | }
4 |
--------------------------------------------------------------------------------
/test/standalone/expected.js:
--------------------------------------------------------------------------------
1 | (function(f){if(typeof exports==="object"&&typeof module!=="undefined"){module.exports=f()}else if(typeof define==="function"&&define.amd){define([],f)}else{var g;if(typeof window!=="undefined"){g=window}else if(typeof global!=="undefined"){g=global}else if(typeof self!=="undefined"){g=self}else{g=this}g.modulename = f()}})(function(){var define,module,exports;
2 | var _$a_1 = function a() {
3 | return 'A'
4 | }
5 |
6 | var _$b_3 = function b() {
7 | return 'B'
8 | }
9 |
10 | var _$app_2 = {};
11 | _$app_2.a = _$a_1
12 | _$app_2.b = _$b_3
13 |
14 | return _$app_2;
15 |
16 | });
17 |
18 |
--------------------------------------------------------------------------------
/test/standalone/options.json:
--------------------------------------------------------------------------------
1 | { "standalone": "modulename" }
2 |
--------------------------------------------------------------------------------
/test/test.js:
--------------------------------------------------------------------------------
1 | var test = require('tape')
2 | var vm = require('vm')
3 | var fs = require('fs')
4 | var path = require('path')
5 | var browserify = require('browserify')
6 | var concat = require('concat-stream')
7 | var pack = require('../plugin')
8 |
9 | var tests = [
10 | 'bare-module',
11 | 'colliding-unused',
12 | 'comment',
13 | 'dedupe',
14 | 'dep-order',
15 | 'destructure',
16 | 'dynamic-require',
17 | 'eager-cycles',
18 | 'exports-name',
19 | 'globals',
20 | 'input-source-map',
21 | 'lazy-cycles',
22 | 'lazy-order',
23 | 'module-parent',
24 | 'remove-decl',
25 | 'set-exports',
26 | 'shorthand',
27 | 'simplify',
28 | 'source-map',
29 | 'standalone',
30 | 'typeof-require',
31 | 'variable'
32 | ]
33 |
34 | tests.forEach(function (name) {
35 | test(name, { skip: /^v4/.test(process.version) && name === 'input-source-map' }, function (t) {
36 | runTest(t, name)
37 | })
38 | })
39 |
40 | function runTest (t, name) {
41 | t.plan(1)
42 | var basedir = path.join(__dirname, name)
43 | var optionsPath = path.join(basedir, 'options.json')
44 | var options = {}
45 | try { options = JSON.parse(fs.readFileSync(optionsPath, 'utf8')) } catch (err) {}
46 | var entry = path.join(basedir, 'app.js')
47 | var expected = path.join(basedir, 'expected.js')
48 | var actual = path.join(basedir, 'actual.js')
49 | options.entries = entry
50 | var bundle = browserify(options)
51 | .plugin(pack)
52 | .bundle()
53 | .on('error', t.fail)
54 |
55 | // Write actual output to a file for easier inspection
56 | bundle.pipe(fs.createWriteStream(actual))
57 |
58 | bundle.pipe(concat(function (result) {
59 | t.is(
60 | result.toString('utf8'),
61 | fs.readFileSync(expected, 'utf8'),
62 | name
63 | )
64 | t.end()
65 | }))
66 | }
67 |
68 | test('parent-cycle', function (t) {
69 | t.plan(2)
70 |
71 | var basedir = path.join(__dirname, 'parent-cycle')
72 | var entry = path.join(basedir, 'app.js')
73 | var actual = path.join(basedir, 'actual.js')
74 |
75 | browserify(entry)
76 | .plugin(pack)
77 | .bundle(function (err, result) {
78 | t.ifError(err)
79 | fs.writeFileSync(actual, result)
80 | vm.runInNewContext(result + '', {
81 | console: { log: log }
82 | })
83 | function log (value) {
84 | t.equal(value, 5)
85 | }
86 | })
87 | })
88 |
--------------------------------------------------------------------------------
/test/typeof-require/app.js:
--------------------------------------------------------------------------------
1 | if (typeof require === 'function' && typeof exports === 'object' && typeof module === 'object') {
2 | console.log('should do this')
3 | module.exports = factory()
4 | } else {
5 | console.log('should not do this')
6 | this.Standalone = factory()
7 | }
8 |
9 | function factory () {
10 | return { value: 10 }
11 | }
12 |
--------------------------------------------------------------------------------
/test/typeof-require/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var _$app_1 = { exports: {} };
3 | if ("function" === 'function' && typeof _$app_1.exports === 'object' && "object" === 'object') {
4 | console.log('should do this')
5 | _$app_1.exports = factory()
6 | } else {
7 | console.log('should not do this')
8 | this.Standalone = factory()
9 | }
10 |
11 | function factory () {
12 | return { value: 10 }
13 | }
14 |
15 | _$app_1 = _$app_1.exports
16 | }());
17 |
--------------------------------------------------------------------------------
/test/variable/app.js:
--------------------------------------------------------------------------------
1 | exports.param = require('./param')
2 | exports.something = function () {
3 | var exports = {}
4 | exports.something = require('./param')
5 | return exports
6 | }
7 |
--------------------------------------------------------------------------------
/test/variable/expected.js:
--------------------------------------------------------------------------------
1 | (function(){
2 | var _$param_2 = function (module) {
3 | return { exports: module }
4 | }
5 |
6 | var _$app_1 = {};
7 | _$app_1.param = _$param_2
8 | _$app_1.something = function () {
9 | var exports = {}
10 | exports.something = _$param_2
11 | return exports
12 | }
13 |
14 | }());
15 |
--------------------------------------------------------------------------------
/test/variable/param.js:
--------------------------------------------------------------------------------
1 | module.exports = function (module) {
2 | return { exports: module }
3 | }
4 |
--------------------------------------------------------------------------------