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

Labels and checkboxes break when using multiple Vue bundles, Vue's internal _uid is not unique enough. #7004

Open
stam opened this issue Jul 4, 2022 · 3 comments

Comments

@stam
Copy link

stam commented Jul 4, 2022

Describe the bug

Bootstrap Vue assigns IDs like __BVID__27 to link labels to their corresponding input.
This ID is generated by the ID mixin and is based on Vue's internal _uid.

If we have multiple Vue bundles with bootstrap-vue on the same page, they might use overlapping IDs which causes checkboxes and labels to not be interactive anymore, because the <label for="__BVID__27" /> might point to a __BVID__27 which is also a Modal on the same page.

We get overlapping IDs because on a page with multiple bundles, each Vue instance keeps track of its' own _uid, which is just a counter and can easily collide with the _uids from the other Vue instances on the page.

Steps to reproduce the bug

It is hard to replicate as it requires a page with multiple vue bundles and overlapping BVIDs, but the resulting bug can be approximated by creating a template where 2 b-form-checkboxes have the same id:

https://codesandbox.io/s/bootstrap-vue-duplicate-id-org18h?file=/src/components/HelloWorld.vue:280-497

<b-form-checkbox id="__BVID__27" v-model="checked1" switch
  >b-form-checkbox 1</b-form-checkbox
>
<b-form-checkbox id="__BVID__27" v-model="checked2" switch
  >b-form-checkbox 2</b-form-checkbox
>

Expected behavior

I expect that the safeID that bootstrap-vue's id mixin generates is safe, universally unique, and does not rely on Vue's internal _uid.
The author of vue himself says that relying on Vue's internal _uid for unique IDs is bad practice: vuejs/vue#5886 (comment)

Versions

Libraries:

  • BootstrapVue: 2.22.0
  • Bootstrap: 4.6.1
  • Vue: 2.6.14

Environment:

  • Device: Macbook Pro
  • OS: macOS
  • Browser: Chrome
  • Version: [e.g. 70]

Demo link

https://codesandbox.io/s/bootstrap-vue-duplicate-id-org18h?file=/src/components/HelloWorld.vue:280-497

Additional context

Obviously the best way to fix this is to simply not have multiple Vue bundles on the same page.
We are however migrating a massive legacy application to Vue, and we are gradually refactoring massive pages to Vue, and it can occur that we get multiple Vue apps on the same page.
This usecase is more common than one might think (google for sharing vuex stores between bundles)

Bug as found on staging:

duplicate_bvid

@dombarter
Copy link

I am facing this exact same issue too, where we are putting multiple Vue.js 'widgets' onto a page, that is internally being rendered using WebForms; and we occasionally are getting id clashes.

Our current work around is to manually set the ID on the components, because this will override the automatic one provided by BootstrapVue, thus preventing the clash from happening.

However, it would be nice to tackle the root issue, I've had a couple of thoughts motivated by comments from Evan You:

Let me know if you have any other ideas, because it would be great to sort this out.

@stam
Copy link
Author

stam commented Jul 5, 2022

Hey @dombarter, we now use a forked version of this library where the safeId logic now returns a universally safe ID: KubusInfo@6cffefd

I could clean this up a bit (don't rely on the browser instance of crypto) and make a PR

@dombarter
Copy link

Thanks @stam. I'll take a look!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants