During QA on almost every web project I’ve worked on, a time comes when somebody files a bug report like this:
在我所从事的几乎每个Web项目的质量检查过程中,都会有人提交如下错误报告:
These links should open in a new window.
这些链接应在新窗口中打开。
I usually try to have a conversation with them about how opening links in a new window is unexpected behavior, it can be jarring, we should let users decide how to use their browser, et cetera, but I have never won that battle and always end up implementing target="_blank"
.
我通常尝试与他们进行对话,讨论如何在新窗口中打开链接是意外行为,这可能会令人讨厌,我们应该让用户决定如何使用他们的浏览器, 等等 ,但是我从未赢得这场战斗,并且总是以失败告终。实施target="_blank"
。
On one project I inherited though, a bunch of links were already opening in a new window. I was doing an accessibility audit and remediation. In order to keep the links opening in a new window and meet WCAG guidelines, links that opened in a new window needed:
不过,在我继承的一个项目中,许多链接已经在新窗口中打开。 我正在进行可访问性审核和修复。 为了使链接在新窗口中打开并符合WCAG准则,在新窗口中打开的链接需要:
- a visual indication that they open in a new window 在新窗口中打开的直观指示
- textual indication that the link would open in a new window for screen readers 文字说明该链接将在屏幕阅读器的新窗口中打开
rel="noopener noreferrer"
for securityrel="noopener noreferrer"
以确保安全
建立 (Setup)
Instead of combing through the markup to add this, I created a small JavaScript module that would accomplish all three. Here’s how I did it.
我没有梳理标记来添加标记,而是创建了一个小JavaScript模块来完成这三个任务。 这是我的方法。
In our initialization, we need two things:
在初始化中,我们需要两件事:
The current host (for example, you are currently on https://benrobertson.io)
当前主机(例如,您当前位于https://benrobertson.io )
- A list of all links on the page. 页面上所有链接的列表。
You can get the current host with JavaScript easily with window.location.host
. We'll use this to compare each link to.
您可以通过window.location.host
轻松地使用JavaScript获取当前主机。 我们将使用它来比较每个链接。
To grab all the links, we can use an attribute selector that targets the href
attribute. We already know we only want external URLs so we'll grab elements with an href that starts with http
.
要获取所有链接,我们可以使用针对href
属性的属性选择器。 我们已经知道我们只需要外部URL,因此我们将获取带有以http
开头的href的元素。
// This will grab every single <a> on the page
document.querySelectorAll('a');// This will grab only <a> elements that have
// a full url in the href, either http or https
document.querySelectorAll('a[href^="http"]');
解析URL数组 (Parse the URLs Array)
Next we need to loop through each array and determine if we need to do anything to it.
接下来,我们需要遍历每个数组,并确定是否需要对它做任何事情。
// Create an array from all the links we found in the
// last step and loop through it.Array.from(this.links).forEach((link) => {
// If the host doesn't match the current host,
// that means it's an external link.
// Otherwise do nothing.
if (link.host !== this.host) {
// Add the external link attributes
link.rel = 'noopener noreferrer';
link.target = '_blank';
this.addIndicator(link);
}
})
添加指标 (Add Indicators)
For this particular site, we were already using Bootstrap + glyphicons, so that gave a nice icon we could use. The only thing we need to do is add some markup with the right class names inside of each link. We also want to add some screen reader text (visually hidden) so that people using assistive technology will know that the link will update in a new window as well.
对于这个特定的网站,我们已经在使用Bootstrap + glyphicons ,因此提供了一个可以使用的漂亮图标。 我们唯一需要做的就是在每个链接中添加带有正确类名的标记。 我们还希望添加一些屏幕阅读器文本(在视觉上是隐藏的),以便使用辅助技术的人将知道该链接也会在新窗口中更新。
addIndicator: function(link) {
// Create a span element to add the icon to.
var icon = document.createElement('span');
// Add the icon classes.
icon.classList.add(
'glyphicon',
'glyphicon-new-window',
'glyphicon--small',
'glyphicon--space-left'
); // Create another span that will add some screen reader
// friendly text to announce that the window will
// open in a new window.
var span = document.createElement('span');
span.textContent = 'new window';
span.classList.add('screen-reader-text'); // Add the markup that we added to the page.
icon.appendChild(span);
link.appendChild(icon);
}
最终密码 (Final Code)
Here’s everything put together. Add the script to a page and then call ExternalLinks.init()
to add the markup and indicators. You could also package up something like this in a library (I'm guessing one or more exists already!).
这是所有的东西。 将脚本添加到页面,然后调用ExternalLinks.init()
添加标记和指示符。 您也可以在库中打包类似的东西(我猜已经存在一个或多个!)。
var ExternalLinks = {
host: '',
links: [], init: function() {
// Get the current host
this.host = window.location.host;
// find all links
this.links = document.querySelectorAll('a[href^="http"]'); // Parse all links
this.parse();
}, parse: function() {
Array.from(this.links).forEach((link, index) => {
if (link.host !== this.host) {
link.rel = 'noopener noreferrer';
link.target = '_blank';
this.addIndicator(link);
}
})
}, addIndicator: function(link) {
var icon = document.createElement('span');
icon.classList.add(
'glyphicon',
'glyphicon-new-window',
'glyphicon--small',
'glyphicon--space-left'
); var span = document.createElement('span');
span.textContent = 'new window';
span.classList.add('screen-reader-text'); icon.appendChild(span);
link.appendChild(icon);
}
};
Originally published at https://benrobertson.io on August 9, 2020.
最初于 2020年8月9日 发布于 https://benrobertson.io 。
翻译自: https://levelup.gitconnected.com/handling-external-links-1668c15b7791