@jsenv/core 41.5.3 → 41.5.4
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/dist/build/build.js +54 -14
- package/dist/start_dev_server/start_dev_server.js +41 -8
- package/package.json +1 -1
- package/src/build/build.js +13 -6
- package/src/plugins/import_meta_scenarios/jsenv_plugin_import_meta_scenarios.js +13 -6
- package/src/plugins/plugins.js +5 -1
- package/src/plugins/resolution_node_esm/jsenv_plugin_node_esm_resolution.js +5 -0
- package/src/plugins/resolution_node_esm/node_esm_resolver.js +18 -1
package/dist/build/build.js
CHANGED
|
@@ -6023,6 +6023,8 @@ const createNodeEsmResolver = ({
|
|
|
6023
6023
|
packageDirectory,
|
|
6024
6024
|
runtimeCompat,
|
|
6025
6025
|
rootDirectoryUrl,
|
|
6026
|
+
dev,
|
|
6027
|
+
build,
|
|
6026
6028
|
packageConditions = {},
|
|
6027
6029
|
packageConditionsConfig,
|
|
6028
6030
|
preservesSymlink,
|
|
@@ -6040,6 +6042,8 @@ const createNodeEsmResolver = ({
|
|
|
6040
6042
|
packageConditionsConfig,
|
|
6041
6043
|
rootDirectoryUrl,
|
|
6042
6044
|
runtimeCompat,
|
|
6045
|
+
dev,
|
|
6046
|
+
build,
|
|
6043
6047
|
preservesSymlink,
|
|
6044
6048
|
},
|
|
6045
6049
|
);
|
|
@@ -6201,6 +6205,8 @@ const createBuildPackageConditions = (
|
|
|
6201
6205
|
packageConditionsConfig,
|
|
6202
6206
|
rootDirectoryUrl,
|
|
6203
6207
|
runtimeCompat,
|
|
6208
|
+
dev,
|
|
6209
|
+
build,
|
|
6204
6210
|
preservesSymlink,
|
|
6205
6211
|
},
|
|
6206
6212
|
) => {
|
|
@@ -6290,8 +6296,19 @@ const createBuildPackageConditions = (
|
|
|
6290
6296
|
};
|
|
6291
6297
|
|
|
6292
6298
|
const conditionDefaultResolvers = {
|
|
6299
|
+
// "dev:*" conditions target packages under active development: they
|
|
6300
|
+
// apply to files resolved outside node_modules (sources, workspace
|
|
6301
|
+
// symlinks), never to installed packages.
|
|
6293
6302
|
"dev:*": devResolver,
|
|
6294
|
-
"development"
|
|
6303
|
+
// "development"/"production" follow the ecosystem semantics
|
|
6304
|
+
// (Vite, webpack): they describe how the app runs, not where the
|
|
6305
|
+
// package lives, so they apply to every package, node_modules
|
|
6306
|
+
// included. Dev server resolves "development"; build resolves
|
|
6307
|
+
// "production", unless the build is dev-flavored
|
|
6308
|
+
// (build({ entryPoints: { "./file.js": { dev: true } } }))
|
|
6309
|
+
// in which case it resolves "development" too.
|
|
6310
|
+
"development": Boolean(dev),
|
|
6311
|
+
"production": Boolean(build) && !dev,
|
|
6295
6312
|
"node": nodeRuntimeEnabled,
|
|
6296
6313
|
"browser": !nodeRuntimeEnabled,
|
|
6297
6314
|
"import": true,
|
|
@@ -6505,6 +6522,7 @@ const jsenvPluginNodeEsmResolution = ({
|
|
|
6505
6522
|
resolutionConfig = {},
|
|
6506
6523
|
packageConditions,
|
|
6507
6524
|
packageConditionsConfig = {},
|
|
6525
|
+
dev,
|
|
6508
6526
|
}) => {
|
|
6509
6527
|
let nodeEsmResolverDefault;
|
|
6510
6528
|
const resolverMap = new Map();
|
|
@@ -6526,6 +6544,8 @@ const jsenvPluginNodeEsmResolution = ({
|
|
|
6526
6544
|
packageDirectory,
|
|
6527
6545
|
runtimeCompat: kitchenContext.runtimeCompat,
|
|
6528
6546
|
rootDirectoryUrl: kitchenContext.rootDirectoryUrl,
|
|
6547
|
+
dev: dev === undefined ? kitchenContext.dev : dev,
|
|
6548
|
+
build: kitchenContext.build,
|
|
6529
6549
|
packageConditions,
|
|
6530
6550
|
packageConditionsConfig: {
|
|
6531
6551
|
...kitchenContext.packageConditionsConfig,
|
|
@@ -6543,6 +6563,8 @@ const jsenvPluginNodeEsmResolution = ({
|
|
|
6543
6563
|
packageDirectory,
|
|
6544
6564
|
runtimeCompat: kitchenContext.runtimeCompat,
|
|
6545
6565
|
rootDirectoryUrl: kitchenContext.rootDirectoryUrl,
|
|
6566
|
+
dev: dev === undefined ? kitchenContext.dev : dev,
|
|
6567
|
+
build: kitchenContext.build,
|
|
6546
6568
|
// preservesSymlink: true,
|
|
6547
6569
|
packageConditions,
|
|
6548
6570
|
packageConditionsConfig: {
|
|
@@ -8189,11 +8211,16 @@ const babelPluginMetadataExpressionPaths = (
|
|
|
8189
8211
|
* - left as is to be evaluated to undefined (import.meta.build but it's the dev server)
|
|
8190
8212
|
* - replaced by undefined (import.meta.dev but it's build; the goal is to ensure it's tree-shaked)
|
|
8191
8213
|
*
|
|
8214
|
+
* A build can also be dev-flavored (build({ entryPoints: { "./file.js": { dev: true } } })):
|
|
8215
|
+
* import.meta.dev is then replaced by true, so a package can publish a build
|
|
8216
|
+
* that keeps its dev-only code, exposed to consumers via the "development"
|
|
8217
|
+
* package export condition.
|
|
8218
|
+
*
|
|
8192
8219
|
* TODO: ideally during dev we would keep import.meta.dev and ensure we set it to true rather than replacing it with true?
|
|
8193
8220
|
*/
|
|
8194
8221
|
|
|
8195
8222
|
|
|
8196
|
-
const jsenvPluginImportMetaScenarios = () => {
|
|
8223
|
+
const jsenvPluginImportMetaScenarios = ({ dev } = {}) => {
|
|
8197
8224
|
return {
|
|
8198
8225
|
name: "jsenv:import_meta_scenario",
|
|
8199
8226
|
appliesDuring: "*",
|
|
@@ -8223,17 +8250,19 @@ const jsenvPluginImportMetaScenarios = () => {
|
|
|
8223
8250
|
}
|
|
8224
8251
|
},
|
|
8225
8252
|
});
|
|
8226
|
-
const
|
|
8253
|
+
const devNodes = importMetaScenarioNodes.dev;
|
|
8254
|
+
const buildNodes = importMetaScenarioNodes.build;
|
|
8227
8255
|
const replacements = [];
|
|
8228
8256
|
const replace = (node, value) => {
|
|
8229
8257
|
replacements.push({ node, value });
|
|
8230
8258
|
};
|
|
8231
8259
|
if (urlInfo.context.build) {
|
|
8232
8260
|
// during build ensure replacement for tree-shaking
|
|
8233
|
-
|
|
8234
|
-
|
|
8261
|
+
// (or for keeping dev code when the build is dev-flavored)
|
|
8262
|
+
devNodes.forEach((node) => {
|
|
8263
|
+
replace(node, dev ? "true" : "undefined");
|
|
8235
8264
|
});
|
|
8236
|
-
|
|
8265
|
+
buildNodes.forEach((node) => {
|
|
8237
8266
|
replace(node, "true");
|
|
8238
8267
|
});
|
|
8239
8268
|
} else {
|
|
@@ -8241,7 +8270,7 @@ const jsenvPluginImportMetaScenarios = () => {
|
|
|
8241
8270
|
// it will be evaluated to undefined.
|
|
8242
8271
|
// Moreover it can be surprising to see some "undefined"
|
|
8243
8272
|
// when source file contains "import.meta.build"
|
|
8244
|
-
|
|
8273
|
+
devNodes.forEach((node) => {
|
|
8245
8274
|
replace(node, "true");
|
|
8246
8275
|
});
|
|
8247
8276
|
}
|
|
@@ -10119,6 +10148,9 @@ const getCorePlugins = ({
|
|
|
10119
10148
|
runtimeCompat,
|
|
10120
10149
|
packageDirectory,
|
|
10121
10150
|
sourceFilesConfig,
|
|
10151
|
+
// during build, a dev-flavored entry point sets dev: true
|
|
10152
|
+
// (during dev the kitchen context already says so, no need to pass it)
|
|
10153
|
+
dev,
|
|
10122
10154
|
|
|
10123
10155
|
referenceAnalysis = {},
|
|
10124
10156
|
nodeEsmResolution = {},
|
|
@@ -10215,6 +10247,7 @@ const getCorePlugins = ({
|
|
|
10215
10247
|
resolutionConfig: nodeEsmResolution,
|
|
10216
10248
|
packageConditions,
|
|
10217
10249
|
packageConditionsConfig,
|
|
10250
|
+
dev,
|
|
10218
10251
|
}),
|
|
10219
10252
|
]
|
|
10220
10253
|
: []),
|
|
@@ -10232,7 +10265,7 @@ const getCorePlugins = ({
|
|
|
10232
10265
|
|
|
10233
10266
|
jsenvPluginImportMetaCss(),
|
|
10234
10267
|
jsenvPluginCommonJsGlobals(),
|
|
10235
|
-
jsenvPluginImportMetaScenarios(),
|
|
10268
|
+
jsenvPluginImportMetaScenarios({ dev }),
|
|
10236
10269
|
...(scenarioPlaceholders ? [jsenvPluginGlobalScenarios()] : []),
|
|
10237
10270
|
jsenvPluginNodeRuntime({ runtimeCompat }),
|
|
10238
10271
|
|
|
@@ -12413,6 +12446,12 @@ const jsenvPluginMappings = (mappings) => {
|
|
|
12413
12446
|
* Relative URL where this entry point will be written in the build directory
|
|
12414
12447
|
* @param {object} [entryPoint.runtimeCompat]
|
|
12415
12448
|
* Runtime compatibility configuration for this entry point
|
|
12449
|
+
* @param {boolean} [entryPoint.dev=false]
|
|
12450
|
+
* Produce a dev-flavored build: import.meta.dev is replaced by true
|
|
12451
|
+
* (instead of undefined) and dependencies resolve their "development"
|
|
12452
|
+
* package export condition (instead of "production"). Meant for packages
|
|
12453
|
+
* publishing two flavors, the dev one exposed to consumers via the
|
|
12454
|
+
* "development" condition in their package.json "exports"
|
|
12416
12455
|
* @param {string} [entryPoint.assetsDirectory]
|
|
12417
12456
|
* Directory where asset files will be written for this entry point
|
|
12418
12457
|
* @param {string|url} [entryPoint.base]
|
|
@@ -12536,12 +12575,10 @@ entryPoints: {
|
|
|
12536
12575
|
let runtimeType;
|
|
12537
12576
|
{
|
|
12538
12577
|
if (isBareSpecifier(key)) {
|
|
12539
|
-
|
|
12540
|
-
|
|
12541
|
-
|
|
12542
|
-
|
|
12543
|
-
"import",
|
|
12544
|
-
];
|
|
12578
|
+
// "development" is not resolved here on purpose: it points at a
|
|
12579
|
+
// package's dev-flavored dist, which is not a build input;
|
|
12580
|
+
// "dev:*" points at sources, which are.
|
|
12581
|
+
const packageConditions = ["dev:*", "node", "import"];
|
|
12545
12582
|
try {
|
|
12546
12583
|
const { url, type } = applyNodeEsmResolution({
|
|
12547
12584
|
conditions: packageConditions,
|
|
@@ -13273,6 +13310,7 @@ entryPoints: {
|
|
|
13273
13310
|
const entryPointDefaultParams = {
|
|
13274
13311
|
buildRelativeUrl: undefined,
|
|
13275
13312
|
mode: undefined,
|
|
13313
|
+
dev: false,
|
|
13276
13314
|
runtimeCompat: undefined,
|
|
13277
13315
|
plugins: [],
|
|
13278
13316
|
mappings: undefined,
|
|
@@ -13328,6 +13366,7 @@ const prepareEntryPointBuild = async (
|
|
|
13328
13366
|
let {
|
|
13329
13367
|
buildRelativeUrl,
|
|
13330
13368
|
mode,
|
|
13369
|
+
dev,
|
|
13331
13370
|
runtimeCompat,
|
|
13332
13371
|
plugins,
|
|
13333
13372
|
mappings,
|
|
@@ -13508,6 +13547,7 @@ const prepareEntryPointBuild = async (
|
|
|
13508
13547
|
packageDirectory,
|
|
13509
13548
|
rootDirectoryUrl: sourceDirectoryUrl,
|
|
13510
13549
|
runtimeCompat,
|
|
13550
|
+
dev,
|
|
13511
13551
|
referenceAnalysis,
|
|
13512
13552
|
nodeEsmResolution,
|
|
13513
13553
|
packageConditions,
|
|
@@ -2689,6 +2689,8 @@ const createNodeEsmResolver = ({
|
|
|
2689
2689
|
packageDirectory,
|
|
2690
2690
|
runtimeCompat,
|
|
2691
2691
|
rootDirectoryUrl,
|
|
2692
|
+
dev,
|
|
2693
|
+
build,
|
|
2692
2694
|
packageConditions = {},
|
|
2693
2695
|
packageConditionsConfig,
|
|
2694
2696
|
preservesSymlink,
|
|
@@ -2706,6 +2708,8 @@ const createNodeEsmResolver = ({
|
|
|
2706
2708
|
packageConditionsConfig,
|
|
2707
2709
|
rootDirectoryUrl,
|
|
2708
2710
|
runtimeCompat,
|
|
2711
|
+
dev,
|
|
2712
|
+
build,
|
|
2709
2713
|
preservesSymlink,
|
|
2710
2714
|
},
|
|
2711
2715
|
);
|
|
@@ -2867,6 +2871,8 @@ const createBuildPackageConditions = (
|
|
|
2867
2871
|
packageConditionsConfig,
|
|
2868
2872
|
rootDirectoryUrl,
|
|
2869
2873
|
runtimeCompat,
|
|
2874
|
+
dev,
|
|
2875
|
+
build,
|
|
2870
2876
|
preservesSymlink,
|
|
2871
2877
|
},
|
|
2872
2878
|
) => {
|
|
@@ -2956,8 +2962,19 @@ const createBuildPackageConditions = (
|
|
|
2956
2962
|
};
|
|
2957
2963
|
|
|
2958
2964
|
const conditionDefaultResolvers = {
|
|
2965
|
+
// "dev:*" conditions target packages under active development: they
|
|
2966
|
+
// apply to files resolved outside node_modules (sources, workspace
|
|
2967
|
+
// symlinks), never to installed packages.
|
|
2959
2968
|
"dev:*": devResolver,
|
|
2960
|
-
"development"
|
|
2969
|
+
// "development"/"production" follow the ecosystem semantics
|
|
2970
|
+
// (Vite, webpack): they describe how the app runs, not where the
|
|
2971
|
+
// package lives, so they apply to every package, node_modules
|
|
2972
|
+
// included. Dev server resolves "development"; build resolves
|
|
2973
|
+
// "production", unless the build is dev-flavored
|
|
2974
|
+
// (build({ entryPoints: { "./file.js": { dev: true } } }))
|
|
2975
|
+
// in which case it resolves "development" too.
|
|
2976
|
+
"development": Boolean(dev),
|
|
2977
|
+
"production": Boolean(build) && !dev,
|
|
2961
2978
|
"node": nodeRuntimeEnabled,
|
|
2962
2979
|
"browser": !nodeRuntimeEnabled,
|
|
2963
2980
|
"import": true,
|
|
@@ -3171,6 +3188,7 @@ const jsenvPluginNodeEsmResolution = ({
|
|
|
3171
3188
|
resolutionConfig = {},
|
|
3172
3189
|
packageConditions,
|
|
3173
3190
|
packageConditionsConfig = {},
|
|
3191
|
+
dev,
|
|
3174
3192
|
}) => {
|
|
3175
3193
|
let nodeEsmResolverDefault;
|
|
3176
3194
|
const resolverMap = new Map();
|
|
@@ -3192,6 +3210,8 @@ const jsenvPluginNodeEsmResolution = ({
|
|
|
3192
3210
|
packageDirectory,
|
|
3193
3211
|
runtimeCompat: kitchenContext.runtimeCompat,
|
|
3194
3212
|
rootDirectoryUrl: kitchenContext.rootDirectoryUrl,
|
|
3213
|
+
dev: dev === undefined ? kitchenContext.dev : dev,
|
|
3214
|
+
build: kitchenContext.build,
|
|
3195
3215
|
packageConditions,
|
|
3196
3216
|
packageConditionsConfig: {
|
|
3197
3217
|
...kitchenContext.packageConditionsConfig,
|
|
@@ -3209,6 +3229,8 @@ const jsenvPluginNodeEsmResolution = ({
|
|
|
3209
3229
|
packageDirectory,
|
|
3210
3230
|
runtimeCompat: kitchenContext.runtimeCompat,
|
|
3211
3231
|
rootDirectoryUrl: kitchenContext.rootDirectoryUrl,
|
|
3232
|
+
dev: dev === undefined ? kitchenContext.dev : dev,
|
|
3233
|
+
build: kitchenContext.build,
|
|
3212
3234
|
// preservesSymlink: true,
|
|
3213
3235
|
packageConditions,
|
|
3214
3236
|
packageConditionsConfig: {
|
|
@@ -5994,11 +6016,16 @@ const babelPluginMetadataExpressionPaths = (
|
|
|
5994
6016
|
* - left as is to be evaluated to undefined (import.meta.build but it's the dev server)
|
|
5995
6017
|
* - replaced by undefined (import.meta.dev but it's build; the goal is to ensure it's tree-shaked)
|
|
5996
6018
|
*
|
|
6019
|
+
* A build can also be dev-flavored (build({ entryPoints: { "./file.js": { dev: true } } })):
|
|
6020
|
+
* import.meta.dev is then replaced by true, so a package can publish a build
|
|
6021
|
+
* that keeps its dev-only code, exposed to consumers via the "development"
|
|
6022
|
+
* package export condition.
|
|
6023
|
+
*
|
|
5997
6024
|
* TODO: ideally during dev we would keep import.meta.dev and ensure we set it to true rather than replacing it with true?
|
|
5998
6025
|
*/
|
|
5999
6026
|
|
|
6000
6027
|
|
|
6001
|
-
const jsenvPluginImportMetaScenarios = () => {
|
|
6028
|
+
const jsenvPluginImportMetaScenarios = ({ dev } = {}) => {
|
|
6002
6029
|
return {
|
|
6003
6030
|
name: "jsenv:import_meta_scenario",
|
|
6004
6031
|
appliesDuring: "*",
|
|
@@ -6028,17 +6055,19 @@ const jsenvPluginImportMetaScenarios = () => {
|
|
|
6028
6055
|
}
|
|
6029
6056
|
},
|
|
6030
6057
|
});
|
|
6031
|
-
const
|
|
6058
|
+
const devNodes = importMetaScenarioNodes.dev;
|
|
6059
|
+
const buildNodes = importMetaScenarioNodes.build;
|
|
6032
6060
|
const replacements = [];
|
|
6033
6061
|
const replace = (node, value) => {
|
|
6034
6062
|
replacements.push({ node, value });
|
|
6035
6063
|
};
|
|
6036
6064
|
if (urlInfo.context.build) {
|
|
6037
6065
|
// during build ensure replacement for tree-shaking
|
|
6038
|
-
|
|
6039
|
-
|
|
6066
|
+
// (or for keeping dev code when the build is dev-flavored)
|
|
6067
|
+
devNodes.forEach((node) => {
|
|
6068
|
+
replace(node, dev ? "true" : "undefined");
|
|
6040
6069
|
});
|
|
6041
|
-
|
|
6070
|
+
buildNodes.forEach((node) => {
|
|
6042
6071
|
replace(node, "true");
|
|
6043
6072
|
});
|
|
6044
6073
|
} else {
|
|
@@ -6046,7 +6075,7 @@ const jsenvPluginImportMetaScenarios = () => {
|
|
|
6046
6075
|
// it will be evaluated to undefined.
|
|
6047
6076
|
// Moreover it can be surprising to see some "undefined"
|
|
6048
6077
|
// when source file contains "import.meta.build"
|
|
6049
|
-
|
|
6078
|
+
devNodes.forEach((node) => {
|
|
6050
6079
|
replace(node, "true");
|
|
6051
6080
|
});
|
|
6052
6081
|
}
|
|
@@ -7984,6 +8013,9 @@ const getCorePlugins = ({
|
|
|
7984
8013
|
runtimeCompat,
|
|
7985
8014
|
packageDirectory,
|
|
7986
8015
|
sourceFilesConfig,
|
|
8016
|
+
// during build, a dev-flavored entry point sets dev: true
|
|
8017
|
+
// (during dev the kitchen context already says so, no need to pass it)
|
|
8018
|
+
dev,
|
|
7987
8019
|
|
|
7988
8020
|
referenceAnalysis = {},
|
|
7989
8021
|
nodeEsmResolution = {},
|
|
@@ -8080,6 +8112,7 @@ const getCorePlugins = ({
|
|
|
8080
8112
|
resolutionConfig: nodeEsmResolution,
|
|
8081
8113
|
packageConditions,
|
|
8082
8114
|
packageConditionsConfig,
|
|
8115
|
+
dev,
|
|
8083
8116
|
}),
|
|
8084
8117
|
]
|
|
8085
8118
|
: []),
|
|
@@ -8097,7 +8130,7 @@ const getCorePlugins = ({
|
|
|
8097
8130
|
|
|
8098
8131
|
jsenvPluginImportMetaCss(),
|
|
8099
8132
|
jsenvPluginCommonJsGlobals(),
|
|
8100
|
-
jsenvPluginImportMetaScenarios(),
|
|
8133
|
+
jsenvPluginImportMetaScenarios({ dev }),
|
|
8101
8134
|
...(scenarioPlaceholders ? [jsenvPluginGlobalScenarios()] : []),
|
|
8102
8135
|
jsenvPluginNodeRuntime({ runtimeCompat }),
|
|
8103
8136
|
|
package/package.json
CHANGED
package/src/build/build.js
CHANGED
|
@@ -117,6 +117,12 @@ import { jsenvPluginMappings } from "./jsenv_plugin_mappings.js";
|
|
|
117
117
|
* Relative URL where this entry point will be written in the build directory
|
|
118
118
|
* @param {object} [entryPoint.runtimeCompat]
|
|
119
119
|
* Runtime compatibility configuration for this entry point
|
|
120
|
+
* @param {boolean} [entryPoint.dev=false]
|
|
121
|
+
* Produce a dev-flavored build: import.meta.dev is replaced by true
|
|
122
|
+
* (instead of undefined) and dependencies resolve their "development"
|
|
123
|
+
* package export condition (instead of "production"). Meant for packages
|
|
124
|
+
* publishing two flavors, the dev one exposed to consumers via the
|
|
125
|
+
* "development" condition in their package.json "exports"
|
|
120
126
|
* @param {string} [entryPoint.assetsDirectory]
|
|
121
127
|
* Directory where asset files will be written for this entry point
|
|
122
128
|
* @param {string|url} [entryPoint.base]
|
|
@@ -240,12 +246,10 @@ entryPoints: {
|
|
|
240
246
|
let runtimeType;
|
|
241
247
|
{
|
|
242
248
|
if (isBareSpecifier(key)) {
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
"import",
|
|
248
|
-
];
|
|
249
|
+
// "development" is not resolved here on purpose: it points at a
|
|
250
|
+
// package's dev-flavored dist, which is not a build input;
|
|
251
|
+
// "dev:*" points at sources, which are.
|
|
252
|
+
const packageConditions = ["dev:*", "node", "import"];
|
|
249
253
|
try {
|
|
250
254
|
const { url, type } = applyNodeEsmResolution({
|
|
251
255
|
conditions: packageConditions,
|
|
@@ -979,6 +983,7 @@ entryPoints: {
|
|
|
979
983
|
const entryPointDefaultParams = {
|
|
980
984
|
buildRelativeUrl: undefined,
|
|
981
985
|
mode: undefined,
|
|
986
|
+
dev: false,
|
|
982
987
|
runtimeCompat: undefined,
|
|
983
988
|
plugins: [],
|
|
984
989
|
mappings: undefined,
|
|
@@ -1034,6 +1039,7 @@ const prepareEntryPointBuild = async (
|
|
|
1034
1039
|
let {
|
|
1035
1040
|
buildRelativeUrl,
|
|
1036
1041
|
mode,
|
|
1042
|
+
dev,
|
|
1037
1043
|
runtimeCompat,
|
|
1038
1044
|
plugins,
|
|
1039
1045
|
mappings,
|
|
@@ -1214,6 +1220,7 @@ const prepareEntryPointBuild = async (
|
|
|
1214
1220
|
packageDirectory,
|
|
1215
1221
|
rootDirectoryUrl: sourceDirectoryUrl,
|
|
1216
1222
|
runtimeCompat,
|
|
1223
|
+
dev,
|
|
1217
1224
|
referenceAnalysis,
|
|
1218
1225
|
nodeEsmResolution,
|
|
1219
1226
|
packageConditions,
|
|
@@ -7,13 +7,18 @@
|
|
|
7
7
|
* - left as is to be evaluated to undefined (import.meta.build but it's the dev server)
|
|
8
8
|
* - replaced by undefined (import.meta.dev but it's build; the goal is to ensure it's tree-shaked)
|
|
9
9
|
*
|
|
10
|
+
* A build can also be dev-flavored (build({ entryPoints: { "./file.js": { dev: true } } })):
|
|
11
|
+
* import.meta.dev is then replaced by true, so a package can publish a build
|
|
12
|
+
* that keeps its dev-only code, exposed to consumers via the "development"
|
|
13
|
+
* package export condition.
|
|
14
|
+
*
|
|
10
15
|
* TODO: ideally during dev we would keep import.meta.dev and ensure we set it to true rather than replacing it with true?
|
|
11
16
|
*/
|
|
12
17
|
|
|
13
18
|
import { getImportMetaPropertyName, visitJsAst } from "@jsenv/ast";
|
|
14
19
|
import { createMagicSource } from "@jsenv/sourcemap";
|
|
15
20
|
|
|
16
|
-
export const jsenvPluginImportMetaScenarios = () => {
|
|
21
|
+
export const jsenvPluginImportMetaScenarios = ({ dev } = {}) => {
|
|
17
22
|
return {
|
|
18
23
|
name: "jsenv:import_meta_scenario",
|
|
19
24
|
appliesDuring: "*",
|
|
@@ -43,17 +48,19 @@ export const jsenvPluginImportMetaScenarios = () => {
|
|
|
43
48
|
}
|
|
44
49
|
},
|
|
45
50
|
});
|
|
46
|
-
const
|
|
51
|
+
const devNodes = importMetaScenarioNodes.dev;
|
|
52
|
+
const buildNodes = importMetaScenarioNodes.build;
|
|
47
53
|
const replacements = [];
|
|
48
54
|
const replace = (node, value) => {
|
|
49
55
|
replacements.push({ node, value });
|
|
50
56
|
};
|
|
51
57
|
if (urlInfo.context.build) {
|
|
52
58
|
// during build ensure replacement for tree-shaking
|
|
53
|
-
|
|
54
|
-
|
|
59
|
+
// (or for keeping dev code when the build is dev-flavored)
|
|
60
|
+
devNodes.forEach((node) => {
|
|
61
|
+
replace(node, dev ? "true" : "undefined");
|
|
55
62
|
});
|
|
56
|
-
|
|
63
|
+
buildNodes.forEach((node) => {
|
|
57
64
|
replace(node, "true");
|
|
58
65
|
});
|
|
59
66
|
} else {
|
|
@@ -61,7 +68,7 @@ export const jsenvPluginImportMetaScenarios = () => {
|
|
|
61
68
|
// it will be evaluated to undefined.
|
|
62
69
|
// Moreover it can be surprising to see some "undefined"
|
|
63
70
|
// when source file contains "import.meta.build"
|
|
64
|
-
|
|
71
|
+
devNodes.forEach((node) => {
|
|
65
72
|
replace(node, "true");
|
|
66
73
|
});
|
|
67
74
|
}
|
package/src/plugins/plugins.js
CHANGED
|
@@ -38,6 +38,9 @@ export const getCorePlugins = ({
|
|
|
38
38
|
runtimeCompat,
|
|
39
39
|
packageDirectory,
|
|
40
40
|
sourceFilesConfig,
|
|
41
|
+
// during build, a dev-flavored entry point sets dev: true
|
|
42
|
+
// (during dev the kitchen context already says so, no need to pass it)
|
|
43
|
+
dev,
|
|
41
44
|
|
|
42
45
|
referenceAnalysis = {},
|
|
43
46
|
nodeEsmResolution = {},
|
|
@@ -134,6 +137,7 @@ export const getCorePlugins = ({
|
|
|
134
137
|
resolutionConfig: nodeEsmResolution,
|
|
135
138
|
packageConditions,
|
|
136
139
|
packageConditionsConfig,
|
|
140
|
+
dev,
|
|
137
141
|
}),
|
|
138
142
|
]
|
|
139
143
|
: []),
|
|
@@ -151,7 +155,7 @@ export const getCorePlugins = ({
|
|
|
151
155
|
|
|
152
156
|
jsenvPluginImportMetaCss(),
|
|
153
157
|
jsenvPluginCommonJsGlobals(),
|
|
154
|
-
jsenvPluginImportMetaScenarios(),
|
|
158
|
+
jsenvPluginImportMetaScenarios({ dev }),
|
|
155
159
|
...(scenarioPlaceholders ? [jsenvPluginGlobalScenarios()] : []),
|
|
156
160
|
jsenvPluginNodeRuntime({ runtimeCompat }),
|
|
157
161
|
|
|
@@ -5,6 +5,7 @@ export const jsenvPluginNodeEsmResolution = ({
|
|
|
5
5
|
resolutionConfig = {},
|
|
6
6
|
packageConditions,
|
|
7
7
|
packageConditionsConfig = {},
|
|
8
|
+
dev,
|
|
8
9
|
}) => {
|
|
9
10
|
let nodeEsmResolverDefault;
|
|
10
11
|
const resolverMap = new Map();
|
|
@@ -26,6 +27,8 @@ export const jsenvPluginNodeEsmResolution = ({
|
|
|
26
27
|
packageDirectory,
|
|
27
28
|
runtimeCompat: kitchenContext.runtimeCompat,
|
|
28
29
|
rootDirectoryUrl: kitchenContext.rootDirectoryUrl,
|
|
30
|
+
dev: dev === undefined ? kitchenContext.dev : dev,
|
|
31
|
+
build: kitchenContext.build,
|
|
29
32
|
packageConditions,
|
|
30
33
|
packageConditionsConfig: {
|
|
31
34
|
...kitchenContext.packageConditionsConfig,
|
|
@@ -43,6 +46,8 @@ export const jsenvPluginNodeEsmResolution = ({
|
|
|
43
46
|
packageDirectory,
|
|
44
47
|
runtimeCompat: kitchenContext.runtimeCompat,
|
|
45
48
|
rootDirectoryUrl: kitchenContext.rootDirectoryUrl,
|
|
49
|
+
dev: dev === undefined ? kitchenContext.dev : dev,
|
|
50
|
+
build: kitchenContext.build,
|
|
46
51
|
// preservesSymlink: true,
|
|
47
52
|
packageConditions,
|
|
48
53
|
packageConditionsConfig: {
|
|
@@ -20,6 +20,8 @@ export const createNodeEsmResolver = ({
|
|
|
20
20
|
packageDirectory,
|
|
21
21
|
runtimeCompat,
|
|
22
22
|
rootDirectoryUrl,
|
|
23
|
+
dev,
|
|
24
|
+
build,
|
|
23
25
|
packageConditions = {},
|
|
24
26
|
packageConditionsConfig,
|
|
25
27
|
preservesSymlink,
|
|
@@ -37,6 +39,8 @@ export const createNodeEsmResolver = ({
|
|
|
37
39
|
packageConditionsConfig,
|
|
38
40
|
rootDirectoryUrl,
|
|
39
41
|
runtimeCompat,
|
|
42
|
+
dev,
|
|
43
|
+
build,
|
|
40
44
|
preservesSymlink,
|
|
41
45
|
},
|
|
42
46
|
);
|
|
@@ -198,6 +202,8 @@ const createBuildPackageConditions = (
|
|
|
198
202
|
packageConditionsConfig,
|
|
199
203
|
rootDirectoryUrl,
|
|
200
204
|
runtimeCompat,
|
|
205
|
+
dev,
|
|
206
|
+
build,
|
|
201
207
|
preservesSymlink,
|
|
202
208
|
},
|
|
203
209
|
) => {
|
|
@@ -287,8 +293,19 @@ const createBuildPackageConditions = (
|
|
|
287
293
|
};
|
|
288
294
|
|
|
289
295
|
const conditionDefaultResolvers = {
|
|
296
|
+
// "dev:*" conditions target packages under active development: they
|
|
297
|
+
// apply to files resolved outside node_modules (sources, workspace
|
|
298
|
+
// symlinks), never to installed packages.
|
|
290
299
|
"dev:*": devResolver,
|
|
291
|
-
"development"
|
|
300
|
+
// "development"/"production" follow the ecosystem semantics
|
|
301
|
+
// (Vite, webpack): they describe how the app runs, not where the
|
|
302
|
+
// package lives, so they apply to every package, node_modules
|
|
303
|
+
// included. Dev server resolves "development"; build resolves
|
|
304
|
+
// "production", unless the build is dev-flavored
|
|
305
|
+
// (build({ entryPoints: { "./file.js": { dev: true } } }))
|
|
306
|
+
// in which case it resolves "development" too.
|
|
307
|
+
"development": Boolean(dev),
|
|
308
|
+
"production": Boolean(build) && !dev,
|
|
292
309
|
"node": nodeRuntimeEnabled,
|
|
293
310
|
"browser": !nodeRuntimeEnabled,
|
|
294
311
|
"import": true,
|