2023年政策修订增补工作正在进行中,欢迎参与!
  • Moegirl.ICU:萌娘百科流亡社群 581077156(QQ),欢迎对萌娘百科运营感到失望的编辑者加入
  • Moegirl.ICU:账号认领正在试运行,有意者请参照账号认领流程

Template:Bots

萌娘百科,万物皆可萌的百科全书!转载请标注来源页面的网页链接,并声明引自萌娘百科。内容不可商用。
跳转到导航 跳转到搜索
Template-info.svg 模板文档  [查看] [编辑] [历史] [刷新]

此模板用于允許或排除機器人對頁面的瀏覽訪問並留下消息。该模板适用于用戶名字空间及所有讨论名字空间中,不推荐在其他名字空间使用。對於机器人账号所有者,建議閣下遵從頁面中{{bots}}及{{nobots}}的指示。

用戶須意識到透過選擇排除來自機器人的通知,根據他們所選擇的標籤,機器人將不會被通知有關他們的消息。

(i)注意 仅限维护人员在非用户或用户讨论名字空间使用该模板。在不允许的名字空间放置该模板将被视为破坏

使用方式

{{nobots}}             拒绝所有机器人账号访问
{{bots}}               允许所有机器人账号访问
{{bots|allow=<botlist>}}  拒绝指定列表外的机器人账号
{{bots|deny=<botlist>}}   拒绝指定列表中的机器人账号

以下指令使用於過濾指定用戶名的機器人帳號(以半形逗號作間隔),另關鍵字“AWB”可以過濾所有使用維基自動瀏覽器的機器人:

{{bots|allow=AWB,AnnAngela-abot}}
{{bots|deny=Cewbot}}

<botlist> 可以透過 "none" or "all" 選項允許/禁止機器人訪問,如下:

{{bots|allow=all}}      允许所有机器人账号访问
{{bots|allow=none}}     禁止所有机器人账号访问
{{bots|deny=all}}       禁止所有机器人账号访问
{{bots|deny=none}}      允许所有机器人账号访问

(i)注意 由於機器人在它們創建時不是為了不通知用戶,因此并非所有机器人会遵守以上标签,这取决于机器人程序的相关设定。

注:deny为最高优先级,其次是optout,再次是allow,最次是(什么都不填)。

过滤指定的通知

另外一種排除通知法是按通知種類而過濾。在对应页面使用时,则相關類型的通知會被過濾。

使用這種選擇性排除的方法,用戶將不會收到來自指定機器人的指定通知(请注意大小写)。

{{bots|optout=all}}                     过滤所有机器人发出的所有通知
{{bots|optout=voteEnd}}                 过滤U:AnnAngela-abot有关投票结束后至发起人用户讨论页的留言提醒
{{bots|optout=proposalAboutToExpire}}   过滤U:AnnAngela-abot对提案即将超时的通知
{{bots|optout=SIGN}}                    过滤U:星海-adminbot有关签名等问题的提醒
{{bots|optout=anchor-fixing}}           阻止U:星海-adminbot对此页面错误锚点的修复
{{bots|optout=fileInfo}}                过滤U:机娘星海酱对错误填写文件上传信息的提醒

以上選項可通过半角逗號間隔相加使用,例如:

{{bots|optout=voteEnd,SIGN}} 

限制

有些机器人操作不能以此模板排除,此類操作包括但不限於:

  1. 机器人未支持该模板
  2. 任何不含上方所述标签的通知(若有被遺忘的標籤,請於萌娘百科_talk:讨论版告訴我們。)

机器人识别方法

  • Pywikipediabot於r4096後支持{{bots}}及{{nobots}},然而可用參數將其忽略。
  • 自動維基瀏覽器由3.2.0.0起完全支持{{bots}}及{{nobots}}。另外,將用戶名設置為awb可以拒絕所有自動維基瀏覽器機械人。自動維基瀏覽器亦有選項可忽略這些模板。

处理编译后html代码的范例

本段描述的是处理编译后html代码(从index.php?action=render等入口获取)的范例,内容仅供参考,请在使用前自行验证。

生成的html代码

本模板会将三个参数填入id为botsMessageConfig的元素的data-属性中,效果如下:

<span id="botsMessageConfig" data-allow="{{{allow|}}}" data-deny="{{{deny|}}}" data-optout="{{{optout|}}}"></span>

因此你可以通过查询相关属性来判断是否匹配。

JavaScript

Nodejs可以通过 cheerio 模块来解析html代码,请自行适配。

"use strict";
/**
 * @param {string | undefined} str 
 * @returns 
 */
const splitCommaString = (str) => `${str || ""}`.split(",").map((a) => a.trim()).filter((a) => a.length > 0);
/**
 * 检测是否允许
 * @param {HTMLElement} rootNode 被检测页面的根元素
 * @param {string} user 机器人用户名
 * @param {string} type 机器人通知类型
 * @returns {boolean}
 */
function allowBots(rootNode, user, type) {
    const {
        dataset: {
            allow,
            deny,
            optout,
        },
    } = rootNode.querySelector("#botsMessageConfig") || { dataset: {} };
    if (deny === "all" || optout === "none" || allow === "none") {
        return false;
    }
    if (deny !== "none" && splitCommaString(deny).includes(user)) {
        return false;
    }
    if (optout !== "all" && splitCommaString(optout).includes(type)) {
        return false;
    }
    return true;
}

处理源代码的范例

本段描述的是直接处理源代码(即页面的wikitext,从index.php?action=raw等入口获取)的范例,内容仅供参考,请在使用前自行验证。

PHP
function allowBots( $text ) {
    global $user;
    if (preg_match('/\{\{(nobots|bots\|allow=none|bots\|deny=all|bots\|optout=all|bots\|deny=.*?'.preg_quote($user,'/').'.*?)\}\}/iS',$text)) { return false; }
    return true;
}
Perl
sub allowBots {
    my($text, $user, $opt) = @_;
    return 0 if $text =~ /{{nob[o]ts}}/;
    return 1 if $text =~ /{{b[o]ts}}/;
    if($text =~ /{{bots\s*\|\s*allow\s*=\s*(.*?)\s*}}/s){
        return 1 if $1 eq 'all';
        return 0 if $1 eq 'none';
        my @bots = split(/\s*,\s*/, $1);
        return (grep $_ eq $user, @bots)?1:0;
    }
    if($text =~ /{{bots\s*\|\s*deny\s*=\s*(.*?)\s*}}/s){
        return 0 if $1 eq 'all';
        return 1 if $1 eq 'none';
        my @bots = split(/\s*,\s*/, $1);
        return (grep $_ eq $user, @bots)?0:1;
    }
    if(defined($opt) && $text =~ /{{bots\s*\|\s*optout\s*=\s*(.*?)\s*}}/s){
        return 0 if $1 eq 'all';
        my @opt = split(/\s*,\s*/, $1);
        return (grep $_ eq $opt, @opt)?0:1;
    }
    return 1;
}
C#
public static bool AllowBots(string text, string user)
{
    return !Regex.IsMatch(text, @"\{\{(nobots|bots\|(allow=none|deny=(?!none).*(" + user.Normalize() + @"|all)|optout=all))\}\}", RegexOptions.IgnoreCase);
}
Java
public static boolean AllowBots(String text, String user)
{
      return !Regex.Match(text, "\\{\\{(nobots|bots\\|(allow=none|deny=(.*?" + user.Normalize() + ".*?|all)|optout=all))\\}\\}", RegexOptions.IgnoreCase).Success;
}
JavaScript
function allowBots(text, user){
  if (!new RegExp("\\{\\{\\s*(nobots|bots[^}]*)\\s*\\}\\}", "i").test(text)) return true;
  return (new RegExp("\\{\\{\\s*bots\\s*\\|\\s*deny\\s*=\\s*([^}]*,\\s*)*"+user+"\\s*(?=[,\\}])[^}]*\\s*\\}\\}", "i").test(text)) ? false : new RegExp("\\{\\{\\s*((?!nobots)|bots(\\s*\\|\\s*allow\\s*=\\s*((?!none)|([^}]*,\\s*)*"+user+"\\s*(?=[,\\}])[^}]*|all))?|bots\\s*\\|\\s*deny\\s*=\\s*(?!all)[^}]*|bots\\s*\\|\\s*optout=(?!all)[^}]*)\\s*\\}\\}", "i").test(text);
}
Python
def Allowbots(text, user):
    if (re.search(r'\{\{(nobots|bots\|(allow=none|deny=.*?' + user + r'.*?|optout=all|deny=all))\}\}', text)):
        return False
    return True

參見