How is metaInfo resolved?

You can define a metaInfo property on any component in the tree. Child components that have metaInfo will recursively merge their metaInfo into the parent context, overwriting any duplicate properties. To better illustrate, consider this component hierarchy:

  1. <parent>
  2. <child></child>
  3. </parent>

If both <parent> and <child> define a title property inside metaInfo, then the title that gets rendered will resolve to the title defined inside <child>.

Concatenate metadata

When specifying an array in metaInfo, like in the below examples, the default behaviour is to simply concatenate the lists.

Input:

  1. // parent component
  2. {
  3. metaInfo: {
  4. meta: [
  5. { charset: 'utf-8' },
  6. { name: 'description', content: 'foo' }
  7. ]
  8. }
  9. }
  10. // child component
  11. {
  12. metaInfo: {
  13. meta: [
  14. { name: 'description', content: 'bar' }
  15. ]
  16. }
  17. }

Output:

  1. <meta charset="utf-8">
  2. <meta name="description" content="foo">
  3. <meta name="description" content="bar">

Unique metadata

This is not what we want, since the meta description needs to be unique for every page. If you want to change this behaviour such that description is instead replaced, then give it a vmid:

Input:

  1. // parent component
  2. {
  3. metaInfo: {
  4. meta: [
  5. { charset: 'utf-8' },
  6. { vmid: 'description', name: 'description', content: 'foo' }
  7. ]
  8. }
  9. }
  10. // child component
  11. {
  12. metaInfo: {
  13. meta: [
  14. { vmid: 'description', name: 'description', content: 'bar' }
  15. ]
  16. }
  17. }

Output:

  1. <meta charset="utf-8">
  2. <meta vmid="description" name="description" content="bar">

While solutions like react-helmet manage the occurrence order and merge behaviour for you automatically, it involves a lot more code and is therefore prone to failure in some edge-cases, whereas this method is almost bulletproof because of its versatility; at the expense of one tradeoff: these vmid properties will be rendered out in the final markup (vue-meta uses these client-side to prevent duplicating or overriding markup). If you are serving your content gzipped, then the slight increase in HTTP payload size is negligible.