前面有朋友问,我博客评论中的外链跳转过渡页是如何实现的?其实,在 本博客的源码 中就可以很容易找到具体的实现代码。不过,为了方便理解,我还是简单梳理一下实现思路。
实际效果
先看看效果图:
上图是点击评论者头像后跳转的页面,然后点击“继续访问”就可以打开目标网站了,当然,这需要评论者在评论时填写网址才行。
该页面比较简单,是模仿“知乎”实现的,网址路径中也用到了一个 target
参数,这个比较关键,后面会多次用到,接下来看一下详细的实现过程。
过渡页
首先,在主题中添加过渡页 redirect.php
,文件中的具体代码如下:
<!DOCTYPE html>
<html>
<head>
<meta charset="<?php $this->options->charset(); ?>">
<meta name="renderer" content="webkit">
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
<title><?php $this->options->title(); ?></title>
<?php if ($this->options->faviconUrl) : ?>
<link rel="icon" href="<?php $this->options->faviconUrl(); ?>" />
<?php endif; ?>
<link rel="stylesheet" href="<?php $this->options->themeUrl('static/bootstrap/bootstrap.min.css'); ?>">
</head>
<body class="px-3 w-100 h-100">
<?php $target = urldecode($_GET['target']); ?>
<div class="card mx-auto" style="max-width: 500px; margin-top: 100px">
<div class="card-body">
<h2 class="card-title"><?php _e("离开" . $this->options->title); ?></h2>
<p class="card-text mt-3"><?php _e("您即将离开" . $this->options->title . ",前往" . $target . ",请注意您的个人隐私和财产安全。") ?></p>
<div class="text-end pt-3 border-top">
<a href="<?php echo $target; ?>" class="btn btn-dark" rel="noopener noreferrer"><?php _e("继续访问"); ?></a>
</div>
</div>
</div>
</body>
</html>
这里面有两句核心代码,一个是 <?php $target = urldecode($_GET['target']); ?>
,顾名思义,就是从 url
的参数中获取目标网址。另一个是<a href="<?php echo $target; ?>" class="btn btn-dark" rel="noopener noreferrer"><?php _e("继续访问"); ?></a>
,也就是跳转到目标网址了,这里考虑到安全性和性能,我们通常会加上 rel="noopener noreferrer"
属性,其它的就没什么可说的了,你可以根据需要定制或美化这个页面。
跳转链接
过渡页有了,接下来就是如何在用户点击外链的时候先导航到过渡页了。还是以我的博客为例,假如需要访问https://abc.com
,如果希望先跳转过渡页,则只需要将跳转链接设置为 https://ilaozhu.com?target=https://abc.com
即可。
在本博客的源码中,可以到 comments.php
文件中找到相关实现:
<?php
$url = getRedirectUrl($comments->url);
if ($url["hasUrl"]): ?>
<a href="<?= $url["url"] ?>" target="_blank">
<img src="<?= getGravatar($comments->mail); ?>" style="whidth:24px;height:24px;transform:scale(2);" class="rounded shadow-sm">
</a>
<?php else: ?>
<img src="<?= getGravatar($comments->mail); ?>" style="whidth:24px;height:24px;transform:scale(2);" class="rounded shadow-sm">
<?php endif; ?>
顾名思义,并不是所有的评论者都会填写网址,只有填了网址的才需要跳转。其中,getRedirectUrl
方法在 functions.php
文件中,具体实现如下:
function getRedirectUrl($url)
{
if (!$url) {
return [
'hasUrl' => false
];
}
$options = Widget::widget(Options::class);
if (str_starts_with($url, $options->siteUrl)) {
return [
'hasUrl' => true,
'url' => $url
];
} else {
return [
'hasUrl' => true,
'url' => $options->siteUrl . '?target=' . urlencode($url)
];
}
}
上述代码的大致意思是,如果没有链接,则不跳转,如果是内链,则直接跳转到目标页面即可,而如果是外链,才需要先跳转到过渡页。
请求拦截
到此就可以了吗?非也。还差最后一步,也就是当链接跳转到 https://ilaozhu.com?target=https://abc.com
时,服务端应该执行 redirect.php
中的代码,并返回给客户端,而不是直接向客户端展示首页。
这一步也很简单,只需要在主题的 index.php
文件的开始位置,拦截 target
参数就可以了,也就是说,只要 url
参数中有 target
,我们就执行跳转过渡页的逻辑,如下图所示:
简单的三行代码就可以了,值得注意的是,exit
是必须的,否则会继续执行后续的代码,导致页面不能正常显示。
好了,到这里,外链跳转过渡页的功能就完成了。当然,具体文章中如果有外链需要经过过渡页也是可以的,只需要将原本的链接地址加上 https://ilaozhu.com?target=
前缀(你自己的网址)就可以了,至于哪里需要过渡页,哪里不需要,这个就需要你自己根据实际情况权衡了。
评论0
暂时没有评论