Right-Click → View Page Source

Verifying a Nuxt Site on Flattr

Out of the box, Nuxt sites cannot be used to verify domains on Flattr.

The only way to verify a domain with the service is to include a <meta> tag in the <head> of all the pages on your site. The Flattr verification service expects this tag to have 2 attributes and 2 attributes only:-

<meta name="flattr:id" content="abc123" />

The reason that this doesn't play nice with Nuxt is due to data-n-head attributes being added to all <meta> and <link> tags. The solution is to hook into specific Nuxt events and modify the HTML appropriately:-

// nuxt.config.js
import cheerio from 'cheerio';

const removeDataAttributeFromFlattrMetaTag = html => {
  const $ = cheerio.load(html);

  $('meta[name="flattr:id"]').removeAttr('data-n-head');

  return $.html();
};

export default {
  head: {
    meta: [{ name: 'flattr:id', content: 'abc123' }],
  },

  hooks: {
    generate: {
      page(page) {
        page.html = removeDataAttributeFromFlattrMetaTag(page.html);
      },
    },

    render: {
      route(url, page) {
        page.html = removeDataAttributeFromFlattrMetaTag(page.html);
      },
    },
  },
};

Stripping the data-n-head attributes from the <meta> tags in this way is enough to appease the Flattr verification service. I have spoken with the support team at Flattr and brought this issue to their attention, but this workaround will suffice for now.

This attribute serves some purpose in the handover between Nuxt SSR and client-side hydration and originates from the Vue Meta plugin. I presume that removing the attribute in the manner outlined above doesn't cause any issues – especially since this attribute won't be updated elsewhere. But, if you're looking for an alternative, you can add the <meta> tag to the app template instead:-

<!-- ~/app.html -->
<!DOCTYPE html>
<html {{ HTML_ATTRS }}>
  <head {{ HEAD_ATTRS }}>
    <meta name="flattr:id" content="abc123" />
    {{ HEAD }}
  </head>
  <body {{ BODY_ATTRS }}>
    {{ APP }}
  </body>
</html>

UPDATE: After getting to know Vue Meta a little better, I discovered the once special metaInfo attribute. This disables reactivity and, in the case of Nuxt, only outputs the tag during server-side rendering (without data-* attributes):-

// nuxt.config.js
export default {
  head: {
    meta: [{ name: 'flattr:id', content: 'abc123', once: true }],
  },
};

Join the converstation on the DEV Community or send a Webmention