@vue/compiler-sfc 3.2.32 → 3.2.34

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.
@@ -111,9 +111,9 @@ var hashSum = sum;
111
111
  const CSS_VARS_HELPER = `useCssVars`;
112
112
  // match v-bind() with max 2-levels of nested parens.
113
113
  const cssVarRE = /v-bind\s*\(((?:[^)(]+|\((?:[^)(]+|\([^)(]*\))*\))*)\)/g;
114
- function genCssVarsFromList(vars, id, isProd) {
114
+ function genCssVarsFromList(vars, id, isProd, isSSR = false) {
115
115
  return `{\n ${vars
116
- .map(key => `"${genVarName(id, key, isProd)}": (${key})`)
116
+ .map(key => `"${isSSR ? `--` : ``}${genVarName(id, key, isProd)}": (${key})`)
117
117
  .join(',\n ')}\n}`;
118
118
  }
119
119
  function genVarName(id, raw, isProd) {
@@ -124,7 +124,7 @@ function genVarName(id, raw, isProd) {
124
124
  return `${id}-${raw.replace(/([^\w-])/g, '_')}`;
125
125
  }
126
126
  }
127
- function noramlizeExpression(exp) {
127
+ function normalizeExpression(exp) {
128
128
  exp = exp.trim();
129
129
  if ((exp[0] === `'` && exp[exp.length - 1] === `'`) ||
130
130
  (exp[0] === `"` && exp[exp.length - 1] === `"`)) {
@@ -139,7 +139,7 @@ function parseCssVars(sfc) {
139
139
  // ignore v-bind() in comments /* ... */
140
140
  const content = style.content.replace(/\/\*([\s\S]*?)\*\//g, '');
141
141
  while ((match = cssVarRE.exec(content))) {
142
- const variable = noramlizeExpression(match[1]);
142
+ const variable = normalizeExpression(match[1]);
143
143
  if (!vars.includes(variable)) {
144
144
  vars.push(variable);
145
145
  }
@@ -155,7 +155,7 @@ const cssVarsPlugin = opts => {
155
155
  // rewrite CSS variables
156
156
  if (cssVarRE.test(decl.value)) {
157
157
  decl.value = decl.value.replace(cssVarRE, (_, $1) => {
158
- return `var(--${genVarName(id, noramlizeExpression($1), isProd)})`;
158
+ return `var(--${genVarName(id, normalizeExpression($1), isProd)})`;
159
159
  });
160
160
  }
161
161
  }
@@ -1011,9 +1011,15 @@ const defaultAssetUrlOptions = {
1011
1011
  const normalizeOptions = (options) => {
1012
1012
  if (Object.keys(options).some(key => shared.isArray(options[key]))) {
1013
1013
  // legacy option format which directly passes in tags config
1014
- return Object.assign(Object.assign({}, defaultAssetUrlOptions), { tags: options });
1014
+ return {
1015
+ ...defaultAssetUrlOptions,
1016
+ tags: options
1017
+ };
1015
1018
  }
1016
- return Object.assign(Object.assign({}, defaultAssetUrlOptions), options);
1019
+ return {
1020
+ ...defaultAssetUrlOptions,
1021
+ ...options
1022
+ };
1017
1023
  };
1018
1024
  const createAssetUrlTransformWithOptions = (options) => {
1019
1025
  return (node, context) => transformAssetUrl(node, context, options);
@@ -1102,6 +1108,10 @@ function getImportsExpressionExp(path, hash, loc, context) {
1102
1108
  return exp;
1103
1109
  }
1104
1110
  const hashExp = `${name} + '${hash}'`;
1111
+ const finalExp = compilerCore.createSimpleExpression(hashExp, false, loc, 3 /* CAN_STRINGIFY */);
1112
+ if (!context.hoistStatic) {
1113
+ return finalExp;
1114
+ }
1105
1115
  const existingHoistIndex = context.hoists.findIndex(h => {
1106
1116
  return (h &&
1107
1117
  h.type === 4 /* SIMPLE_EXPRESSION */ &&
@@ -1111,7 +1121,7 @@ function getImportsExpressionExp(path, hash, loc, context) {
1111
1121
  if (existingHoistIndex > -1) {
1112
1122
  return compilerCore.createSimpleExpression(`_hoisted_${existingHoistIndex + 1}`, false, loc, 3 /* CAN_STRINGIFY */);
1113
1123
  }
1114
- return context.hoist(compilerCore.createSimpleExpression(hashExp, false, loc, 3 /* CAN_STRINGIFY */));
1124
+ return context.hoist(finalExp);
1115
1125
  }
1116
1126
  else {
1117
1127
  return compilerCore.createSimpleExpression(`''`, false, loc, 3 /* CAN_STRINGIFY */);
@@ -1153,35 +1163,41 @@ const transformSrcset = (node, context, options = defaultAssetUrlOptions) => {
1153
1163
  imageCandidates.splice(i, 1);
1154
1164
  }
1155
1165
  }
1156
- const hasQualifiedUrl = imageCandidates.some(({ url }) => {
1166
+ const shouldProcessUrl = (url) => {
1157
1167
  return (!isExternalUrl(url) &&
1158
1168
  !isDataUrl(url) &&
1159
1169
  (options.includeAbsolute || isRelativeUrl(url)));
1160
- });
1170
+ };
1161
1171
  // When srcset does not contain any qualified URLs, skip transforming
1162
- if (!hasQualifiedUrl) {
1172
+ if (!imageCandidates.some(({ url }) => shouldProcessUrl(url))) {
1163
1173
  return;
1164
1174
  }
1165
1175
  if (options.base) {
1166
1176
  const base = options.base;
1167
1177
  const set = [];
1168
- imageCandidates.forEach(({ url, descriptor }) => {
1178
+ let needImportTransform = false;
1179
+ imageCandidates.forEach(candidate => {
1180
+ let { url, descriptor } = candidate;
1169
1181
  descriptor = descriptor ? ` ${descriptor}` : ``;
1170
- if (isRelativeUrl(url)) {
1171
- set.push((path__default.posix || path__default).join(base, url) + descriptor);
1182
+ if (url[0] === '.') {
1183
+ candidate.url = (path__default.posix || path__default).join(base, url);
1184
+ set.push(candidate.url + descriptor);
1185
+ }
1186
+ else if (shouldProcessUrl(url)) {
1187
+ needImportTransform = true;
1172
1188
  }
1173
1189
  else {
1174
1190
  set.push(url + descriptor);
1175
1191
  }
1176
1192
  });
1177
- attr.value.content = set.join(', ');
1178
- return;
1193
+ if (!needImportTransform) {
1194
+ attr.value.content = set.join(', ');
1195
+ return;
1196
+ }
1179
1197
  }
1180
1198
  const compoundExpression = compilerCore.createCompoundExpression([], attr.loc);
1181
1199
  imageCandidates.forEach(({ url, descriptor }, index) => {
1182
- if (!isExternalUrl(url) &&
1183
- !isDataUrl(url) &&
1184
- (options.includeAbsolute || isRelativeUrl(url))) {
1200
+ if (shouldProcessUrl(url)) {
1185
1201
  const { path } = parseUrl(url);
1186
1202
  let exp;
1187
1203
  if (path) {
@@ -1211,13 +1227,16 @@ const transformSrcset = (node, context, options = defaultAssetUrlOptions) => {
1211
1227
  compoundExpression.children.push(` + ', ' + `);
1212
1228
  }
1213
1229
  });
1214
- const hoisted = context.hoist(compoundExpression);
1215
- hoisted.constType = 3 /* CAN_STRINGIFY */;
1230
+ let exp = compoundExpression;
1231
+ if (context.hoistStatic) {
1232
+ exp = context.hoist(compoundExpression);
1233
+ exp.constType = 3 /* CAN_STRINGIFY */;
1234
+ }
1216
1235
  node.props[index] = {
1217
1236
  type: 7 /* DIRECTIVE */,
1218
1237
  name: 'bind',
1219
1238
  arg: compilerCore.createSimpleExpression('srcset', true, attr.loc),
1220
- exp: hoisted,
1239
+ exp,
1221
1240
  modifiers: [],
1222
1241
  loc: attr.loc
1223
1242
  };
@@ -3072,7 +3091,7 @@ function preprocess({ source, filename, preprocessOptions }, preprocessor) {
3072
3091
  // have to be sync because they are applied via Node.js require hooks)
3073
3092
  let res = '';
3074
3093
  let err = null;
3075
- preprocessor.render(source, Object.assign({ filename }, preprocessOptions), (_err, _res) => {
3094
+ preprocessor.render(source, { filename, ...preprocessOptions }, (_err, _res) => {
3076
3095
  if (_err)
3077
3096
  err = _err;
3078
3097
  res = _res;
@@ -3090,7 +3109,10 @@ function compileTemplate(options) {
3090
3109
  : false;
3091
3110
  if (preprocessor) {
3092
3111
  try {
3093
- return doCompileTemplate(Object.assign(Object.assign({}, options), { source: preprocess(options, preprocessor) }));
3112
+ return doCompileTemplate({
3113
+ ...options,
3114
+ source: preprocess(options, preprocessor)
3115
+ });
3094
3116
  }
3095
3117
  catch (e) {
3096
3118
  return {
@@ -3141,9 +3163,23 @@ function doCompileTemplate({ filename, id, scoped, slotted, inMap, source, ssr =
3141
3163
  }
3142
3164
  const shortId = id.replace(/^data-v-/, '');
3143
3165
  const longId = `data-v-${shortId}`;
3144
- let { code, ast, preamble, map } = compiler.compile(source, Object.assign(Object.assign({ mode: 'module', prefixIdentifiers: true, hoistStatic: true, cacheHandlers: true, ssrCssVars: ssr && ssrCssVars && ssrCssVars.length
3145
- ? genCssVarsFromList(ssrCssVars, shortId, isProd)
3146
- : '', scopeId: scoped ? longId : undefined, slotted, sourceMap: true }, compilerOptions), { nodeTransforms: nodeTransforms.concat(compilerOptions.nodeTransforms || []), filename, onError: e => errors.push(e), onWarn: w => warnings.push(w) }));
3166
+ let { code, ast, preamble, map } = compiler.compile(source, {
3167
+ mode: 'module',
3168
+ prefixIdentifiers: true,
3169
+ hoistStatic: true,
3170
+ cacheHandlers: true,
3171
+ ssrCssVars: ssr && ssrCssVars && ssrCssVars.length
3172
+ ? genCssVarsFromList(ssrCssVars, shortId, isProd, true)
3173
+ : '',
3174
+ scopeId: scoped ? longId : undefined,
3175
+ slotted,
3176
+ sourceMap: true,
3177
+ ...compilerOptions,
3178
+ nodeTransforms: nodeTransforms.concat(compilerOptions.nodeTransforms || []),
3179
+ filename,
3180
+ onError: e => errors.push(e),
3181
+ onWarn: w => warnings.push(w)
3182
+ });
3147
3183
  // inMap should be the map produced by ./parse.ts which is a simple line-only
3148
3184
  // mapping. If it is present, we need to adjust the final map and errors to
3149
3185
  // reflect the original line numbers.
@@ -3228,7 +3264,7 @@ function patchErrors(errors, source, inMap) {
3228
3264
  }
3229
3265
 
3230
3266
  const defaultExportRE = /((?:^|\n|;)\s*)export(\s*)default/;
3231
- const namedDefaultExportRE = /((?:^|\n|;)\s*)export(.+)as(\s*)default/s;
3267
+ const namedDefaultExportRE = /((?:^|\n|;)\s*)export(.+)(?:as)?(\s*)default/s;
3232
3268
  const exportDefaultClassRE = /((?:^|\n|;)\s*)export\s+default\s+class\s+([\w$]+)/;
3233
3269
  /**
3234
3270
  * Utility for rewriting `export default` in a script block into a variable
@@ -3263,21 +3299,56 @@ function rewriteDefault(input, as, parserPlugins) {
3263
3299
  s.overwrite(node.start, node.declaration.start, `const ${as} = `);
3264
3300
  }
3265
3301
  if (node.type === 'ExportNamedDeclaration') {
3266
- node.specifiers.forEach(specifier => {
3302
+ for (const specifier of node.specifiers) {
3267
3303
  if (specifier.type === 'ExportSpecifier' &&
3268
3304
  specifier.exported.type === 'Identifier' &&
3269
3305
  specifier.exported.name === 'default') {
3270
- const end = specifier.end;
3271
- s.overwrite(specifier.start, input.charAt(end) === ',' ? end + 1 : end, ``);
3306
+ if (node.source) {
3307
+ if (specifier.local.name === 'default') {
3308
+ const end = specifierEnd(input, specifier.local.end, node.end);
3309
+ s.prepend(`import { default as __VUE_DEFAULT__ } from '${node.source.value}'\n`);
3310
+ s.overwrite(specifier.start, end, ``);
3311
+ s.append(`\nconst ${as} = __VUE_DEFAULT__`);
3312
+ continue;
3313
+ }
3314
+ else {
3315
+ const end = specifierEnd(input, specifier.exported.end, node.end);
3316
+ s.prepend(`import { ${input.slice(specifier.local.start, specifier.local.end)} } from '${node.source?.value}'\n`);
3317
+ s.overwrite(specifier.start, end, ``);
3318
+ s.append(`\nconst ${as} = ${specifier.local.name}`);
3319
+ continue;
3320
+ }
3321
+ }
3322
+ const end = specifierEnd(input, specifier.end, node.end);
3323
+ s.overwrite(specifier.start, end, ``);
3272
3324
  s.append(`\nconst ${as} = ${specifier.local.name}`);
3273
3325
  }
3274
- });
3326
+ }
3275
3327
  }
3276
3328
  });
3277
3329
  return s.toString();
3278
3330
  }
3279
3331
  function hasDefaultExport(input) {
3280
3332
  return defaultExportRE.test(input) || namedDefaultExportRE.test(input);
3333
+ }
3334
+ function specifierEnd(input, end, nodeEnd) {
3335
+ // export { default , foo } ...
3336
+ let hasCommas = false;
3337
+ let oldEnd = end;
3338
+ while (end < nodeEnd) {
3339
+ if (/\s/.test(input.charAt(end))) {
3340
+ end++;
3341
+ }
3342
+ else if (input.charAt(end) === ',') {
3343
+ end++;
3344
+ hasCommas = true;
3345
+ break;
3346
+ }
3347
+ else if (input.charAt(end) === '}') {
3348
+ break;
3349
+ }
3350
+ }
3351
+ return hasCommas ? end : oldEnd;
3281
3352
  }
3282
3353
 
3283
3354
  // Special compiler macros
@@ -3322,6 +3393,11 @@ function compileScript(sfc, options) {
3322
3393
  if (!isTS || scriptLang === 'tsx' || scriptSetupLang === 'tsx') {
3323
3394
  plugins.push('jsx');
3324
3395
  }
3396
+ else {
3397
+ // If don't match the case of adding jsx, should remove the jsx from the babelParserPlugins
3398
+ if (options.babelParserPlugins)
3399
+ options.babelParserPlugins = options.babelParserPlugins.filter(n => n !== 'jsx');
3400
+ }
3325
3401
  if (options.babelParserPlugins)
3326
3402
  plugins.push(...options.babelParserPlugins);
3327
3403
  if (isTS)
@@ -3368,9 +3444,13 @@ function compileScript(sfc, options) {
3368
3444
  content += genNormalScriptCssVarsCode(cssVars, bindings, scopeId, isProd);
3369
3445
  content += `\nexport default ${DEFAULT_VAR}`;
3370
3446
  }
3371
- return Object.assign(Object.assign({}, script), { content,
3447
+ return {
3448
+ ...script,
3449
+ content,
3372
3450
  map,
3373
- bindings, scriptAst: scriptAst.body });
3451
+ bindings,
3452
+ scriptAst: scriptAst.body
3453
+ };
3374
3454
  }
3375
3455
  catch (e) {
3376
3456
  // silently fallback if parse fails since user may be using custom
@@ -3397,6 +3477,8 @@ function compileScript(sfc, options) {
3397
3477
  let hasDefinePropsCall = false;
3398
3478
  let hasDefineEmitCall = false;
3399
3479
  let hasDefineExposeCall = false;
3480
+ let hasDefaultExportName = false;
3481
+ let hasDefaultExportRender = false;
3400
3482
  let propsRuntimeDecl;
3401
3483
  let propsRuntimeDefaults;
3402
3484
  let propsDestructureDecl;
@@ -3439,12 +3521,18 @@ function compileScript(sfc, options) {
3439
3521
  function error(msg, node, end = node.end + startOffset) {
3440
3522
  throw new Error(`[@vue/compiler-sfc] ${msg}\n\n${sfc.filename}\n${shared.generateCodeFrame(source, node.start + startOffset, end)}`);
3441
3523
  }
3442
- function registerUserImport(source, local, imported, isType, isFromSetup) {
3524
+ function registerUserImport(source, local, imported, isType, isFromSetup, needTemplateUsageCheck) {
3443
3525
  if (source === 'vue' && imported) {
3444
3526
  userImportAlias[imported] = local;
3445
3527
  }
3446
- let isUsedInTemplate = true;
3447
- if (isTS && sfc.template && !sfc.template.src && !sfc.template.lang) {
3528
+ // template usage check is only needed in non-inline mode, so we can skip
3529
+ // the work if inlineTemplate is true.
3530
+ let isUsedInTemplate = needTemplateUsageCheck;
3531
+ if (needTemplateUsageCheck &&
3532
+ isTS &&
3533
+ sfc.template &&
3534
+ !sfc.template.src &&
3535
+ !sfc.template.lang) {
3448
3536
  isUsedInTemplate = isImportUsed(local, sfc);
3449
3537
  }
3450
3538
  userImports[local] = {
@@ -3486,7 +3574,9 @@ function compileScript(sfc, options) {
3486
3574
  if (prop.computed) {
3487
3575
  error(`${DEFINE_PROPS}() destructure cannot use computed key.`, prop.key);
3488
3576
  }
3489
- const propKey = prop.key.name;
3577
+ const propKey = prop.key.type === 'StringLiteral'
3578
+ ? prop.key.value
3579
+ : prop.key.name;
3490
3580
  if (prop.value.type === 'AssignmentPattern') {
3491
3581
  // default value { foo = 123 }
3492
3582
  const { left, right } = prop.value;
@@ -3715,7 +3805,7 @@ function compileScript(sfc, options) {
3715
3805
  if (destructured && destructured.default) {
3716
3806
  const value = scriptSetup.content.slice(destructured.default.start, destructured.default.end);
3717
3807
  const isLiteral = destructured.default.type.endsWith('Literal');
3718
- return isLiteral ? value : `() => ${value}`;
3808
+ return isLiteral ? value : `() => (${value})`;
3719
3809
  }
3720
3810
  }
3721
3811
  function genSetupPropsType(node) {
@@ -3763,12 +3853,42 @@ function compileScript(sfc, options) {
3763
3853
  const imported = specifier.type === 'ImportSpecifier' &&
3764
3854
  specifier.imported.type === 'Identifier' &&
3765
3855
  specifier.imported.name;
3766
- registerUserImport(node.source.value, specifier.local.name, imported, node.importKind === 'type', false);
3856
+ registerUserImport(node.source.value, specifier.local.name, imported, node.importKind === 'type' ||
3857
+ (specifier.type === 'ImportSpecifier' &&
3858
+ specifier.importKind === 'type'), false, !options.inlineTemplate);
3767
3859
  }
3768
3860
  }
3769
3861
  else if (node.type === 'ExportDefaultDeclaration') {
3770
3862
  // export default
3771
3863
  defaultExport = node;
3864
+ // check if user has manually specified `name` or 'render` option in
3865
+ // export default
3866
+ // if has name, skip name inference
3867
+ // if has render and no template, generate return object instead of
3868
+ // empty render function (#4980)
3869
+ let optionProperties;
3870
+ if (defaultExport.declaration.type === 'ObjectExpression') {
3871
+ optionProperties = defaultExport.declaration.properties;
3872
+ }
3873
+ else if (defaultExport.declaration.type === 'CallExpression' &&
3874
+ defaultExport.declaration.arguments[0].type === 'ObjectExpression') {
3875
+ optionProperties = defaultExport.declaration.arguments[0].properties;
3876
+ }
3877
+ if (optionProperties) {
3878
+ for (const s of optionProperties) {
3879
+ if (s.type === 'ObjectProperty' &&
3880
+ s.key.type === 'Identifier' &&
3881
+ s.key.name === 'name') {
3882
+ hasDefaultExportName = true;
3883
+ }
3884
+ if ((s.type === 'ObjectMethod' || s.type === 'ObjectProperty') &&
3885
+ s.key.type === 'Identifier' &&
3886
+ s.key.name === 'render') {
3887
+ // TODO warn when we provide a better way to do it?
3888
+ hasDefaultExportRender = true;
3889
+ }
3890
+ }
3891
+ }
3772
3892
  // export default { ... } --> const __default__ = { ... }
3773
3893
  const start = node.start + scriptStartOffset;
3774
3894
  const end = node.declaration.start + scriptStartOffset;
@@ -3821,6 +3941,10 @@ function compileScript(sfc, options) {
3821
3941
  // we need to move the block up so that `const __default__` is
3822
3942
  // declared before being used in the actual component definition
3823
3943
  if (scriptStartOffset > startOffset) {
3944
+ // if content doesn't end with newline, add one
3945
+ if (!/\n$/.test(script.content.trim())) {
3946
+ s.appendLeft(scriptEndOffset, `\n`);
3947
+ }
3824
3948
  s.move(scriptStartOffset, scriptEndOffset, 0);
3825
3949
  }
3826
3950
  }
@@ -3875,9 +3999,12 @@ function compileScript(sfc, options) {
3875
3999
  for (let i = 0; i < node.specifiers.length; i++) {
3876
4000
  const specifier = node.specifiers[i];
3877
4001
  const local = specifier.local.name;
3878
- const imported = specifier.type === 'ImportSpecifier' &&
4002
+ let imported = specifier.type === 'ImportSpecifier' &&
3879
4003
  specifier.imported.type === 'Identifier' &&
3880
4004
  specifier.imported.name;
4005
+ if (specifier.type === 'ImportNamespaceSpecifier') {
4006
+ imported = '*';
4007
+ }
3881
4008
  const source = node.source.value;
3882
4009
  const existing = userImports[local];
3883
4010
  if (source === 'vue' &&
@@ -3897,7 +4024,9 @@ function compileScript(sfc, options) {
3897
4024
  }
3898
4025
  }
3899
4026
  else {
3900
- registerUserImport(source, local, imported, node.importKind === 'type', true);
4027
+ registerUserImport(source, local, imported, node.importKind === 'type' ||
4028
+ (specifier.type === 'ImportSpecifier' &&
4029
+ specifier.importKind === 'type'), true, !options.inlineTemplate);
3901
4030
  }
3902
4031
  }
3903
4032
  if (node.specifiers.length && removed === node.specifiers.length) {
@@ -3960,18 +4089,33 @@ function compileScript(sfc, options) {
3960
4089
  // await
3961
4090
  if ((node.type === 'VariableDeclaration' && !node.declare) ||
3962
4091
  node.type.endsWith('Statement')) {
4092
+ const scope = [scriptSetupAst.body];
3963
4093
  estreeWalker.walk(node, {
3964
4094
  enter(child, parent) {
3965
4095
  if (CompilerDOM.isFunctionType(child)) {
3966
4096
  this.skip();
3967
4097
  }
4098
+ if (child.type === 'BlockStatement') {
4099
+ scope.push(child.body);
4100
+ }
3968
4101
  if (child.type === 'AwaitExpression') {
3969
4102
  hasAwait = true;
3970
- const needsSemi = scriptSetupAst.body.some(n => {
3971
- return n.type === 'ExpressionStatement' && n.start === child.start;
4103
+ // if the await expression is an expression statement and
4104
+ // - is in the root scope
4105
+ // - or is not the first statement in a nested block scope
4106
+ // then it needs a semicolon before the generated code.
4107
+ const currentScope = scope[scope.length - 1];
4108
+ const needsSemi = currentScope.some((n, i) => {
4109
+ return ((scope.length === 1 || i > 0) &&
4110
+ n.type === 'ExpressionStatement' &&
4111
+ n.start === child.start);
3972
4112
  });
3973
4113
  processAwait(child, needsSemi, parent.type === 'ExpressionStatement');
3974
4114
  }
4115
+ },
4116
+ exit(node) {
4117
+ if (node.type === 'BlockStatement')
4118
+ scope.pop();
3975
4119
  }
3976
4120
  });
3977
4121
  }
@@ -4020,7 +4164,7 @@ function compileScript(sfc, options) {
4020
4164
  checkInvalidScopeReference(propsRuntimeDecl, DEFINE_PROPS);
4021
4165
  checkInvalidScopeReference(propsRuntimeDefaults, DEFINE_PROPS);
4022
4166
  checkInvalidScopeReference(propsDestructureDecl, DEFINE_PROPS);
4023
- checkInvalidScopeReference(emitsRuntimeDecl, DEFINE_PROPS);
4167
+ checkInvalidScopeReference(emitsRuntimeDecl, DEFINE_EMITS);
4024
4168
  // 6. remove non-script content
4025
4169
  if (script) {
4026
4170
  if (startOffset < scriptStartOffset) {
@@ -4056,7 +4200,8 @@ function compileScript(sfc, options) {
4056
4200
  // props aliases
4057
4201
  if (propsDestructureDecl) {
4058
4202
  if (propsDestructureRestId) {
4059
- bindingMetadata[propsDestructureRestId] = "setup-const" /* SETUP_CONST */;
4203
+ bindingMetadata[propsDestructureRestId] =
4204
+ "setup-reactive-const" /* SETUP_REACTIVE_CONST */;
4060
4205
  }
4061
4206
  for (const key in propsDestructuredBindings) {
4062
4207
  const { local } = propsDestructuredBindings[key];
@@ -4071,7 +4216,9 @@ function compileScript(sfc, options) {
4071
4216
  if (isType)
4072
4217
  continue;
4073
4218
  bindingMetadata[key] =
4074
- (imported === 'default' && source.endsWith('.vue')) || source === 'vue'
4219
+ imported === '*' ||
4220
+ (imported === 'default' && source.endsWith('.vue')) ||
4221
+ source === 'vue'
4075
4222
  ? "setup-const" /* SETUP_CONST */
4076
4223
  : "setup-maybe-ref" /* SETUP_MAYBE_REF */;
4077
4224
  }
@@ -4088,7 +4235,9 @@ function compileScript(sfc, options) {
4088
4235
  }
4089
4236
  }
4090
4237
  // 8. inject `useCssVars` calls
4091
- if (cssVars.length) {
4238
+ if (cssVars.length &&
4239
+ // no need to do this when targeting SSR
4240
+ !(options.inlineTemplate && options.templateOptions?.ssr)) {
4092
4241
  helperImports.add(CSS_VARS_HELPER);
4093
4242
  helperImports.add('unref');
4094
4243
  s.prependRight(startOffset, `\n${genCssVarsCode(cssVars, bindingMetadata, scopeId, isProd)}\n`);
@@ -4127,16 +4276,45 @@ function compileScript(sfc, options) {
4127
4276
  }
4128
4277
  // 10. generate return statement
4129
4278
  let returned;
4130
- if (options.inlineTemplate) {
4279
+ if (!options.inlineTemplate || (!sfc.template && hasDefaultExportRender)) {
4280
+ // non-inline mode, or has manual render in normal <script>
4281
+ // return bindings from script and script setup
4282
+ const allBindings = {
4283
+ ...scriptBindings,
4284
+ ...setupBindings
4285
+ };
4286
+ for (const key in userImports) {
4287
+ if (!userImports[key].isType && userImports[key].isUsedInTemplate) {
4288
+ allBindings[key] = true;
4289
+ }
4290
+ }
4291
+ returned = `{ ${Object.keys(allBindings).join(', ')} }`;
4292
+ }
4293
+ else {
4294
+ // inline mode
4131
4295
  if (sfc.template && !sfc.template.src) {
4132
4296
  if (options.templateOptions && options.templateOptions.ssr) {
4133
4297
  hasInlinedSsrRenderFn = true;
4134
4298
  }
4135
4299
  // inline render function mode - we are going to compile the template and
4136
4300
  // inline it right here
4137
- const { code, ast, preamble, tips, errors } = compileTemplate(Object.assign(Object.assign({ filename, source: sfc.template.content, inMap: sfc.template.map }, options.templateOptions), { id: scopeId, scoped: sfc.styles.some(s => s.scoped), isProd: options.isProd, ssrCssVars: sfc.cssVars, compilerOptions: Object.assign(Object.assign({}, (options.templateOptions &&
4138
- options.templateOptions.compilerOptions)), { inline: true, isTS,
4139
- bindingMetadata }) }));
4301
+ const { code, ast, preamble, tips, errors } = compileTemplate({
4302
+ filename,
4303
+ source: sfc.template.content,
4304
+ inMap: sfc.template.map,
4305
+ ...options.templateOptions,
4306
+ id: scopeId,
4307
+ scoped: sfc.styles.some(s => s.scoped),
4308
+ isProd: options.isProd,
4309
+ ssrCssVars: sfc.cssVars,
4310
+ compilerOptions: {
4311
+ ...(options.templateOptions &&
4312
+ options.templateOptions.compilerOptions),
4313
+ inline: true,
4314
+ isTS,
4315
+ bindingMetadata
4316
+ }
4317
+ });
4140
4318
  if (tips.length) {
4141
4319
  tips.forEach(warnOnce);
4142
4320
  }
@@ -4170,16 +4348,6 @@ function compileScript(sfc, options) {
4170
4348
  returned = `() => {}`;
4171
4349
  }
4172
4350
  }
4173
- else {
4174
- // return bindings from script and script setup
4175
- const allBindings = Object.assign(Object.assign({}, scriptBindings), setupBindings);
4176
- for (const key in userImports) {
4177
- if (!userImports[key].isType && userImports[key].isUsedInTemplate) {
4178
- allBindings[key] = true;
4179
- }
4180
- }
4181
- returned = `{ ${Object.keys(allBindings).join(', ')} }`;
4182
- }
4183
4351
  if (!options.inlineTemplate && !false) {
4184
4352
  // in non-inline mode, the `__isScriptSetup: true` flag is used by
4185
4353
  // componentPublicInstance proxy to allow properties that start with $ or _
@@ -4193,6 +4361,12 @@ function compileScript(sfc, options) {
4193
4361
  }
4194
4362
  // 11. finalize default export
4195
4363
  let runtimeOptions = ``;
4364
+ if (!hasDefaultExportName && filename && filename !== DEFAULT_FILENAME) {
4365
+ const match = filename.match(/([^/\\]+)\.\w+$/);
4366
+ if (match) {
4367
+ runtimeOptions += `\n name: '${match[1]}',`;
4368
+ }
4369
+ }
4196
4370
  if (hasInlinedSsrRenderFn) {
4197
4371
  runtimeOptions += `\n __ssrInlineRender: true,`;
4198
4372
  }
@@ -4259,13 +4433,21 @@ function compileScript(sfc, options) {
4259
4433
  .join(', ')} } from 'vue'\n`);
4260
4434
  }
4261
4435
  s.trim();
4262
- return Object.assign(Object.assign({}, scriptSetup), { bindings: bindingMetadata, imports: userImports, content: s.toString(), map: genSourceMap
4436
+ return {
4437
+ ...scriptSetup,
4438
+ bindings: bindingMetadata,
4439
+ imports: userImports,
4440
+ content: s.toString(),
4441
+ map: genSourceMap
4263
4442
  ? s.generateMap({
4264
4443
  source: filename,
4265
4444
  hires: true,
4266
4445
  includeContent: true
4267
4446
  })
4268
- : undefined, scriptAst: scriptAst === null || scriptAst === void 0 ? void 0 : scriptAst.body, scriptSetupAst: scriptSetupAst === null || scriptSetupAst === void 0 ? void 0 : scriptSetupAst.body });
4447
+ : undefined,
4448
+ scriptAst: scriptAst?.body,
4449
+ scriptSetupAst: scriptSetupAst?.body
4450
+ };
4269
4451
  }
4270
4452
  function registerBinding(bindings, node, type) {
4271
4453
  bindings[node.name] = type;
@@ -4282,14 +4464,18 @@ function walkDeclaration(node, bindings, userImportAlias) {
4282
4464
  const userReactiveBinding = userImportAlias['reactive'] || 'reactive';
4283
4465
  if (isCallOf(init, userReactiveBinding)) {
4284
4466
  // treat reactive() calls as let since it's meant to be mutable
4285
- bindingType = "setup-let" /* SETUP_LET */;
4467
+ bindingType = isConst
4468
+ ? "setup-reactive-const" /* SETUP_REACTIVE_CONST */
4469
+ : "setup-let" /* SETUP_LET */;
4286
4470
  }
4287
4471
  else if (
4288
4472
  // if a declaration is a const literal, we can mark it so that
4289
4473
  // the generated render fn code doesn't need to unref() it
4290
4474
  isDefineCall ||
4291
4475
  (isConst && canNeverBeRef(init, userReactiveBinding))) {
4292
- bindingType = "setup-const" /* SETUP_CONST */;
4476
+ bindingType = isCallOf(init, DEFINE_PROPS)
4477
+ ? "setup-reactive-const" /* SETUP_REACTIVE_CONST */
4478
+ : "setup-const" /* SETUP_CONST */;
4293
4479
  }
4294
4480
  else if (isConst) {
4295
4481
  if (isCallOf(init, userImportAlias['ref'] || 'ref')) {
@@ -4465,6 +4651,7 @@ function inferRuntimeType(node, declaredTypes) {
4465
4651
  case 'WeakSet':
4466
4652
  case 'WeakMap':
4467
4653
  case 'Date':
4654
+ case 'Promise':
4468
4655
  return [node.typeName.name];
4469
4656
  case 'Record':
4470
4657
  case 'Partial':
@@ -4702,13 +4889,13 @@ function resolveTemplateUsageCheckString(sfc) {
4702
4889
  code += `,v${shared.capitalize(shared.camelize(prop.name))}`;
4703
4890
  }
4704
4891
  if (prop.exp) {
4705
- code += `,${stripStrings(prop.exp.content)}`;
4892
+ code += `,${processExp(prop.exp.content)}`;
4706
4893
  }
4707
4894
  }
4708
4895
  }
4709
4896
  }
4710
4897
  else if (node.type === 5 /* INTERPOLATION */) {
4711
- code += `,${stripStrings(node.content.content)}`;
4898
+ code += `,${processExp(node.content.content)}`;
4712
4899
  }
4713
4900
  }
4714
4901
  ]
@@ -4717,6 +4904,18 @@ function resolveTemplateUsageCheckString(sfc) {
4717
4904
  templateUsageCheckCache.set(content, code);
4718
4905
  return code;
4719
4906
  }
4907
+ function processExp(exp) {
4908
+ if (/ as \w|<.*>/.test(exp)) {
4909
+ let ret = '';
4910
+ // has potential type cast or generic arguments that uses types
4911
+ const ast = parser$2.parseExpression(exp, { plugins: ['typescript'] });
4912
+ CompilerDOM.walkIdentifiers(ast, node => {
4913
+ ret += `,` + node.name;
4914
+ });
4915
+ return ret;
4916
+ }
4917
+ return stripStrings(exp);
4918
+ }
4720
4919
  function stripStrings(exp) {
4721
4920
  return exp
4722
4921
  .replace(/'[^']*'|"[^"]*"/g, '')
@@ -4757,8 +4956,9 @@ function hmrShouldReload(prevImports, next) {
4757
4956
  return false;
4758
4957
  }
4759
4958
 
4959
+ const DEFAULT_FILENAME = 'anonymous.vue';
4760
4960
  const sourceToSFC = createCache();
4761
- function parse(source, { sourceMap = true, filename = 'anonymous.vue', sourceRoot = '', pad = false, ignoreEmpty = true, compiler = CompilerDOM__namespace } = {}) {
4961
+ function parse(source, { sourceMap = true, filename = DEFAULT_FILENAME, sourceRoot = '', pad = false, ignoreEmpty = true, compiler = CompilerDOM__namespace } = {}) {
4762
4962
  const sourceKey = source + sourceMap + filename + sourceRoot + pad + compiler.parse;
4763
4963
  const cache = sourceToSFC.get(sourceKey);
4764
4964
  if (cache) {
@@ -4917,7 +5117,7 @@ function createBlock(node, source, pad) {
4917
5117
  offset: start.offset + offset
4918
5118
  };
4919
5119
  }
4920
- end = Object.assign({}, start);
5120
+ end = { ...start };
4921
5121
  }
4922
5122
  const loc = {
4923
5123
  source: content,
@@ -9387,7 +9587,13 @@ function merge$1(oldMap, newMap) {
9387
9587
  // .scss/.sass processor
9388
9588
  const scss = (source, map, options, load = require) => {
9389
9589
  const nodeSass = load('sass');
9390
- const finalOptions = Object.assign(Object.assign({}, options), { data: getSource(source, options.filename, options.additionalData), file: options.filename, outFile: options.filename, sourceMap: !!map });
9590
+ const finalOptions = {
9591
+ ...options,
9592
+ data: getSource(source, options.filename, options.additionalData),
9593
+ file: options.filename,
9594
+ outFile: options.filename,
9595
+ sourceMap: !!map
9596
+ };
9391
9597
  try {
9392
9598
  const result = nodeSass.renderSync(finalOptions);
9393
9599
  const dependencies = result.stats.includedFiles;
@@ -9405,13 +9611,16 @@ const scss = (source, map, options, load = require) => {
9405
9611
  return { code: '', errors: [e], dependencies: [] };
9406
9612
  }
9407
9613
  };
9408
- const sass = (source, map, options, load) => scss(source, map, Object.assign(Object.assign({}, options), { indentedSyntax: true }), load);
9614
+ const sass = (source, map, options, load) => scss(source, map, {
9615
+ ...options,
9616
+ indentedSyntax: true
9617
+ }, load);
9409
9618
  // .less
9410
9619
  const less = (source, map, options, load = require) => {
9411
9620
  const nodeLess = load('less');
9412
9621
  let result;
9413
9622
  let error = null;
9414
- nodeLess.render(getSource(source, options.filename, options.additionalData), Object.assign(Object.assign({}, options), { syncImport: true }), (err, output) => {
9623
+ nodeLess.render(getSource(source, options.filename, options.additionalData), { ...options, syncImport: true }, (err, output) => {
9415
9624
  error = err;
9416
9625
  result = output;
9417
9626
  });
@@ -17178,10 +17387,16 @@ var postcss$3 = true;
17178
17387
  build.postcss = postcss$3;
17179
17388
 
17180
17389
  function compileStyle(options) {
17181
- return doCompileStyle(Object.assign(Object.assign({}, options), { isAsync: false }));
17390
+ return doCompileStyle({
17391
+ ...options,
17392
+ isAsync: false
17393
+ });
17182
17394
  }
17183
17395
  function compileStyleAsync(options) {
17184
- return doCompileStyle(Object.assign(Object.assign({}, options), { isAsync: true }));
17396
+ return doCompileStyle({
17397
+ ...options,
17398
+ isAsync: true
17399
+ });
17185
17400
  }
17186
17401
  function doCompileStyle(options) {
17187
17402
  const { filename, id, scoped = false, trim = true, isProd = false, modules = false, modulesOptions = {}, preprocessLang, postcssOptions, postcssPlugins } = options;
@@ -17206,11 +17421,18 @@ function doCompileStyle(options) {
17206
17421
  if (!options.isAsync) {
17207
17422
  throw new Error('[@vue/compiler-sfc] `modules` option can only be used with compileStyleAsync().');
17208
17423
  }
17209
- plugins.push(build(Object.assign(Object.assign({}, modulesOptions), { getJSON: (_cssFileName, json) => {
17424
+ plugins.push(build({
17425
+ ...modulesOptions,
17426
+ getJSON: (_cssFileName, json) => {
17210
17427
  cssModules = json;
17211
- } })));
17428
+ }
17429
+ }));
17212
17430
  }
17213
- const postCSSOptions = Object.assign(Object.assign({}, postcssOptions), { to: filename, from: filename });
17431
+ const postCSSOptions = {
17432
+ ...postcssOptions,
17433
+ to: filename,
17434
+ from: filename
17435
+ };
17214
17436
  if (map) {
17215
17437
  postCSSOptions.map = {
17216
17438
  inline: false,
@@ -17276,7 +17498,10 @@ function doCompileStyle(options) {
17276
17498
  };
17277
17499
  }
17278
17500
  function preprocess$1(options, preprocessor) {
17279
- return preprocessor(options.source, options.inMap || options.map, Object.assign({ filename: options.filename }, options.preprocessOptions), options.preprocessCustomRequire);
17501
+ return preprocessor(options.source, options.inMap || options.map, {
17502
+ filename: options.filename,
17503
+ ...options.preprocessOptions
17504
+ }, options.preprocessCustomRequire);
17280
17505
  }
17281
17506
 
17282
17507
  // API