@jsenv/core 23.8.6 → 23.8.12

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@jsenv/core",
3
- "version": "23.8.6",
3
+ "version": "23.8.12",
4
4
  "description": "Tool to develop, test and build js projects",
5
5
  "license": "MIT",
6
6
  "repository": {
@@ -67,12 +67,11 @@
67
67
  "@c88/v8-coverage": "0.1.1",
68
68
  "@jsenv/abort": "4.1.1",
69
69
  "@jsenv/filesystem": "2.5.1",
70
- "@jsenv/importmap": "1.1.0",
70
+ "@jsenv/importmap": "1.2.0",
71
71
  "@jsenv/log": "1.4.0",
72
72
  "@jsenv/logger": "4.0.1",
73
73
  "@jsenv/server": "10.0.11",
74
74
  "@jsenv/uneval": "1.6.0",
75
- "@jsenv/workers": "1.2.0",
76
75
  "@rollup/plugin-commonjs": "21.0.0",
77
76
  "@rollup/plugin-json": "4.1.0",
78
77
  "@rollup/plugin-node-resolve": "13.0.5",
@@ -121,11 +120,11 @@
121
120
  "@babel/preset-env": "7.15.8",
122
121
  "@jsenv/assert": "2.3.2",
123
122
  "@jsenv/babel-preset": "./packages/jsenv-babel-preset",
124
- "@jsenv/eslint-config": "16.0.8",
123
+ "@jsenv/eslint-config": "16.0.9",
125
124
  "@jsenv/github-release-package": "1.2.3",
126
- "@jsenv/https-local": "1.0.2",
125
+ "@jsenv/https-local": "1.0.3",
127
126
  "@jsenv/importmap-eslint-resolver": "5.1.2",
128
- "@jsenv/importmap-node-module": "2.4.1",
127
+ "@jsenv/importmap-node-module": "2.7.0",
129
128
  "@jsenv/package-publish": "1.6.2",
130
129
  "@jsenv/performance-impact": "2.2.1",
131
130
  "@jsenv/prettier-check-project": "5.6.1",
@@ -34,7 +34,7 @@ export const buildProject = async ({
34
34
  systemJsUrl,
35
35
  globalName,
36
36
  globals = {},
37
- babelPluginMap,
37
+ babelPluginMap = {},
38
38
  customCompilers,
39
39
  runtimeSupport = format === "global" ||
40
40
  format === "systemjs" ||
@@ -70,7 +70,7 @@ export const buildProject = async ({
70
70
 
71
71
  minify = process.env.NODE_ENV === "production",
72
72
  // https://github.com/kangax/html-minifier#options-quick-reference
73
- minifyHtmlOptions = { collapseWhitespace: true },
73
+ minifyHtmlOptions = { collapseWhitespace: true, removeComments: true },
74
74
  // https://github.com/terser/terser#minify-options
75
75
  minifyJsOptions,
76
76
  // https://github.com/cssnano/cssnano/tree/master/packages/cssnano-preset-default
@@ -1,3 +1,5 @@
1
+ /* eslint-env browser */
2
+
1
3
  export const displayErrorInDocument = (error) => {
2
4
  const title = "An error occured"
3
5
  let theme
@@ -1,3 +1,4 @@
1
+ /* eslint-env browser */
1
2
  const { Notification } = window
2
3
 
3
4
  const displayErrorNotificationNotAvailable = () => {}
@@ -186,6 +186,14 @@ const executeSource = async ({
186
186
  coverage,
187
187
  }
188
188
  })
189
+ } else {
190
+ transformResult = composeTransformer(transformResult, (result) => {
191
+ const { namespace: fileExecutionResultMap } = result
192
+ Object.keys(fileExecutionResultMap).forEach((fileRelativeUrl) => {
193
+ delete fileExecutionResultMap[fileRelativeUrl].coverage
194
+ })
195
+ return result
196
+ })
189
197
  }
190
198
 
191
199
  const fileClientUrl = resolveUrl(fileRelativeUrl, `${compileServerOrigin}/`)
@@ -7,6 +7,9 @@ import { fetchUrl } from "../browser-utils/fetch-browser.js"
7
7
  import { fetchAndEvalUsingFetch } from "../browser-utils/fetchAndEvalUsingFetch.js"
8
8
  import { memoize } from "../memoize.js"
9
9
 
10
+ import { displayErrorInDocument } from "./displayErrorInDocument.js"
11
+ import { displayErrorNotification } from "./displayErrorNotification.js"
12
+
10
13
  const getNavigationStartTime = () => {
11
14
  try {
12
15
  return window.performance.timing.navigationStart
@@ -73,13 +76,15 @@ const executeFileUsingDynamicImport = async (
73
76
  const executionResult = {
74
77
  status: "completed",
75
78
  namespace,
79
+ coverage: readCoverage(),
76
80
  }
77
81
  return executionResult
78
82
  } catch (e) {
79
83
  performance.measure(`jsenv_file_import`, `jsenv_file_import_start`)
80
84
  const executionResult = {
81
85
  status: "errored",
82
- exceptionSource: unevalException(e),
86
+ error: e,
87
+ coverage: readCoverage(),
83
88
  }
84
89
  onExecutionError(executionResult, { currentScript })
85
90
  return executionResult
@@ -112,16 +117,23 @@ const executeFileUsingSystemJs = (specifier) => {
112
117
  return fileExecutionResultPromise
113
118
  }
114
119
 
115
- const onExecutionError = (executionResult, { currentScript }) => {
116
- // eslint-disable-next-line no-eval
117
- const originalError = window.eval(executionResult.exceptionSource)
118
- if (originalError.code === "NETWORK_FAILURE") {
120
+ const onExecutionError = (
121
+ executionResult,
122
+ {
123
+ currentScript,
124
+ errorExposureInConsole = true,
125
+ errorExposureInNotification = false,
126
+ errorExposureInDocument = true,
127
+ },
128
+ ) => {
129
+ const error = executionResult.error
130
+ if (error.code === "NETWORK_FAILURE") {
119
131
  if (currentScript) {
120
132
  const errorEvent = new Event("error")
121
133
  currentScript.dispatchEvent(errorEvent)
122
134
  }
123
135
  } else {
124
- const { parsingError } = originalError
136
+ const { parsingError } = error
125
137
  const globalErrorEvent = new Event("error")
126
138
  if (parsingError) {
127
139
  globalErrorEvent.filename = parsingError.filename
@@ -129,13 +141,26 @@ const onExecutionError = (executionResult, { currentScript }) => {
129
141
  globalErrorEvent.message = parsingError.message
130
142
  globalErrorEvent.colno = parsingError.columnNumber
131
143
  } else {
132
- globalErrorEvent.filename = originalError.filename
133
- globalErrorEvent.lineno = originalError.lineno
134
- globalErrorEvent.message = originalError.message
135
- globalErrorEvent.colno = originalError.columnno
144
+ globalErrorEvent.filename = error.filename
145
+ globalErrorEvent.lineno = error.lineno
146
+ globalErrorEvent.message = error.message
147
+ globalErrorEvent.colno = error.columnno
136
148
  }
137
149
  window.dispatchEvent(globalErrorEvent)
138
150
  }
151
+
152
+ if (errorExposureInConsole) {
153
+ console.error(error)
154
+ }
155
+ if (errorExposureInNotification) {
156
+ displayErrorNotification(error)
157
+ }
158
+ if (errorExposureInDocument) {
159
+ displayErrorInDocument(error)
160
+ }
161
+
162
+ executionResult.exceptionSource = unevalException(error)
163
+ delete executionResult.error
139
164
  }
140
165
 
141
166
  const getBrowserRuntime = memoize(async () => {
@@ -191,6 +216,8 @@ const getBrowserRuntime = memoize(async () => {
191
216
 
192
217
  const livereloadingCallbacks = {}
193
218
 
219
+ const readCoverage = () => window.__coverage__
220
+
194
221
  window.__jsenv__ = {
195
222
  livereloadingCallbacks,
196
223
  executionResultPromise,
@@ -14,6 +14,7 @@ import {
14
14
  isNodePartOfSupportedRuntimes,
15
15
  isBrowserPartOfSupportedRuntimes,
16
16
  } from "@jsenv/core/src/internal/generateGroupMap/runtime_support.js"
17
+ import { featuresCompatMap } from "@jsenv/core/src/internal/generateGroupMap/featuresCompatMap.js"
17
18
  import { createRuntimeCompat } from "@jsenv/core/src/internal/generateGroupMap/runtime_compat.js"
18
19
  import { createJsenvRollupPlugin } from "./createJsenvRollupPlugin.js"
19
20
 
@@ -71,16 +72,7 @@ export const buildUsingRollup = async ({
71
72
  import_assertion_type_json: true,
72
73
  import_assertion_type_css: true,
73
74
  },
74
- pluginCompatMap: {
75
- import_assertion_type_json: {
76
- chrome: "91",
77
- edge: "91",
78
- },
79
- import_assertion_type_css: {
80
- chrome: "93",
81
- edge: "93",
82
- },
83
- },
75
+ pluginCompatMap: featuresCompatMap,
84
76
  })
85
77
  const importAssertionsSupport = {
86
78
  json:
@@ -13,7 +13,6 @@ import {
13
13
  normalizeStructuredMetaMap,
14
14
  urlToMeta,
15
15
  } from "@jsenv/filesystem"
16
- import { createWorkersForJavaScriptModules } from "@jsenv/workers"
17
16
  import { UNICODE } from "@jsenv/log"
18
17
 
19
18
  import { createUrlConverter } from "@jsenv/core/src/internal/url_conversion.js"
@@ -220,15 +219,17 @@ export const createJsenvRollupPlugin = async ({
220
219
  const jsenvRollupPlugin = {}
221
220
 
222
221
  if (minify) {
223
- const { methodHooks, workers } = createWorkersForJavaScriptModules({
224
- minifyJs: `${new URL("./js/minifyJs.js", import.meta.url)}#minifyJs`,
225
- minifyHtml: `${new URL(
226
- "./html/minifyHtml.js",
227
- import.meta.url,
228
- )}#minifyHtml`,
229
- })
222
+ const methodHooks = {
223
+ minifyJs: async (...args) => {
224
+ const { minifyJs } = await import("./js/minifyJs.js")
225
+ return minifyJs(...args)
226
+ },
227
+ minifyHtml: async (...args) => {
228
+ const { minifyHtml } = await import("./html/minifyHtml.js")
229
+ return minifyHtml(...args)
230
+ },
231
+ }
230
232
 
231
- // inspired from https://github.com/vitejs/vite/blob/06d86e4a2e90ca916a43d450bca1e6c28bc4bfe2/packages/vite/src/node/plugins/terser.ts#L23
232
233
  minifyJs = async ({ url, code, map, ...rest }) => {
233
234
  const result = await methodHooks.minifyJs({
234
235
  url,
@@ -265,10 +266,6 @@ export const createJsenvRollupPlugin = async ({
265
266
  map,
266
267
  }
267
268
  }
268
-
269
- onBundleEnd = () => {
270
- workers.destroy()
271
- }
272
269
  }
273
270
 
274
271
  Object.assign(jsenvRollupPlugin, {
@@ -361,6 +358,7 @@ export const createJsenvRollupPlugin = async ({
361
358
  importMapInfoFromHtml.src,
362
359
  asCompiledServerUrl(importMapInfoFromHtml.htmlUrl),
363
360
  )
361
+ importMapUrl = applyUrlMappings(importMapUrl)
364
362
 
365
363
  if (!urlIsInsideOf(importMapUrl, compileDirectoryRemoteUrl)) {
366
364
  logger.warn(
@@ -6,6 +6,9 @@ import {
6
6
  urlToMeta,
7
7
  } from "@jsenv/filesystem"
8
8
 
9
+ import { featuresCompatMap } from "@jsenv/core/src/internal/generateGroupMap/featuresCompatMap.js"
10
+ import { createRuntimeCompat } from "@jsenv/core/src/internal/generateGroupMap/runtime_compat.js"
11
+
9
12
  import { serverUrlToCompileInfo } from "@jsenv/core/src/internal/url_conversion.js"
10
13
  import { setUrlExtension } from "../url_utils.js"
11
14
  import {
@@ -52,6 +55,15 @@ export const createCompiledFileService = ({
52
55
  sourcemapMethod,
53
56
  sourcemapExcludeSources,
54
57
  }) => {
58
+ const moduleFormats = {}
59
+ Object.keys(groupMap).forEach((groupName) => {
60
+ moduleFormats[groupName] = canAvoidSystemJs({
61
+ runtimeSupport: groupMap[groupName].minRuntimeVersions,
62
+ })
63
+ ? "esmodule"
64
+ : "systemjs"
65
+ })
66
+
55
67
  Object.keys(customCompilers).forEach((key) => {
56
68
  const value = customCompilers[key]
57
69
  if (typeof value !== "function") {
@@ -171,7 +183,10 @@ export const createCompiledFileService = ({
171
183
  request,
172
184
 
173
185
  runtimeSupport,
174
- moduleOutFormat,
186
+ moduleOutFormat:
187
+ moduleOutFormat === undefined
188
+ ? moduleFormats[compileId]
189
+ : moduleOutFormat,
175
190
  importMetaFormat,
176
191
  transformTopLevelAwait,
177
192
  babelPluginMap: babelPluginMapFromCompileId(compileId, {
@@ -189,6 +204,20 @@ export const createCompiledFileService = ({
189
204
  }
190
205
  }
191
206
 
207
+ const canAvoidSystemJs = ({ runtimeSupport }) => {
208
+ const runtimeCompatMap = createRuntimeCompat({
209
+ runtimeSupport,
210
+ pluginMap: {
211
+ module: true,
212
+ importmap: true,
213
+ import_assertion_type_json: true,
214
+ import_assertion_type_css: true,
215
+ },
216
+ pluginCompatMap: featuresCompatMap,
217
+ })
218
+ return runtimeCompatMap.pluginRequiredNameArray.length === 0
219
+ }
220
+
192
221
  const getCompiler = ({ originalFileUrl, compileMeta }) => {
193
222
  const { jsenvCompiler, customCompiler } = urlToMeta({
194
223
  url: originalFileUrl,
@@ -279,7 +279,6 @@ const inlineImportmapScripts = async ({ logger, htmlAst, htmlFileUrl }) => {
279
279
  },
280
280
  ),
281
281
  )
282
-
283
282
  return
284
283
  }
285
284
 
@@ -24,7 +24,7 @@ export const jsenvTransform = async ({
24
24
 
25
25
  babelPluginMap,
26
26
  moduleOutFormat,
27
- importMetaFormat,
27
+ importMetaFormat = moduleOutFormat,
28
28
 
29
29
  babelHelpersInjectionAsImport,
30
30
  allowTopLevelAwait,
@@ -206,7 +206,9 @@ export const jsenvTransform = async ({
206
206
  ...(moduleOutFormat === "systemjs"
207
207
  ? {
208
208
  "proposal-dynamic-import": [proposalDynamicImport],
209
- "transform-modules-systemjs": [transformModulesSystemJs],
209
+ ...(moduleOutFormat === "systemjs"
210
+ ? { "transform-modules-systemjs": [transformModulesSystemJs] }
211
+ : {}),
210
212
  }
211
213
  : {}),
212
214
  }),
@@ -1,10 +1,13 @@
1
1
  import { resolveUrl, urlToRelativeUrl } from "@jsenv/filesystem"
2
+ import { moveImportMap, composeTwoImportMaps } from "@jsenv/importmap"
3
+ import { createDetailedMessage } from "@jsenv/logger"
2
4
 
3
5
  import {
4
6
  jsenvBrowserSystemFileInfo,
5
7
  jsenvToolbarHtmlFileInfo,
6
8
  jsenvToolbarInjectorFileInfo,
7
9
  } from "@jsenv/core/src/internal/jsenvInternalFiles.js"
10
+ import { fetchUrl } from "@jsenv/core/src/internal/fetchUrl.js"
8
11
  import { getDefaultImportMap } from "@jsenv/core/src/internal/import-resolution/importmap-default.js"
9
12
  import {
10
13
  setJavaScriptSourceMappingUrl,
@@ -26,11 +29,10 @@ import {
26
29
  replaceHtmlNode,
27
30
  } from "./compileHtml.js"
28
31
  import { generateCompiledFileAssetUrl } from "./compile-directory/compile-asset.js"
29
- import { composeTwoImportMaps } from "@jsenv/importmap"
30
32
 
31
33
  export const compileHtml = async ({
32
34
  // cancellationToken,
33
- // logger,
35
+ logger,
34
36
  // request,
35
37
  code,
36
38
  url,
@@ -89,17 +91,29 @@ export const compileHtml = async ({
89
91
 
90
92
  let hasImportmap = false
91
93
  const inlineScriptsContentMap = {}
94
+ const importmapsToInline = []
92
95
  scripts.forEach((script) => {
93
96
  const typeAttribute = getHtmlNodeAttributeByName(script, "type")
94
97
  const srcAttribute = getHtmlNodeAttributeByName(script, "src")
95
98
 
96
99
  // importmap
97
100
  if (typeAttribute && typeAttribute.value === "importmap") {
101
+ hasImportmap = true
102
+
98
103
  if (srcAttribute) {
99
- hasImportmap = true
100
- typeAttribute.value = "jsenv-importmap"
104
+ if (moduleOutFormat === "systemjs") {
105
+ typeAttribute.value = "jsenv-importmap"
106
+ return // no need to inline
107
+ }
108
+
109
+ // we force inline because browsers supporting importmap supports only when they are inline
110
+ importmapsToInline.push({
111
+ script,
112
+ src: srcAttribute.value,
113
+ })
101
114
  return
102
115
  }
116
+
103
117
  const defaultImportMap = getDefaultImportMap({
104
118
  importMapFileUrl: compiledUrl,
105
119
  projectDirectoryUrl,
@@ -107,40 +121,51 @@ export const compileHtml = async ({
107
121
  })
108
122
  const inlineImportMap = JSON.parse(getHtmlNodeTextNode(script).value)
109
123
  const mappings = composeTwoImportMaps(defaultImportMap, inlineImportMap)
110
- hasImportmap = true
111
- typeAttribute.value = "jsenv-importmap"
124
+ if (moduleOutFormat === "systemjs") {
125
+ typeAttribute.value = "jsenv-importmap"
126
+ }
112
127
  setHtmlNodeText(script, JSON.stringify(mappings, null, " "))
113
128
  return
114
129
  }
115
130
 
131
+ // remote module script
116
132
  if (typeAttribute && typeAttribute.value === "module" && srcAttribute) {
117
- removeHtmlNodeAttribute(script, typeAttribute)
133
+ if (moduleOutFormat === "systemjs") {
134
+ removeHtmlNodeAttribute(script, typeAttribute)
135
+ }
118
136
  removeHtmlNodeAttribute(script, srcAttribute)
137
+ const src = srcAttribute.value
138
+ const jsenvMethod =
139
+ moduleOutFormat === "systemjs"
140
+ ? "executeFileUsingSystemJs"
141
+ : "executeFileUsingDynamicImport"
119
142
  setHtmlNodeText(
120
143
  script,
121
- `window.__jsenv__.executeFileUsingSystemJs(${JSON.stringify(
122
- srcAttribute.value,
123
- )})`,
144
+ `window.__jsenv__.${jsenvMethod}(${JSON.stringify(src)})`,
124
145
  )
125
146
  return
126
147
  }
127
- // inline
148
+
149
+ // inline module script
128
150
  const textNode = getHtmlNodeTextNode(script)
129
151
  if (typeAttribute && typeAttribute.value === "module" && textNode) {
152
+ if (moduleOutFormat === "systemjs") {
153
+ removeHtmlNodeAttribute(script, typeAttribute)
154
+ }
155
+ removeHtmlNodeAttribute(script, srcAttribute)
130
156
  const scriptAssetUrl = generateCompiledFileAssetUrl(
131
157
  compiledUrl,
132
158
  getUniqueNameForInlineHtmlNode(script, scripts, `[id].js`),
133
159
  )
134
160
  const specifier = `./${urlToRelativeUrl(scriptAssetUrl, compiledUrl)}`
135
161
  inlineScriptsContentMap[specifier] = textNode.value
136
-
137
- removeHtmlNodeAttribute(script, typeAttribute)
138
- removeHtmlNodeAttribute(script, srcAttribute)
162
+ const jsenvMethod =
163
+ moduleOutFormat === "systemjs"
164
+ ? "executeFileUsingSystemJs"
165
+ : "executeFileUsingDynamicImport"
139
166
  setHtmlNodeText(
140
167
  script,
141
- `window.__jsenv__.executeFileUsingSystemJs(${JSON.stringify(
142
- specifier,
143
- )})`,
168
+ `window.__jsenv__.${jsenvMethod}(${JSON.stringify(specifier)})`,
144
169
  )
145
170
  htmlDependencies.push({
146
171
  htmlNode: script,
@@ -149,17 +174,18 @@ export const compileHtml = async ({
149
174
  return
150
175
  }
151
176
  })
177
+
152
178
  if (hasImportmap === false) {
153
179
  const defaultImportMap = getDefaultImportMap({
154
180
  importMapFileUrl: compiledUrl,
155
181
  projectDirectoryUrl,
156
182
  compileDirectoryRelativeUrl: `${outDirectoryRelativeUrl}${compileId}/`,
157
183
  })
158
-
159
184
  manipulateHtmlAst(htmlAst, {
160
185
  scriptInjections: [
161
186
  {
162
- type: "jsenv-importmap",
187
+ type:
188
+ moduleOutFormat === "systemjs" ? "jsenv-importmap" : "importmap",
163
189
  // in case there is no importmap, force the presence
164
190
  // so that '@jsenv/core/' are still remapped
165
191
  text: JSON.stringify(defaultImportMap, null, " "),
@@ -168,6 +194,46 @@ export const compileHtml = async ({
168
194
  })
169
195
  }
170
196
 
197
+ await Promise.all(
198
+ importmapsToInline.map(async ({ script, src }) => {
199
+ const importMapUrl = resolveUrl(src, url)
200
+ const importMapResponse = await fetchUrl(importMapUrl)
201
+ if (importMapResponse.status !== 200) {
202
+ logger.warn(
203
+ createDetailedMessage(
204
+ importMapResponse.status === 404
205
+ ? `Cannot inline importmap script because file cannot be found.`
206
+ : `Cannot inline importmap script due to unexpected response status (${importMapResponse.status}).`,
207
+ {
208
+ "importmap script src": src,
209
+ "importmap url": importMapUrl,
210
+ "html url": url,
211
+ },
212
+ ),
213
+ )
214
+ return
215
+ }
216
+
217
+ const importMapContent = await importMapResponse.json()
218
+ const importMapInlined = moveImportMap(
219
+ importMapContent,
220
+ importMapUrl,
221
+ url,
222
+ )
223
+ replaceHtmlNode(
224
+ script,
225
+ `<script type="importmap">${JSON.stringify(
226
+ importMapInlined,
227
+ null,
228
+ " ",
229
+ )}</script>`,
230
+ {
231
+ attributesToIgnore: ["src"],
232
+ },
233
+ )
234
+ }),
235
+ )
236
+
171
237
  const htmlAfterTransformation = stringifyHtmlAst(htmlAst)
172
238
 
173
239
  let assets = []
@@ -29,10 +29,10 @@ import {
29
29
  createCallbackListNotifiedOnce,
30
30
  } from "@jsenv/abort"
31
31
 
32
+ import { generateGroupMap } from "@jsenv/core/src/internal/generateGroupMap/generateGroupMap.js"
32
33
  import { isBrowserPartOfSupportedRuntimes } from "@jsenv/core/src/internal/generateGroupMap/runtime_support.js"
33
34
  import { loadBabelPluginMapFromFile } from "./load_babel_plugin_map_from_file.js"
34
35
  import { extractSyntaxBabelPluginMap } from "./babel_plugins.js"
35
- import { generateGroupMap } from "../generateGroupMap/generateGroupMap.js"
36
36
  import {
37
37
  jsenvCompileProxyFileInfo,
38
38
  sourcemapMainFileInfo,
@@ -69,8 +69,8 @@ export const startCompileServer = async ({
69
69
 
70
70
  // js compile options
71
71
  transformTopLevelAwait = true,
72
- moduleOutFormat = "systemjs",
73
- importMetaFormat = moduleOutFormat,
72
+ moduleOutFormat,
73
+ importMetaFormat,
74
74
  env = {},
75
75
  processEnvNodeEnv = process.env.NODE_ENV,
76
76
  replaceProcessEnvNodeEnv = true,
@@ -589,24 +589,33 @@ const setupServerSentEventsForLivereload = ({
589
589
  ...livereloadWatchConfig,
590
590
  [jsenvDirectoryRelativeUrl]: false,
591
591
  }
592
- const unregisterDirectoryLifecyle = registerDirectoryLifecycle(
593
- projectDirectoryUrl,
594
- {
595
- watchDescription,
596
- updated: ({ relativeUrl }) => {
597
- projectFileModified.notify(relativeUrl)
598
- },
599
- removed: ({ relativeUrl }) => {
600
- projectFileRemoved.notify(relativeUrl)
601
- },
602
- added: ({ relativeUrl }) => {
603
- projectFileAdded.notify(relativeUrl)
592
+
593
+ // wait 100ms to actually start watching
594
+ // otherwise server starting is delayed by the filesystem scan done in
595
+ // registerDirectoryLifecycle
596
+ const timeout = setTimeout(() => {
597
+ const unregisterDirectoryLifecyle = registerDirectoryLifecycle(
598
+ projectDirectoryUrl,
599
+ {
600
+ watchDescription,
601
+ updated: ({ relativeUrl }) => {
602
+ projectFileModified.notify(relativeUrl)
603
+ },
604
+ removed: ({ relativeUrl }) => {
605
+ projectFileRemoved.notify(relativeUrl)
606
+ },
607
+ added: ({ relativeUrl }) => {
608
+ projectFileAdded.notify(relativeUrl)
609
+ },
610
+ keepProcessAlive: false,
611
+ recursive: true,
604
612
  },
605
- keepProcessAlive: false,
606
- recursive: true,
607
- },
608
- )
609
- serverStopCallbackList.add(unregisterDirectoryLifecyle)
613
+ )
614
+ serverStopCallbackList.add(unregisterDirectoryLifecyle)
615
+ }, 100)
616
+ serverStopCallbackList.add(() => {
617
+ clearTimeout(timeout)
618
+ })
610
619
 
611
620
  const getDependencySet = (mainRelativeUrl) => {
612
621
  if (trackerMap.has(mainRelativeUrl)) {
@@ -48,8 +48,12 @@ export const reportToCoverage = async (
48
48
  // in any scenario we are fine because
49
49
  // coverDescription will generate empty coverage for files
50
50
  // that were suppose to be coverage but were not.
51
- if (executionResult.status === "completed") {
52
- logger.debug(
51
+ if (
52
+ executionResult.status === "completed" &&
53
+ executionResult.runtimeName !== "node" &&
54
+ !process.env.NODE_V8_COVERAGE
55
+ ) {
56
+ logger.warn(
53
57
  `No execution.coverageFileUrl from execution named "${executionName}" of ${file}`,
54
58
  )
55
59
  }
@@ -118,7 +122,13 @@ export const reportToCoverage = async (
118
122
  fileByFileCoverage,
119
123
  babelPluginMap,
120
124
  })
121
- Object.assign(fileByFileCoverage, missingFileByFileCoverage)
125
+ Object.assign(
126
+ fileByFileCoverage,
127
+ normalizeFileByFileCoveragePaths(
128
+ missingFileByFileCoverage,
129
+ projectDirectoryUrl,
130
+ ),
131
+ )
122
132
  }
123
133
 
124
134
  return fileByFileCoverage
@@ -0,0 +1,29 @@
1
+ // https://github.com/babel/babel/blob/master/packages/babel-compat-data/data/native-modules.json#L1
2
+
3
+ export const featuresCompatMap = {
4
+ module: {
5
+ edge: "16",
6
+ firefox: "60",
7
+ chrome: "61",
8
+ safari: "10.1",
9
+ opera: "48",
10
+ ios: "10.3",
11
+ android: "61",
12
+ samsung: "8.2",
13
+ },
14
+ // https://caniuse.com/import-maps
15
+ importmap: {
16
+ edge: "89",
17
+ chrome: "89",
18
+ opera: "76",
19
+ samsung: "15",
20
+ },
21
+ import_assertion_type_json: {
22
+ chrome: "91",
23
+ edge: "91",
24
+ },
25
+ import_assertion_type_css: {
26
+ chrome: "93",
27
+ edge: "93",
28
+ },
29
+ }