@vue/compiler-ssr 3.2.26 → 3.2.30

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.
@@ -22,6 +22,7 @@ const SSR_RENDER_DYNAMIC_MODEL = Symbol(`ssrRenderDynamicModel`);
22
22
  const SSR_GET_DYNAMIC_MODEL_PROPS = Symbol(`ssrGetDynamicModelProps`);
23
23
  const SSR_RENDER_TELEPORT = Symbol(`ssrRenderTeleport`);
24
24
  const SSR_RENDER_SUSPENSE = Symbol(`ssrRenderSuspense`);
25
+ const SSR_GET_DIRECTIVE_PROPS = Symbol(`ssrGetDirectiveProps`);
25
26
  const ssrHelpers = {
26
27
  [SSR_INTERPOLATE]: `ssrInterpolate`,
27
28
  [SSR_RENDER_VNODE]: `ssrRenderVNode`,
@@ -39,7 +40,8 @@ const ssrHelpers = {
39
40
  [SSR_RENDER_DYNAMIC_MODEL]: `ssrRenderDynamicModel`,
40
41
  [SSR_GET_DYNAMIC_MODEL_PROPS]: `ssrGetDynamicModelProps`,
41
42
  [SSR_RENDER_TELEPORT]: `ssrRenderTeleport`,
42
- [SSR_RENDER_SUSPENSE]: `ssrRenderSuspense`
43
+ [SSR_RENDER_SUSPENSE]: `ssrRenderSuspense`,
44
+ [SSR_GET_DIRECTIVE_PROPS]: `ssrGetDirectiveProps`
43
45
  };
44
46
  // Note: these are helpers imported from @vue/server-renderer
45
47
  // make sure the names match!
@@ -145,17 +147,16 @@ function createSSRCompilerError(code, loc) {
145
147
  return compilerDom.createCompilerError(code, loc, SSRErrorMessages);
146
148
  }
147
149
  const SSRErrorMessages = {
148
- [61 /* X_SSR_CUSTOM_DIRECTIVE_NO_TRANSFORM */]: `Custom directive is missing corresponding SSR transform and will be ignored.`,
149
- [62 /* X_SSR_UNSAFE_ATTR_NAME */]: `Unsafe attribute name for SSR.`,
150
- [63 /* X_SSR_NO_TELEPORT_TARGET */]: `Missing the 'to' prop on teleport element.`,
151
- [64 /* X_SSR_INVALID_AST_NODE */]: `Invalid AST node during SSR transform.`
150
+ [61 /* X_SSR_UNSAFE_ATTR_NAME */]: `Unsafe attribute name for SSR.`,
151
+ [62 /* X_SSR_NO_TELEPORT_TARGET */]: `Missing the 'to' prop on teleport element.`,
152
+ [63 /* X_SSR_INVALID_AST_NODE */]: `Invalid AST node during SSR transform.`
152
153
  };
153
154
 
154
155
  // Note: this is a 2nd-pass codegen transform.
155
156
  function ssrProcessTeleport(node, context) {
156
157
  const targetProp = compilerDom.findProp(node, 'to');
157
158
  if (!targetProp) {
158
- context.onError(createSSRCompilerError(63 /* X_SSR_NO_TELEPORT_TARGET */, node.loc));
159
+ context.onError(createSSRCompilerError(62 /* X_SSR_NO_TELEPORT_TARGET */, node.loc));
159
160
  return;
160
161
  }
161
162
  let target;
@@ -167,7 +168,7 @@ function ssrProcessTeleport(node, context) {
167
168
  target = targetProp.exp;
168
169
  }
169
170
  if (!target) {
170
- context.onError(createSSRCompilerError(63 /* X_SSR_NO_TELEPORT_TARGET */, targetProp.loc));
171
+ context.onError(createSSRCompilerError(62 /* X_SSR_NO_TELEPORT_TARGET */, targetProp.loc));
171
172
  return;
172
173
  }
173
174
  const disabledProp = compilerDom.findProp(node, 'disabled', false, true /* allow empty */);
@@ -266,224 +267,6 @@ function ssrProcessTransitionGroup(node, context) {
266
267
  }
267
268
  }
268
269
 
269
- // We need to construct the slot functions in the 1st pass to ensure proper
270
- // scope tracking, but the children of each slot cannot be processed until
271
- // the 2nd pass, so we store the WIP slot functions in a weakmap during the 1st
272
- // pass and complete them in the 2nd pass.
273
- const wipMap$1 = new WeakMap();
274
- const componentTypeMap = new WeakMap();
275
- // ssr component transform is done in two phases:
276
- // In phase 1. we use `buildSlot` to analyze the children of the component into
277
- // WIP slot functions (it must be done in phase 1 because `buildSlot` relies on
278
- // the core transform context).
279
- // In phase 2. we convert the WIP slots from phase 1 into ssr-specific codegen
280
- // nodes.
281
- const ssrTransformComponent = (node, context) => {
282
- if (node.type !== 1 /* ELEMENT */ ||
283
- node.tagType !== 1 /* COMPONENT */) {
284
- return;
285
- }
286
- const component = compilerDom.resolveComponentType(node, context, true /* ssr */);
287
- componentTypeMap.set(node, component);
288
- if (shared.isSymbol(component)) {
289
- if (component === compilerDom.SUSPENSE) {
290
- return ssrTransformSuspense(node, context);
291
- }
292
- return; // built-in component: fallthrough
293
- }
294
- // Build the fallback vnode-based branch for the component's slots.
295
- // We need to clone the node into a fresh copy and use the buildSlots' logic
296
- // to get access to the children of each slot. We then compile them with
297
- // a child transform pipeline using vnode-based transforms (instead of ssr-
298
- // based ones), and save the result branch (a ReturnStatement) in an array.
299
- // The branch is retrieved when processing slots again in ssr mode.
300
- const vnodeBranches = [];
301
- const clonedNode = clone(node);
302
- return function ssrPostTransformComponent() {
303
- // Using the cloned node, build the normal VNode-based branches (for
304
- // fallback in case the child is render-fn based). Store them in an array
305
- // for later use.
306
- if (clonedNode.children.length) {
307
- compilerDom.buildSlots(clonedNode, context, (props, children) => {
308
- vnodeBranches.push(createVNodeSlotBranch(props, children, context));
309
- return compilerDom.createFunctionExpression(undefined);
310
- });
311
- }
312
- const props = node.props.length > 0
313
- ? // note we are not passing ssr: true here because for components, v-on
314
- // handlers should still be passed
315
- compilerDom.buildProps(node, context).props || `null`
316
- : `null`;
317
- const wipEntries = [];
318
- wipMap$1.set(node, wipEntries);
319
- const buildSSRSlotFn = (props, children, loc) => {
320
- const fn = compilerDom.createFunctionExpression([props || `_`, `_push`, `_parent`, `_scopeId`], undefined, // no return, assign body later
321
- true, // newline
322
- true, // isSlot
323
- loc);
324
- wipEntries.push({
325
- fn,
326
- children,
327
- // also collect the corresponding vnode branch built earlier
328
- vnodeBranch: vnodeBranches[wipEntries.length]
329
- });
330
- return fn;
331
- };
332
- const slots = node.children.length
333
- ? compilerDom.buildSlots(node, context, buildSSRSlotFn).slots
334
- : `null`;
335
- if (typeof component !== 'string') {
336
- // dynamic component that resolved to a `resolveDynamicComponent` call
337
- // expression - since the resolved result may be a plain element (string)
338
- // or a VNode, handle it with `renderVNode`.
339
- node.ssrCodegenNode = compilerDom.createCallExpression(context.helper(SSR_RENDER_VNODE), [
340
- `_push`,
341
- compilerDom.createCallExpression(context.helper(compilerDom.CREATE_VNODE), [
342
- component,
343
- props,
344
- slots
345
- ]),
346
- `_parent`
347
- ]);
348
- }
349
- else {
350
- node.ssrCodegenNode = compilerDom.createCallExpression(context.helper(SSR_RENDER_COMPONENT), [component, props, slots, `_parent`]);
351
- }
352
- };
353
- };
354
- function ssrProcessComponent(node, context) {
355
- const component = componentTypeMap.get(node);
356
- if (!node.ssrCodegenNode) {
357
- // this is a built-in component that fell-through.
358
- if (component === compilerDom.TELEPORT) {
359
- return ssrProcessTeleport(node, context);
360
- }
361
- else if (component === compilerDom.SUSPENSE) {
362
- return ssrProcessSuspense(node, context);
363
- }
364
- else if (component === compilerDom.TRANSITION_GROUP) {
365
- return ssrProcessTransitionGroup(node, context);
366
- }
367
- else {
368
- // real fall-through: Transition / KeepAlive
369
- // just render its children.
370
- processChildren(node.children, context);
371
- }
372
- }
373
- else {
374
- // finish up slot function expressions from the 1st pass.
375
- const wipEntries = wipMap$1.get(node) || [];
376
- for (let i = 0; i < wipEntries.length; i++) {
377
- const { fn, children, vnodeBranch } = wipEntries[i];
378
- // For each slot, we generate two branches: one SSR-optimized branch and
379
- // one normal vnode-based branch. The branches are taken based on the
380
- // presence of the 2nd `_push` argument (which is only present if the slot
381
- // is called by `_ssrRenderSlot`.
382
- fn.body = compilerDom.createIfStatement(compilerDom.createSimpleExpression(`_push`, false), processChildrenAsStatement(children, context, false, true /* withSlotScopeId */), vnodeBranch);
383
- }
384
- // component is inside a slot, inherit slot scope Id
385
- if (context.withSlotScopeId) {
386
- node.ssrCodegenNode.arguments.push(`_scopeId`);
387
- }
388
- if (typeof component === 'string') {
389
- // static component
390
- context.pushStatement(compilerDom.createCallExpression(`_push`, [node.ssrCodegenNode]));
391
- }
392
- else {
393
- // dynamic component (`resolveDynamicComponent` call)
394
- // the codegen node is a `renderVNode` call
395
- context.pushStatement(node.ssrCodegenNode);
396
- }
397
- }
398
- }
399
- const rawOptionsMap = new WeakMap();
400
- const [baseNodeTransforms, baseDirectiveTransforms] = compilerDom.getBaseTransformPreset(true);
401
- const vnodeNodeTransforms = [...baseNodeTransforms, ...compilerDom.DOMNodeTransforms];
402
- const vnodeDirectiveTransforms = Object.assign(Object.assign({}, baseDirectiveTransforms), compilerDom.DOMDirectiveTransforms);
403
- function createVNodeSlotBranch(props, children, parentContext) {
404
- // apply a sub-transform using vnode-based transforms.
405
- const rawOptions = rawOptionsMap.get(parentContext.root);
406
- const subOptions = Object.assign(Object.assign({}, rawOptions), {
407
- // overwrite with vnode-based transforms
408
- nodeTransforms: [
409
- ...vnodeNodeTransforms,
410
- ...(rawOptions.nodeTransforms || [])
411
- ], directiveTransforms: Object.assign(Object.assign({}, vnodeDirectiveTransforms), (rawOptions.directiveTransforms || {})) });
412
- // wrap the children with a wrapper template for proper children treatment.
413
- const wrapperNode = {
414
- type: 1 /* ELEMENT */,
415
- ns: 0 /* HTML */,
416
- tag: 'template',
417
- tagType: 3 /* TEMPLATE */,
418
- isSelfClosing: false,
419
- // important: provide v-slot="props" on the wrapper for proper
420
- // scope analysis
421
- props: [
422
- {
423
- type: 7 /* DIRECTIVE */,
424
- name: 'slot',
425
- exp: props,
426
- arg: undefined,
427
- modifiers: [],
428
- loc: compilerDom.locStub
429
- }
430
- ],
431
- children,
432
- loc: compilerDom.locStub,
433
- codegenNode: undefined
434
- };
435
- subTransform(wrapperNode, subOptions, parentContext);
436
- return compilerDom.createReturnStatement(children);
437
- }
438
- function subTransform(node, options, parentContext) {
439
- const childRoot = compilerDom.createRoot([node]);
440
- const childContext = compilerDom.createTransformContext(childRoot, options);
441
- // this sub transform is for vnode fallback branch so it should be handled
442
- // like normal render functions
443
- childContext.ssr = false;
444
- // inherit parent scope analysis state
445
- childContext.scopes = Object.assign({}, parentContext.scopes);
446
- childContext.identifiers = Object.assign({}, parentContext.identifiers);
447
- childContext.imports = parentContext.imports;
448
- // traverse
449
- compilerDom.traverseNode(childRoot, childContext);
450
- ['helpers', 'components', 'directives'].forEach(key => {
451
- childContext[key].forEach((value, helperKey) => {
452
- if (key === 'helpers') {
453
- const parentCount = parentContext.helpers.get(helperKey);
454
- if (parentCount === undefined) {
455
- parentContext.helpers.set(helperKey, value);
456
- }
457
- else {
458
- parentContext.helpers.set(helperKey, value + parentCount);
459
- }
460
- }
461
- else {
462
- parentContext[key].add(value);
463
- }
464
- });
465
- });
466
- // imports/hoists are not merged because:
467
- // - imports are only used for asset urls and should be consistent between
468
- // node/client branches
469
- // - hoists are not enabled for the client branch here
470
- }
471
- function clone(v) {
472
- if (shared.isArray(v)) {
473
- return v.map(clone);
474
- }
475
- else if (shared.isObject(v)) {
476
- const res = {};
477
- for (const key in v) {
478
- res[key] = clone(v[key]);
479
- }
480
- return res;
481
- }
482
- else {
483
- return v;
484
- }
485
- }
486
-
487
270
  // for directives with children overwrite (e.g. v-html & v-text), we need to
488
271
  // store the raw children so that they can be added in the 2nd pass.
489
272
  const rawChildrenMap = new WeakMap();
@@ -498,14 +281,17 @@ const ssrTransformElement = (node, context) => {
498
281
  const openTag = [`<${node.tag}`];
499
282
  // some tags need to be passed to runtime for special checks
500
283
  const needTagForRuntime = node.tag === 'textarea' || node.tag.indexOf('-') > 0;
501
- // v-bind="obj" or v-bind:[key] can potentially overwrite other static
502
- // attrs and can affect final rendering result, so when they are present
503
- // we need to bail out to full `renderAttrs`
284
+ // v-bind="obj", v-bind:[key] and custom directives can potentially
285
+ // overwrite other static attrs and can affect final rendering result,
286
+ // so when they are present we need to bail out to full `renderAttrs`
504
287
  const hasDynamicVBind = compilerDom.hasDynamicKeyVBind(node);
505
- if (hasDynamicVBind) {
506
- const { props } = compilerDom.buildProps(node, context, node.props, true /* ssr */);
507
- if (props) {
508
- const propsExp = compilerDom.createCallExpression(context.helper(SSR_RENDER_ATTRS), [props]);
288
+ const hasCustomDir = node.props.some(p => p.type === 7 /* DIRECTIVE */ && !shared.isBuiltInDirective(p.name));
289
+ const needMergeProps = hasDynamicVBind || hasCustomDir;
290
+ if (needMergeProps) {
291
+ const { props, directives } = compilerDom.buildProps(node, context, node.props, true /* ssr */);
292
+ if (props || directives.length) {
293
+ const mergedProps = buildSSRProps(props, directives, context);
294
+ const propsExp = compilerDom.createCallExpression(context.helper(SSR_RENDER_ATTRS), [mergedProps]);
509
295
  if (node.tag === 'textarea') {
510
296
  const existingText = node.children[0];
511
297
  // If interpolation, this is dynamic <textarea> content, potentially
@@ -517,7 +303,7 @@ const ssrTransformElement = (node, context) => {
517
303
  // it contains value (if yes, render is as children).
518
304
  const tempId = `_temp${context.temps++}`;
519
305
  propsExp.arguments = [
520
- compilerDom.createAssignmentExpression(compilerDom.createSimpleExpression(tempId, false), props)
306
+ compilerDom.createAssignmentExpression(compilerDom.createSimpleExpression(tempId, false), mergedProps)
521
307
  ];
522
308
  rawChildrenMap.set(node, compilerDom.createCallExpression(context.helper(SSR_INTERPOLATE), [
523
309
  compilerDom.createConditionalExpression(compilerDom.createSimpleExpression(`"value" in ${tempId}`, false), compilerDom.createSimpleExpression(`${tempId}.value`, false), compilerDom.createSimpleExpression(existingText ? existingText.content : ``, true), false)
@@ -535,7 +321,7 @@ const ssrTransformElement = (node, context) => {
535
321
  const tempExp = compilerDom.createSimpleExpression(tempId, false);
536
322
  propsExp.arguments = [
537
323
  compilerDom.createSequenceExpression([
538
- compilerDom.createAssignmentExpression(tempExp, props),
324
+ compilerDom.createAssignmentExpression(tempExp, mergedProps),
539
325
  compilerDom.createCallExpression(context.helper(compilerDom.MERGE_PROPS), [
540
326
  tempExp,
541
327
  compilerDom.createCallExpression(context.helper(SSR_GET_DYNAMIC_MODEL_PROPS), [
@@ -577,18 +363,14 @@ const ssrTransformElement = (node, context) => {
577
363
  context.onError(compilerDom.createCompilerError(40 /* X_V_SLOT_MISPLACED */, prop.loc));
578
364
  }
579
365
  else if (isTextareaWithValue(node, prop) && prop.exp) {
580
- if (!hasDynamicVBind) {
366
+ if (!needMergeProps) {
581
367
  node.children = [compilerDom.createInterpolation(prop.exp, prop.loc)];
582
368
  }
583
369
  }
584
- else {
370
+ else if (!needMergeProps) {
585
371
  // Directive transforms.
586
372
  const directiveTransform = context.directiveTransforms[prop.name];
587
- if (!directiveTransform) {
588
- // no corresponding ssr directive transform found.
589
- context.onError(createSSRCompilerError(61 /* X_SSR_CUSTOM_DIRECTIVE_NO_TRANSFORM */, prop.loc));
590
- }
591
- else if (!hasDynamicVBind) {
373
+ if (directiveTransform) {
592
374
  const { props, ssrTagParts } = directiveTransform(prop, node, context);
593
375
  if (ssrTagParts) {
594
376
  openTag.push(...ssrTagParts);
@@ -628,7 +410,7 @@ const ssrTransformElement = (node, context) => {
628
410
  ]));
629
411
  }
630
412
  else {
631
- context.onError(createSSRCompilerError(62 /* X_SSR_UNSAFE_ATTR_NAME */, key.loc));
413
+ context.onError(createSSRCompilerError(61 /* X_SSR_UNSAFE_ATTR_NAME */, key.loc));
632
414
  }
633
415
  }
634
416
  }
@@ -651,7 +433,7 @@ const ssrTransformElement = (node, context) => {
651
433
  if (node.tag === 'textarea' && prop.name === 'value' && prop.value) {
652
434
  rawChildrenMap.set(node, shared.escapeHtml(prop.value.content));
653
435
  }
654
- else if (!hasDynamicVBind) {
436
+ else if (!needMergeProps) {
655
437
  if (prop.name === 'key' || prop.name === 'ref') {
656
438
  continue;
657
439
  }
@@ -675,6 +457,30 @@ const ssrTransformElement = (node, context) => {
675
457
  node.ssrCodegenNode = compilerDom.createTemplateLiteral(openTag);
676
458
  };
677
459
  };
460
+ function buildSSRProps(props, directives, context) {
461
+ let mergePropsArgs = [];
462
+ if (props) {
463
+ if (props.type === 14 /* JS_CALL_EXPRESSION */) {
464
+ // already a mergeProps call
465
+ mergePropsArgs = props.arguments;
466
+ }
467
+ else {
468
+ mergePropsArgs.push(props);
469
+ }
470
+ }
471
+ if (directives.length) {
472
+ for (const dir of directives) {
473
+ context.directives.add(dir.name);
474
+ mergePropsArgs.push(compilerDom.createCallExpression(context.helper(SSR_GET_DIRECTIVE_PROPS), [
475
+ `_ctx`,
476
+ ...compilerDom.buildDirectiveArgs(dir, context).elements
477
+ ]));
478
+ }
479
+ }
480
+ return mergePropsArgs.length > 1
481
+ ? compilerDom.createCallExpression(context.helper(compilerDom.MERGE_PROPS), mergePropsArgs)
482
+ : mergePropsArgs[0];
483
+ }
678
484
  function isTrueFalseValue(prop) {
679
485
  if (prop.type === 7 /* DIRECTIVE */) {
680
486
  return (prop.name === 'bind' &&
@@ -735,6 +541,228 @@ function ssrProcessElement(node, context) {
735
541
  }
736
542
  }
737
543
 
544
+ // We need to construct the slot functions in the 1st pass to ensure proper
545
+ // scope tracking, but the children of each slot cannot be processed until
546
+ // the 2nd pass, so we store the WIP slot functions in a weakMap during the 1st
547
+ // pass and complete them in the 2nd pass.
548
+ const wipMap$1 = new WeakMap();
549
+ const componentTypeMap = new WeakMap();
550
+ // ssr component transform is done in two phases:
551
+ // In phase 1. we use `buildSlot` to analyze the children of the component into
552
+ // WIP slot functions (it must be done in phase 1 because `buildSlot` relies on
553
+ // the core transform context).
554
+ // In phase 2. we convert the WIP slots from phase 1 into ssr-specific codegen
555
+ // nodes.
556
+ const ssrTransformComponent = (node, context) => {
557
+ if (node.type !== 1 /* ELEMENT */ ||
558
+ node.tagType !== 1 /* COMPONENT */) {
559
+ return;
560
+ }
561
+ const component = compilerDom.resolveComponentType(node, context, true /* ssr */);
562
+ componentTypeMap.set(node, component);
563
+ if (shared.isSymbol(component)) {
564
+ if (component === compilerDom.SUSPENSE) {
565
+ return ssrTransformSuspense(node, context);
566
+ }
567
+ return; // built-in component: fallthrough
568
+ }
569
+ // Build the fallback vnode-based branch for the component's slots.
570
+ // We need to clone the node into a fresh copy and use the buildSlots' logic
571
+ // to get access to the children of each slot. We then compile them with
572
+ // a child transform pipeline using vnode-based transforms (instead of ssr-
573
+ // based ones), and save the result branch (a ReturnStatement) in an array.
574
+ // The branch is retrieved when processing slots again in ssr mode.
575
+ const vnodeBranches = [];
576
+ const clonedNode = clone(node);
577
+ return function ssrPostTransformComponent() {
578
+ // Using the cloned node, build the normal VNode-based branches (for
579
+ // fallback in case the child is render-fn based). Store them in an array
580
+ // for later use.
581
+ if (clonedNode.children.length) {
582
+ compilerDom.buildSlots(clonedNode, context, (props, children) => {
583
+ vnodeBranches.push(createVNodeSlotBranch(props, children, context));
584
+ return compilerDom.createFunctionExpression(undefined);
585
+ });
586
+ }
587
+ let propsExp = `null`;
588
+ if (node.props.length) {
589
+ // note we are not passing ssr: true here because for components, v-on
590
+ // handlers should still be passed
591
+ const { props, directives } = compilerDom.buildProps(node, context);
592
+ if (props || directives.length) {
593
+ propsExp = buildSSRProps(props, directives, context);
594
+ }
595
+ }
596
+ const wipEntries = [];
597
+ wipMap$1.set(node, wipEntries);
598
+ const buildSSRSlotFn = (props, children, loc) => {
599
+ const fn = compilerDom.createFunctionExpression([props || `_`, `_push`, `_parent`, `_scopeId`], undefined, // no return, assign body later
600
+ true, // newline
601
+ true, // isSlot
602
+ loc);
603
+ wipEntries.push({
604
+ fn,
605
+ children,
606
+ // also collect the corresponding vnode branch built earlier
607
+ vnodeBranch: vnodeBranches[wipEntries.length]
608
+ });
609
+ return fn;
610
+ };
611
+ const slots = node.children.length
612
+ ? compilerDom.buildSlots(node, context, buildSSRSlotFn).slots
613
+ : `null`;
614
+ if (typeof component !== 'string') {
615
+ // dynamic component that resolved to a `resolveDynamicComponent` call
616
+ // expression - since the resolved result may be a plain element (string)
617
+ // or a VNode, handle it with `renderVNode`.
618
+ node.ssrCodegenNode = compilerDom.createCallExpression(context.helper(SSR_RENDER_VNODE), [
619
+ `_push`,
620
+ compilerDom.createCallExpression(context.helper(compilerDom.CREATE_VNODE), [
621
+ component,
622
+ propsExp,
623
+ slots
624
+ ]),
625
+ `_parent`
626
+ ]);
627
+ }
628
+ else {
629
+ node.ssrCodegenNode = compilerDom.createCallExpression(context.helper(SSR_RENDER_COMPONENT), [component, propsExp, slots, `_parent`]);
630
+ }
631
+ };
632
+ };
633
+ function ssrProcessComponent(node, context) {
634
+ const component = componentTypeMap.get(node);
635
+ if (!node.ssrCodegenNode) {
636
+ // this is a built-in component that fell-through.
637
+ if (component === compilerDom.TELEPORT) {
638
+ return ssrProcessTeleport(node, context);
639
+ }
640
+ else if (component === compilerDom.SUSPENSE) {
641
+ return ssrProcessSuspense(node, context);
642
+ }
643
+ else if (component === compilerDom.TRANSITION_GROUP) {
644
+ return ssrProcessTransitionGroup(node, context);
645
+ }
646
+ else {
647
+ // real fall-through: Transition / KeepAlive
648
+ // just render its children.
649
+ processChildren(node.children, context);
650
+ }
651
+ }
652
+ else {
653
+ // finish up slot function expressions from the 1st pass.
654
+ const wipEntries = wipMap$1.get(node) || [];
655
+ for (let i = 0; i < wipEntries.length; i++) {
656
+ const { fn, children, vnodeBranch } = wipEntries[i];
657
+ // For each slot, we generate two branches: one SSR-optimized branch and
658
+ // one normal vnode-based branch. The branches are taken based on the
659
+ // presence of the 2nd `_push` argument (which is only present if the slot
660
+ // is called by `_ssrRenderSlot`.
661
+ fn.body = compilerDom.createIfStatement(compilerDom.createSimpleExpression(`_push`, false), processChildrenAsStatement(children, context, false, true /* withSlotScopeId */), vnodeBranch);
662
+ }
663
+ // component is inside a slot, inherit slot scope Id
664
+ if (context.withSlotScopeId) {
665
+ node.ssrCodegenNode.arguments.push(`_scopeId`);
666
+ }
667
+ if (typeof component === 'string') {
668
+ // static component
669
+ context.pushStatement(compilerDom.createCallExpression(`_push`, [node.ssrCodegenNode]));
670
+ }
671
+ else {
672
+ // dynamic component (`resolveDynamicComponent` call)
673
+ // the codegen node is a `renderVNode` call
674
+ context.pushStatement(node.ssrCodegenNode);
675
+ }
676
+ }
677
+ }
678
+ const rawOptionsMap = new WeakMap();
679
+ const [baseNodeTransforms, baseDirectiveTransforms] = compilerDom.getBaseTransformPreset(true);
680
+ const vnodeNodeTransforms = [...baseNodeTransforms, ...compilerDom.DOMNodeTransforms];
681
+ const vnodeDirectiveTransforms = Object.assign(Object.assign({}, baseDirectiveTransforms), compilerDom.DOMDirectiveTransforms);
682
+ function createVNodeSlotBranch(props, children, parentContext) {
683
+ // apply a sub-transform using vnode-based transforms.
684
+ const rawOptions = rawOptionsMap.get(parentContext.root);
685
+ const subOptions = Object.assign(Object.assign({}, rawOptions), {
686
+ // overwrite with vnode-based transforms
687
+ nodeTransforms: [
688
+ ...vnodeNodeTransforms,
689
+ ...(rawOptions.nodeTransforms || [])
690
+ ], directiveTransforms: Object.assign(Object.assign({}, vnodeDirectiveTransforms), (rawOptions.directiveTransforms || {})) });
691
+ // wrap the children with a wrapper template for proper children treatment.
692
+ const wrapperNode = {
693
+ type: 1 /* ELEMENT */,
694
+ ns: 0 /* HTML */,
695
+ tag: 'template',
696
+ tagType: 3 /* TEMPLATE */,
697
+ isSelfClosing: false,
698
+ // important: provide v-slot="props" on the wrapper for proper
699
+ // scope analysis
700
+ props: [
701
+ {
702
+ type: 7 /* DIRECTIVE */,
703
+ name: 'slot',
704
+ exp: props,
705
+ arg: undefined,
706
+ modifiers: [],
707
+ loc: compilerDom.locStub
708
+ }
709
+ ],
710
+ children,
711
+ loc: compilerDom.locStub,
712
+ codegenNode: undefined
713
+ };
714
+ subTransform(wrapperNode, subOptions, parentContext);
715
+ return compilerDom.createReturnStatement(children);
716
+ }
717
+ function subTransform(node, options, parentContext) {
718
+ const childRoot = compilerDom.createRoot([node]);
719
+ const childContext = compilerDom.createTransformContext(childRoot, options);
720
+ // this sub transform is for vnode fallback branch so it should be handled
721
+ // like normal render functions
722
+ childContext.ssr = false;
723
+ // inherit parent scope analysis state
724
+ childContext.scopes = Object.assign({}, parentContext.scopes);
725
+ childContext.identifiers = Object.assign({}, parentContext.identifiers);
726
+ childContext.imports = parentContext.imports;
727
+ // traverse
728
+ compilerDom.traverseNode(childRoot, childContext);
729
+ ['helpers', 'components', 'directives'].forEach(key => {
730
+ childContext[key].forEach((value, helperKey) => {
731
+ if (key === 'helpers') {
732
+ const parentCount = parentContext.helpers.get(helperKey);
733
+ if (parentCount === undefined) {
734
+ parentContext.helpers.set(helperKey, value);
735
+ }
736
+ else {
737
+ parentContext.helpers.set(helperKey, value + parentCount);
738
+ }
739
+ }
740
+ else {
741
+ parentContext[key].add(value);
742
+ }
743
+ });
744
+ });
745
+ // imports/hoists are not merged because:
746
+ // - imports are only used for asset urls and should be consistent between
747
+ // node/client branches
748
+ // - hoists are not enabled for the client branch here
749
+ }
750
+ function clone(v) {
751
+ if (shared.isArray(v)) {
752
+ return v.map(clone);
753
+ }
754
+ else if (shared.isObject(v)) {
755
+ const res = {};
756
+ for (const key in v) {
757
+ res[key] = clone(v[key]);
758
+ }
759
+ return res;
760
+ }
761
+ else {
762
+ return v;
763
+ }
764
+ }
765
+
738
766
  // Because SSR codegen output is completely different from client-side output
739
767
  // (e.g. multiple elements can be concatenated into a single template literal
740
768
  // instead of each getting a corresponding call), we need to apply an extra
@@ -823,7 +851,7 @@ function processChildren(children, context, asFragment = false, disableNestedFra
823
851
  // TODO
824
852
  break;
825
853
  default:
826
- context.onError(createSSRCompilerError(64 /* X_SSR_INVALID_AST_NODE */, child.loc));
854
+ context.onError(createSSRCompilerError(63 /* X_SSR_INVALID_AST_NODE */, child.loc));
827
855
  // make sure we exhaust all possible types
828
856
  const exhaustiveCheck = child;
829
857
  return exhaustiveCheck;
@@ -855,7 +883,7 @@ function processChildren(children, context, asFragment = false, disableNestedFra
855
883
  // `transformText` is not used during SSR compile.
856
884
  break;
857
885
  default:
858
- context.onError(createSSRCompilerError(64 /* X_SSR_INVALID_AST_NODE */, child.loc));
886
+ context.onError(createSSRCompilerError(63 /* X_SSR_INVALID_AST_NODE */, child.loc));
859
887
  // make sure we exhaust all possible types
860
888
  const exhaustiveCheck = child;
861
889
  return exhaustiveCheck;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vue/compiler-ssr",
3
- "version": "3.2.26",
3
+ "version": "3.2.30",
4
4
  "description": "@vue/compiler-ssr",
5
5
  "main": "dist/compiler-ssr.cjs.js",
6
6
  "types": "dist/compiler-ssr.d.ts",
@@ -15,7 +15,7 @@
15
15
  },
16
16
  "repository": {
17
17
  "type": "git",
18
- "url": "git+https://github.com/vuejs/vue-next.git",
18
+ "url": "git+https://github.com/vuejs/core.git",
19
19
  "directory": "packages/compiler-ssr"
20
20
  },
21
21
  "keywords": [
@@ -24,11 +24,11 @@
24
24
  "author": "Evan You",
25
25
  "license": "MIT",
26
26
  "bugs": {
27
- "url": "https://github.com/vuejs/vue-next/issues"
27
+ "url": "https://github.com/vuejs/core/issues"
28
28
  },
29
- "homepage": "https://github.com/vuejs/vue-next/tree/master/packages/compiler-ssr#readme",
29
+ "homepage": "https://github.com/vuejs/core/tree/main/packages/compiler-ssr#readme",
30
30
  "dependencies": {
31
- "@vue/shared": "3.2.26",
32
- "@vue/compiler-dom": "3.2.26"
31
+ "@vue/shared": "3.2.30",
32
+ "@vue/compiler-dom": "3.2.30"
33
33
  }
34
34
  }