Smartideo 是个 WordPress 视频解析插件,作者 Fens Liu,官方页面 7yper.com/3639。它的功能一句话讲清:
在文章里单独粘一行视频网址,发布后自动变成播放器。
比如粘一行 https://www.bilibili.com/video/BV1GJ411x7h7,前台就渲染成一个 B 站播放器。手机上也能播,不需要装任何额外插件。
感谢作者!
原理不复杂:它在 WordPress 里注册了 14 条正则,把你贴的网址匹配出来,替换成对应平台的官方播放器 iframe。所以它不是"解析"视频(不下载、不转码),而是换一个官方嵌入地址——这也是为什么它能免广告:用的都是平台给第三方的官方嵌入播放器。
支持平台:YouTube、哔哩哔哩(含分P、av 号、b23.tv 短链)、抖音、腾讯视频、优酷、搜狐视频、AcFun、56网,以及网易云音乐、QQ 音乐。
老实说,2.9.0 版本的思路是对的,代码也很克制,全才 250 行。但它已经许久没更新了,2026 年的今天,插件里有一半平台是播不了的。
我用workbuddy查了一下,问题是三类。
第一类:平台自己换了地址
这不是插件写错了,是平台那边改了。实测下来:
| 平台 | 原代码里的地址 | 2026 年实测 |
|---|---|---|
| 腾讯视频 | v.qq.com/iframe/player.html |
旧路径已废弃,现行为 v.qq.com/txp/iframe/player.html |
| 搜狐视频 | upload/static/share/share_play.html |
2016 年的老地址,新行为 tv.sohu.com/s/sohuplayer/iplay.html |
| AcFun | www.acfun.cn/player/ac{id} |
502,播放器目录整个下线 |
| b23.tv 短链 | 正则要求链接里含 BV 号 |
平台改成 6 位随机码(b23.tv/i2YArd1J),绝大多数短链压根匹配不上 |
| 56网 | www.56.com/iframe/{id} |
站点已停止更新,且原代码硬编码 http://,HTTPS 站点会被浏览器当混合内容拦掉 |
其中 b23.tv 那个最隐蔽——它不是"失效",是"规则变了",旧正则看起来没毛病,实际一条都匹配不上。
第二类:代码本身有 bug
翻代码找到几个实打实的问题:
最严重的一个:style 属性注入。 get_size_style() 把后台设置的宽高直接拼进 style="..." 属性,全程没转义。我搭了个测试环境实测,输入 100%" onmouseover="alert(1) 之后的真实输出是:
<div class="player" style="width: 100%" onmouseover="alert(1);height: 400px;">
事件属性被成功注入。虽然要管理员权限才能填这个值,实际风险不高,但这是 WordPress 编码规范的硬性违规项,多用户协作站点上可被利用。
其余几个:
$matches['video_id1']没做存在性判断——PHP 8 下会抛 warning,命名捕获组没匹配时这个 key 根本不存在extract()死代码——整个函数提取出来的变量,一处都没用到- tips 文案直接拼进 HTML 属性,没走
esc_attr() - 隐私增强模式自相矛盾:加了 youtube-nocookie,却又发
referrerpolicy="unsafe-url"把来源地址递出去 - 后台权限判断用的是
update_core(升内核权限),和菜单注册的manage_options不一致;无权限时只 echo 一句裸 HTML,页面会塌成一块白 - 源站播放的提示语写着"暂时无法播放",但那明明是用户自己主动开启的功能
第三类:不适应新版本
| 项 | 原来 | 问题 |
|---|---|---|
Requires at least |
3.5.0 | 不实。代码用到的 wp_safe_remote_head() 是 WP 4.6+ 才有 |
Requires PHP |
没写 | 缺这个头,WordPress 无法在安装前拦截不兼容环境 |
Tested up to |
6.9.4 | 停在两个大版本之前 |
Text Domain |
声明了 smartideo | 全代码零 __(),界面全是硬编码中文,属于虚假声明 |
| 后台判断 | is_admin() |
改用 WP_ADMIN 常量语义更明确 |
| 响应式 | wp_is_mobile() |
UA 嗅探,WordPress 官方已不推荐用于新代码 |
还有个体验问题一并说了:原来的"固定大小"模式靠 wp_is_mobile() 判断要不要切移动端尺寸——意味着你在桌面浏览器里把窗口拉窄,播放器不会变,只有手机浏览器才切。
我主要做了以下几件事:
恢复了 7 个失效站点
| 平台 | 改成 |
|---|---|
| 腾讯视频 | v.qq.com/txp/iframe/player.html?vid= |
| 搜狐视频 | tv.sohu.com/s/sohuplayer/iplay.html?vid=,并兼容新版 tv.sohu.com/v/{id} 链接 |
| AcFun | 见下方说明 |
| b23.tv | 新增跟随跳转解析真实 BV 号,Transient 缓存 7 天;解析失败降级为可点击链接,不白屏 |
| 抖音 | 补上 iesdouyin.com 分享页和 v.douyin.com 短链 |
| 优酷 | 补上 ?vid= 和无 /video/ 前缀两种形态 |
| B站 | 补上 av 号、分P(?p= ?page= index_)、m.bilibili.com |
| YouTube | 补上 youtu.be 短链、shorts,以及编辑器转义 & 后的链接 |
按你的要求移除了 56 网:删掉正则和处理函数,同时注销 WordPress 自带的 56 handler——这样 56 链接会变成普通链接,而不是生成失效播放器。
修掉了 8 个代码问题
最主要是那个 style 注入。修法不是简单加 esc_attr(),而是加白名单:只放行"数字 + 合法 CSS 单位",其余一律丢弃,并且存库前就过滤一道。
修复前: style="width: 100%" onmouseover="alert(1);height: 400px;" 修复后: style="--sm-h:400px;"
其余七项:命名组缺失统一走 pick() 兜底、删掉 extract()、输出补 esc_url/esc_attr/esc_html、nocookie 时改用 no-referrer、权限改 WP_ADMIN、后台提示改用 wp_admin_notice()、卸载时自动清理设置项。
顺手修掉一个体验缺陷
移除 wp_is_mobile() 后,固定大小模式改成输出 CSS 变量 + 样式表媒体查询:
<div class="player" style="--sm-w:80%;--sm-h:450px;--sm-wm:100%;--sm-hm:250px;">
@media screen and (max-width:639px){
.smartideo .player { width: var(--sm-wm, 100%); height: var(--sm-hm, 250px); }
}
这样桌面浏览器拉窄窗口也会正确切换到移动端尺寸——原来的 UA 判断做不到这件事。
AcFun 是个例外。我修完才发现,AcFun 恢复不了内嵌。它所有存活入口都返回 X-Frame-Options: SAMEORIGIN,意味着只有 AcFun 自己的页面能嵌套它,第三方网站嵌进去必然白屏。这是 A 站主动关闭了第三方嵌入能力,不是代码问题。
所以 AcFun 链接改成显示"AcFun 不支持第三方网站嵌入播放,点击前往观看"的提示卡片。等 A 站哪天恢复开放,改回一行代码就能重新内嵌。
兼容性结论:PHP 8.5.8 和 WordPress 7.1.2 下全部干净。 PHP 8.4 弃用的隐式 nullable、8.5 的新特性,这份代码都没触及;WordPress 7.1 的破坏性变更(编辑器强制 iframe 化、jQuery UI 升 1.14.2、媒体改客户端处理)也都跟这个插件无关——它不进编辑器、不用 jQuery UI、不处理媒体。
部署提醒:Requires at least 提到了 6.4(因为用了 wp_admin_notice(),该函数 6.4 引入)。站点若低于 6.4 会拒绝安装。纯 PHP + CSS 改动,不涉及数据库,升级前备份插件目录即可。
附:修改文件清单
| 文件 | 变更 |
|---|---|
smartideo.php |
14 条正则重写、新增 pick()/safe_id()/safe_size()/resolve_short_url()、AcFun 降级、56 移除、插件头补版本声明 |
smartideo-admin.php |
权限修正、wp_admin_notice()、尺寸存库白名单、默认值回显 |
static/smartideo.css |
播放器改 CSS 变量驱动、iframe 补 border:0、容器补 max-width |
readme.txt |
版本声明更新、3.0.0 完整 changelog |
点我下载。