Adding target="_blank" to all links in dynamically loaded content
3 quarters ago - 8 min read • #vueOn this website I'm using Hygraph as CMS for my articles and via GraphQL it is loaded to the Nuxt website.
The content is stored as Markdown. Via MarkdownIt it is converted to HTML and displayed on the page.
But when you click to any of those links in this article (yeah, try it..) you see the links are being opened in a new browser window. All the links have target="_blank"
attribute.
In Markdown there is no easy way how to pass attributes to the link. And I don't want to think on it and add attributes manually to all my links anyway.
The way is a simple Custom Vue Directive.
Vue Custom Directives
Here is what official docs say:
A custom directive is defined as an object containing lifecycle hooks similar to those of a component. The hooks receive the element the directive is bound to. ... In <script setup>, any camelCase variable that starts with the v prefix can be used as a custom directive.
v-add-target-blank directive
When we know this it is easy to loop all the link elements and add the target attribute:
const vAddTargetBlank = {
mounted: (el: HTMLElement) => {
const links = el.querySelectorAll("a")
links.forEach((link) => {
link.setAttribute("target", "_blank")
})
}
}
<div v-html="content" v-add-target-blank></div>
Going further
In this case it is not necessary, but we can do one more step and pass the value of the attribute as an argument:
const vAddTargetBlank = {
mounted: (el: HTMLElement, binding: any) => {
const links = el.querySelectorAll("a")
links.forEach((link) => {
link.setAttribute("target", binding.value)
})
}
}
<div v-html="render" v-add-target-blank="'_blank'"></div>