| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -1,3 +1,10 @@ | |||
| 1 | + 1.0.0 | ||
| 2 | + - Unsafe getter tracking (https://github.com/guybedford/cjs-module-lexer/pull/29) | ||
| 3 | + | ||
| 4 | + 0.6.0 | ||
| 5 | + - API-only breaking change: Unify JS and Wasm interfaces (https://github.com/guybedford/cjs-module-lexer/pull/27) | ||
| 6 | + - Add type definitions (https://github.com/guybedford/cjs-module-lexer/pull/28) | ||
| 7 | + | ||
| 1 | 8 | 0.5.2 | |
| 2 | 9 | - Support named getter functions (https://github.com/guybedford/cjs-module-lexer/pull/26) | |
| 3 | 10 | ||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -19,7 +19,9 @@ npm install cjs-module-lexer | |||
| 19 | 19 | For use in CommonJS: | |
| 20 | 20 | ||
| 21 | 21 | ```js | |
| 22 | - const parse = require('cjs-module-lexer'); | ||
| 22 | + const { parse } = require('cjs-module-lexer'); | ||
| 23 | + | ||
| 24 | + // `init` return a promise for parity with the ESM API, but you do not have to call it | ||
| 23 | 25 | ||
| 24 | 26 | const { exports, reexports } = parse(` | |
| 25 | 27 | // named exports detection | |
@@ -84,7 +86,9 @@ EXPORTS_SPREAD: `...` (IDENTIFIER | REQUIRE) | |||
| 84 | 86 | ||
| 85 | 87 | EXPORTS_MEMBER: EXPORTS_DOT_ASSIGN | EXPORTS_LITERAL_COMPUTED_ASSIGN | |
| 86 | 88 | ||
| 87 | - EXPORTS_DEFINE: `Object` `.` `defineProperty `(` IDENTIFIER_STRING `, {` | ||
| 89 | + EXPORTS_DEFINE: `Object` `.` `defineProperty `(` EXPORTS_IDENFITIER `,` IDENTIFIER_STRING | ||
| 90 | + | ||
| 91 | + EXPORTS_DEFINE_VALUE: EXPORTS_DEFINE `, {` | ||
| 88 | 92 | (`enumerable: true,`)? | |
| 89 | 93 | ( | |
| 90 | 94 | `value:` | | |
@@ -119,7 +123,9 @@ EXPORT_STAR_LIB: `Object.keys(` IDENTIFIER$1 `).forEach(function (` IDENTIFIER$2 | |||
| 119 | 123 | ||
| 120 | 124 | Spacing between tokens is taken to be any ECMA-262 whitespace, ECMA-262 block comment or ECMA-262 line comment. | |
| 121 | 125 | ||
| 122 | - * The returned export names are taken to be the combination of the `IDENTIFIER` and `IDENTIFIER_STRING` slots for all `EXPORTS_MEMBER`, `EXPORTS_LITERAL` and `EXPORTS_DEFINE` matches. | ||
| 126 | + * The returned export names are taken to be the combination of: | ||
| 127 | + 1. All `IDENTIFIER` and `IDENTIFIER_STRING` slots for `EXPORTS_MEMBER` and `EXPORTS_LITERAL` matches. | ||
| 128 | + 2. The first `IDENTIFIER_STRING` slot for all `EXPORTS_DEFINE_VALUE` matches where that same string is not an `EXPORTS_DEFINE` match that is not also an `EXPORTS_DEFINE_VALUE` match. | ||
| 123 | 129 | * The reexport specifiers are taken to be the the combination of: | |
| 124 | 130 | 1. The `REQUIRE` matches of the last matched of either `MODULE_EXPORTS_ASSIGN` or `EXPORTS_LITERAL`. | |
| 125 | 131 | 2. All _top-level_ `EXPORT_STAR` `REQUIRE` matches and `EXPORTS_ASSIGN` matches whose `IDENTIFIER` also matches the first `IDENTIFIER` in `EXPORT_STAR_LIB`. | |
@@ -160,6 +166,8 @@ It will in turn underclassify in cases where the identifiers are renamed: | |||
| 160 | 166 | })(exports); | |
| 161 | 167 | ``` | |
| 162 | 168 | ||
| 169 | + #### Getter Exports Parsing | ||
| 170 | + | ||
| 163 | 171 | `Object.defineProperty` is detected for specifically value and getter forms returning an identifier or member expression: | |
| 164 | 172 | ||
| 165 | 173 | ```js | |
@@ -186,6 +194,24 @@ Object.defineProperty(exports, 'd', { value: 'd' }); | |||
| 186 | 194 | Object.defineProperty(exports, '__esModule', { value: true }); | |
| 187 | 195 | ``` | |
| 188 | 196 | ||
| 197 | + To avoid matching getters that have side effects, any getter for an export name that does not support the forms above will | ||
| 198 | + opt-out of the getter matching: | ||
| 199 | + | ||
| 200 | + ```js | ||
| 201 | + // DETECTS: NO EXPORTS | ||
| 202 | + Object.defineProperty(exports, 'a', { | ||
| 203 | + value: 'no problem' | ||
| 204 | + }); | ||
| 205 | + | ||
| 206 | + if (false) { | ||
| 207 | + Object.defineProperty(module.exports, 'a', { | ||
| 208 | + get () { | ||
| 209 | + return dynamic(); | ||
| 210 | + } | ||
| 211 | + }) | ||
| 212 | + } | ||
| 213 | + ``` | ||
| 214 | + | ||
| 189 | 215 | Alternative object definition structures or getter function bodies are not detected: | |
| 190 | 216 | ||
| 191 | 217 | ```js | |
@@ -335,63 +361,63 @@ JS Build: | |||
| 335 | 361 | ||
| 336 | 362 | ``` | |
| 337 | 363 | Module load time | |
| 338 | - > 5ms | ||
| 364 | + > 4ms | ||
| 339 | 365 | Cold Run, All Samples | |
| 340 | 366 | test/samples/*.js (3635 KiB) | |
| 341 | - > 323ms | ||
| 367 | + > 299ms | ||
| 342 | 368 | ||
| 343 | 369 | Warm Runs (average of 25 runs) | |
| 344 | 370 | test/samples/angular.js (1410 KiB) | |
| 345 | - > 14.84ms | ||
| 371 | + > 13.96ms | ||
| 346 | 372 | test/samples/angular.min.js (303 KiB) | |
| 347 | - > 4.8ms | ||
| 373 | + > 4.72ms | ||
| 348 | 374 | test/samples/d3.js (553 KiB) | |
| 349 | - > 7.84ms | ||
| 375 | + > 6.76ms | ||
| 350 | 376 | test/samples/d3.min.js (250 KiB) | |
| 351 | 377 | > 4ms | |
| 352 | 378 | test/samples/magic-string.js (34 KiB) | |
| 353 | - > 0.72ms | ||
| 379 | + > 0.64ms | ||
| 354 | 380 | test/samples/magic-string.min.js (20 KiB) | |
| 355 | - > 0.4ms | ||
| 381 | + > 0ms | ||
| 356 | 382 | test/samples/rollup.js (698 KiB) | |
| 357 | - > 9.32ms | ||
| 383 | + > 8.48ms | ||
| 358 | 384 | test/samples/rollup.min.js (367 KiB) | |
| 359 | - > 6.52ms | ||
| 385 | + > 5.36ms | ||
| 360 | 386 | ||
| 361 | 387 | Warm Runs, All Samples (average of 25 runs) | |
| 362 | 388 | test/samples/*.js (3635 KiB) | |
| 363 | - > 44ms | ||
| 389 | + > 40.28ms | ||
| 364 | 390 | ``` | |
| 365 | 391 | ||
| 366 | 392 | Wasm Build: | |
| 367 | 393 | ``` | |
| 368 | 394 | Module load time | |
| 369 | - > 11ms | ||
| 395 | + > 10ms | ||
| 370 | 396 | Cold Run, All Samples | |
| 371 | 397 | test/samples/*.js (3635 KiB) | |
| 372 | - > 42ms | ||
| 398 | + > 43ms | ||
| 373 | 399 | ||
| 374 | 400 | Warm Runs (average of 25 runs) | |
| 375 | 401 | test/samples/angular.js (1410 KiB) | |
| 376 | - > 9.92ms | ||
| 402 | + > 9.32ms | ||
| 377 | 403 | test/samples/angular.min.js (303 KiB) | |
| 378 | - > 3.2ms | ||
| 404 | + > 3.16ms | ||
| 379 | 405 | test/samples/d3.js (553 KiB) | |
| 380 | - > 5.2ms | ||
| 406 | + > 5ms | ||
| 381 | 407 | test/samples/d3.min.js (250 KiB) | |
| 382 | - > 2.52ms | ||
| 408 | + > 2.32ms | ||
| 383 | 409 | test/samples/magic-string.js (34 KiB) | |
| 384 | 410 | > 0.16ms | |
| 385 | 411 | test/samples/magic-string.min.js (20 KiB) | |
| 386 | - > 0.04ms | ||
| 412 | + > 0ms | ||
| 387 | 413 | test/samples/rollup.js (698 KiB) | |
| 388 | - > 6.44ms | ||
| 414 | + > 6.28ms | ||
| 389 | 415 | test/samples/rollup.min.js (367 KiB) | |
| 390 | - > 3.96ms | ||
| 416 | + > 3.6ms | ||
| 391 | 417 | ||
| 392 | 418 | Warm Runs, All Samples (average of 25 runs) | |
| 393 | 419 | test/samples/*.js (3635 KiB) | |
| 394 | - > 30.48ms | ||
| 420 | + > 27.76ms | ||
| 395 | 421 | ``` | |
| 396 | 422 | ||
| 397 | 423 | ### Wasm Build Steps | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -11,6 +11,7 @@ let openTokenDepth, | |||
| 11 | 11 | starExportMap, | |
| 12 | 12 | lastStarExportSpecifier, | |
| 13 | 13 | _exports, | |
| 14 | + unsafeGetters, | ||
| 14 | 15 | reexports; | |
| 15 | 16 | ||
| 16 | 17 | function resetState () { | |
@@ -27,6 +28,7 @@ function resetState () { | |||
| 27 | 28 | lastStarExportSpecifier = null; | |
| 28 | 29 | ||
| 29 | 30 | _exports = new Set(); | |
| 31 | + unsafeGetters = new Set(); | ||
| 30 | 32 | reexports = new Set(); | |
| 31 | 33 | } | |
| 32 | 34 | ||
@@ -37,7 +39,7 @@ const ExportStar = 2; | |||
| 37 | 39 | ||
| 38 | 40 | const strictReserved = new Set(['implements', 'interface', 'let', 'package', 'private', 'protected', 'public', 'static', 'yield', 'enum']); | |
| 39 | 41 | ||
| 40 | - module.exports = function parseCJS (source, name = '@') { | ||
| 42 | + function parseCJS (source, name = '@') { | ||
| 41 | 43 | resetState(); | |
| 42 | 44 | try { | |
| 43 | 45 | parseSource(source); | |
@@ -47,7 +49,7 @@ module.exports = function parseCJS (source, name = '@') { | |||
| 47 | 49 | e.loc = pos; | |
| 48 | 50 | throw e; | |
| 49 | 51 | } | |
| 50 | - const result = { exports: [..._exports], reexports: [...reexports] }; | ||
| 52 | + const result = { exports: [..._exports].filter(expt => !unsafeGetters.has(expt)), reexports: [...reexports] }; | ||
| 51 | 53 | resetState(); | |
| 52 | 54 | return result; | |
| 53 | 55 | } | |
@@ -260,6 +262,7 @@ function tryParseObjectDefineOrKeys (keys) { | |||
| 260 | 262 | pos++; | |
| 261 | 263 | ch = commentWhitespace(); | |
| 262 | 264 | if (ch === 100/*d*/ && source.startsWith('efineProperty', pos + 1)) { | |
| 265 | + let expt; | ||
| 263 | 266 | while (true) { | |
| 264 | 267 | pos += 14; | |
| 265 | 268 | revertPos = pos - 1; | |
@@ -276,7 +279,7 @@ function tryParseObjectDefineOrKeys (keys) { | |||
| 276 | 279 | let quot = ch; | |
| 277 | 280 | const exportPos = ++pos; | |
| 278 | 281 | if (!identifier() || source.charCodeAt(pos) !== quot) break; | |
| 279 | - const expt = source.slice(exportPos, pos); | ||
| 282 | + expt = source.slice(exportPos, pos); | ||
| 280 | 283 | pos++; | |
| 281 | 284 | ch = commentWhitespace(); | |
| 282 | 285 | if (ch !== 44/*,*/) break; | |
@@ -304,9 +307,9 @@ function tryParseObjectDefineOrKeys (keys) { | |||
| 304 | 307 | pos += 5; | |
| 305 | 308 | ch = commentWhitespace(); | |
| 306 | 309 | if (ch !== 58/*:*/) break; | |
| 307 | - pos++; | ||
| 308 | 310 | addExport(expt); | |
| 309 | - break; | ||
| 311 | + pos = revertPos; | ||
| 312 | + return; | ||
| 310 | 313 | } | |
| 311 | 314 | else if (ch === 103/*g*/) { | |
| 312 | 315 | if (!source.startsWith('et', pos + 1)) break; | |
@@ -372,6 +375,9 @@ function tryParseObjectDefineOrKeys (keys) { | |||
| 372 | 375 | } | |
| 373 | 376 | break; | |
| 374 | 377 | } | |
| 378 | + if (expt) { | ||
| 379 | + unsafeGetters.add(expt); | ||
| 380 | + } | ||
| 375 | 381 | } | |
| 376 | 382 | else if (keys && ch === 107/*k*/ && source.startsWith('eys', pos + 1)) { | |
| 377 | 383 | while (true) { | |
@@ -899,7 +905,7 @@ function tryParseLiteralExports () { | |||
| 899 | 905 | ||
| 900 | 906 | // --- Extracted from AcornJS --- | |
| 901 | 907 | //(https://github.com/acornjs/acorn/blob/master/acorn/src/identifier.js#L23 | |
| 902 | - // | ||
| 908 | + // | ||
| 903 | 909 | // MIT License | |
| 904 | 910 | ||
| 905 | 911 | // Copyright (C) 2012-2018 by various contributors (see AUTHORS) | |
@@ -1034,7 +1040,7 @@ function throwIfImportStatement () { | |||
| 1034 | 1040 | case 46/*.*/: | |
| 1035 | 1041 | throw new Error('Unexpected import.meta in CJS module.'); | |
| 1036 | 1042 | return; | |
| 1037 | - | ||
| 1043 | + | ||
| 1038 | 1044 | default: | |
| 1039 | 1045 | // no space after "import" -> not an import keyword | |
| 1040 | 1046 | if (pos === startPos + 6) | |
@@ -1203,7 +1209,7 @@ function readPrecedingKeyword (pos, match) { | |||
| 1203 | 1209 | } | |
| 1204 | 1210 | ||
| 1205 | 1211 | function readPrecedingKeyword1 (pos, ch) { | |
| 1206 | - return source.charCodeAt(pos) === ch && (pos === 0 || isBrOrWsOrPunctuatorNotDot(source.charCodeAt(pos - 1))); | ||
| 1212 | + return source.charCodeAt(pos) === ch && (pos === 0 || isBrOrWsOrPunctuatorNotDot(source.charCodeAt(pos - 1))); | ||
| 1207 | 1213 | } | |
| 1208 | 1214 | ||
| 1209 | 1215 | // Detects one of case, debugger, delete, do, else, in, instanceof, new, | |
@@ -1274,7 +1280,7 @@ function isExpressionKeyword (pos) { | |||
| 1274 | 1280 | // throw | |
| 1275 | 1281 | return readPrecedingKeyword(pos - 2, 'thr'); | |
| 1276 | 1282 | default: | |
| 1277 | - return false; | ||
| 1283 | + return false; | ||
| 1278 | 1284 | } | |
| 1279 | 1285 | } | |
| 1280 | 1286 | return false; | |
@@ -1320,3 +1326,8 @@ function isExpressionTerminator (curPos) { | |||
| 1320 | 1326 | } | |
| 1321 | 1327 | return false; | |
| 1322 | 1328 | } | |
| 1329 | + | ||
| 1330 | + const initPromise = Promise.resolve(); | ||
| 1331 | + | ||
| 1332 | + module.exports.init = () => initPromise; | ||
| 1333 | + module.exports.parse = parseCJS; | ||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -1,12 +1,13 @@ | |||
| 1 | 1 | { | |
| 2 | 2 | "name": "cjs-module-lexer", | |
| 3 | - "version": "0.5.2", | ||
| 3 | + "version": "1.0.0", | ||
| 4 | 4 | "description": "Lexes CommonJS modules, returning their named exports metadata", | |
| 5 | 5 | "main": "lexer.js", | |
| 6 | 6 | "exports": { | |
| 7 | 7 | "import": "./dist/lexer.mjs", | |
| 8 | 8 | "default": "./lexer.js" | |
| 9 | 9 | }, | |
| 10 | + "types": "lexer.d.ts", | ||
| 10 | 11 | "scripts": { | |
| 11 | 12 | "test-js": "mocha -b -u tdd test/*.js", | |
| 12 | 13 | "test-wasm": "WASM=1 mocha -b -u tdd test/*.js", | |
@@ -28,7 +29,8 @@ | |||
| 28 | 29 | "terser": "^4.1.4" | |
| 29 | 30 | }, | |
| 30 | 31 | "files": [ | |
| 31 | - "dist" | ||
| 32 | + "dist", | ||
| 33 | + "lexer.d.ts" | ||
| 32 | 34 | ], | |
| 33 | 35 | "repository": { | |
| 34 | 36 | "type": "git", | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -1296,7 +1296,7 @@ success! | |||
| 1296 | 1296 | [`Uint8Array`]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Uint8Array | |
| 1297 | 1297 | [dynamic instantiate hook]: #esm_code_dynamicinstantiate_code_hook | |
| 1298 | 1298 | [`util.TextDecoder`]: util.md#util_class_util_textdecoder | |
| 1299 | - [cjs-module-lexer]: https://github.com/guybedford/cjs-module-lexer/tree/0.5.2 | ||
| 1299 | + [cjs-module-lexer]: https://github.com/guybedford/cjs-module-lexer/tree/1.0.0 | ||
| 1300 | 1300 | [special scheme]: https://url.spec.whatwg.org/#special-scheme | |
| 1301 | 1301 | [the official standard format]: https://tc39.github.io/ecma262/#sec-modules | |
| 1302 | 1302 | [transpiler loader example]: #esm_transpiler_loader | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -60,7 +60,7 @@ const asyncESM = require('internal/process/esm_loader'); | |||
| 60 | 60 | let cjsParse; | |
| 61 | 61 | async function initCJSParse() { | |
| 62 | 62 | if (typeof WebAssembly === 'undefined') { | |
| 63 | - cjsParse = require('internal/deps/cjs-module-lexer/lexer'); | ||
| 63 | + cjsParse = require('internal/deps/cjs-module-lexer/lexer').parse; | ||
| 64 | 64 | } else { | |
| 65 | 65 | const { parse, init } = | |
| 66 | 66 | require('internal/deps/cjs-module-lexer/dist/lexer'); | |
| Back | FazBrowse Home | New Git URL |
0 commit comments