Subscribe on changes!

@vue/server-renderer <img> inside slot leads to double import of same asset

avatar
Oct 15th 2020

Version

3.0.0

Reproduction link

https://github.com/BobbySpoon/vue-compiler-ssr-staticAsset-slot

Steps to reproduce

This is a modified version of #2379. I did some further investigation. Actually the issue is not router-link based, but slot-based. See below for details.

const { compileTemplate } = require('@vue/compiler-sfc');

const { code } = compileTemplate({
  source: "<slot-test><img class='logo' src='./logo.png' /></slot-test>",
  inMap: undefined,
  filename: 'C:\\some\\file',
  ssr: true,
  compiler: undefine
  compilerOptions: { scopeId: null, bindingMetadata: {} },
  transformAssetUrls: true,
});

console.log(code);

What is expected?

No duplicate import of same asset.

What is actually happening?

During compilation @vue/compiler-ssr (lines 250ff) is creating a clone of node (fallback vnode-based branch) which is being traversed by @vue/compiler-dom. (@vue/compiler-ssr lines 387 [function subTransform(node, options, parentContext) {..}]. In a next step, some properties of the context of the cloned node (childcontext) are being added to the parentcontext. Since no checks are being performed, parentcontext ends up with same import _imports_0 from './logo.png' twice (since transformAssetUrl (@vue/compiler-sfc lines 335) is being called both on parent and clone)


I am not completely aware of why the fallback-branch has to be created, so I'm also not very sure on how to fix this. Most obvious to me would be to check if path in childcontext.imports already exists in parentcontext.imports. On the other hand, I feel like this is always the case since the same traversion is being performed on both parent and child (clone), so maybe leave out transformAssetUrl when traversing the clone?

avatar
Feb 9th 2021

This can also be reproduced by compiling a simple template (for SSR):

<div>
  <img src="./logo.png">
  <img src="./logo.png">
</div>
SyntaxError: /Users/Razvan/work/test/v2/src/pages/Index.vue: Identifier '_imports_0' has already been declared (4:7)

  2 | import { ssrRenderComponent as _ssrRenderComponent, ssrRenderAttr as _ssrRenderAttr, ssrInterpolate as _ssrInterpolate } from "@vue/server-renderer"
  3 | import _imports_0 from './logo.png'
> 4 | import _imports_0 from './logo.png'
avatar
Feb 16th 2021

met the same problem. I hope it be fixed soon

avatar
Feb 25th 2021

Fixed by c69f4ea8

avatar
Mar 31st 2021

Has this fix been deployed yet?