Subscribe on changes!

Add Unique Component Instance ID

avatar
Feb 21st 2022

What problem does this feature solve?

Take the following code as an example:

<template>
  <div>
    <label for="some_id">Hello</label>
    <input id="some_id" type="text">
  </div>
</template>

If there are multiple instances of that component on a page, it breaks the HTML as all id attributes must be unique.

Most of the solutions online handle this situation kinda like this (this is off the top of my head but the gist is there):

<template>
  <div>
    <label :for="id">Hello</label>
    <input :id="id" type="text">
  </div>
</template>

<script>
let id = 0

export default {
  data() {
    return { id: null }
  }
  created() {
    id++
    this.id = id
  }
}
</script>

This seems fair until you attempt this with SSR. The server will generate a different id from the client. As far as I know, there is no workaround for this.

This not only affects this situation but other accessibility-related instances where the HTML id is necessary (aria-labelby for example) as well as implementations using non-Vue libraries such as Popper.js.

I know this has been an issue for years (just do a google search and you'll see tons of results about it).

Is there any possibility of adding a unique component instance identifier than we can use in the script as well as the template?

If not, what is the best practice for handling this, keeping in mind the necessity of having it work with SSR.

Thank you!

What does the proposed API look like?

I'd love to have a this.$instanceId exposed for each component that could be used to identify a unique component instance in both server and client environments.

So, the issue from above could be solved with something like this:

<template>
  <div>
    <label :for="`${$instanceId}__input`">Hello</label>
    <input :id="`${$instanceId}__input`" type="text">
  </div>
</template>
avatar
Feb 22nd 2022