Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow configuring how the hmr Id is generated in @vitejs/plugin-vue #21

Open
4 tasks done
PPetau opened this issue Jul 27, 2022 · 4 comments
Open
4 tasks done

Allow configuring how the hmr Id is generated in @vitejs/plugin-vue #21

PPetau opened this issue Jul 27, 2022 · 4 comments
Labels
enhancement New feature or request has workaround

Comments

@PPetau
Copy link

PPetau commented Jul 27, 2022

Description

I was trying to import a Vue component from another instance of vite.

The problem lies here:
https://github.com/vitejs/vite/blob/c78e4099e502876a2ab23fd8163455d8172ff5b7/packages/plugin-vue/src/utils/descriptorCache.ts#L30
Due to how the id on the descriptor is generated it is impossible to me to change how the css-Scope/__hmrId ... will be generated resulting in a broken hmr runtime and conflicting css.

Using the isProduction flag is not viable because it disables the hmr runtime on vue components.

Suggested solution

Could we introduce another flag or an option to specify how this Id would generate?

There could be an Option that works like isProduction to include the source when creating the id hash

Alternative

No response

Additional context

Repro in StackBlitz: https://stackblitz.com/edit/vitejs-vite-kr3fdz?file=vite-1/index.html

If we then edit the vite-1/src/App.vue the other app gets broken because their internal _hmrId is the same.

Validations

@bluwy
Copy link
Member

bluwy commented Jul 28, 2022

This feels like a very niche usecase which many plugins won't support, so it's not only a problem with plugin-vue. What is your usecase needing to accessing Vue components from a different server?

@PPetau
Copy link
Author

PPetau commented Jul 28, 2022

I am trying to create some kind of micro-frontend where I am importing other Vue apps from different packages within a workspace. I would like to have multiple vite instances serving the different projects so that the main application can dynamically import these and still utilize the hot reload functionality. Because how the projects are structured, the logic determining how the _hmrId is generated, results in the same id for every component that have the same root-relative path (ex. src/App.vue => "7a7a37b1").

I have written one workaround that tries to rewrite the generated id after the plugin transformed the SFC, but was unable to catch every place where the generated id is used.

@arnoson
Copy link

arnoson commented Sep 11, 2022

@PPetau could you share your workaround? I have a similar usecase: I have a production app that is extendable with plugins. While the user develops a new plugin I want HMR. I can consume the plugin component in my app directly from the plugin's vite dev server, but the ids won't match so only global styles and scripts are working right now.

@PPetau
Copy link
Author

PPetau commented Sep 12, 2022

Hi @arnoson, this is the snipped that runs in the transform hook and replaces the generated hmrIds (only of the .vue files).

const hmrUniqueIdentifier = "your_custom_id_namespace";

if (/\.vue/.test(id)) {
  if (code.includes("_sfc_main.__hmrId")) {
    const magicString = new MagicString(code);
    const hmrId = code.match(
      /_sfc_main\.__hmrId\s*\=\s*["'](.+)["']/m
    )?.[1];
    if (hmrId) {
      magicString.replace(
        new RegExp(hmrId, "g"),
        hmrId + hmrUniqueIdentifier
      );
    return {
      code: magicString.toString(),
      map: magicString.generateMap()
    };
  }
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request has workaround
Projects
None yet
Development

No branches or pull requests

4 participants