├── .gitignore ├── LICENSE ├── README.md ├── app.py ├── config ├── __init__.py └── default.py ├── docs ├── js │ ├── Bangumi - Info Export.user.js │ ├── Byrbt - Auto Thanks.user.js │ ├── Byrbt - BigImg Resize.user.js │ ├── Byrbt - Enhanced log.user.js │ ├── Byrbt - Get Movie Info Directly.user.js │ ├── Byrbt - Give Other Bones.user.js │ ├── Byrbt - IP2Loc.user.js │ ├── Byrbt - Img Check.user.js │ ├── Byrbt - Quote in CKEditor.user.js │ ├── Byrbt - Tree View.user.js │ ├── NEU6 - Info Clone.user.js │ ├── NPUBits - Clone btn in torrents page.user.js │ ├── Putao - Get Movie Info Directly.user.js │ ├── ZXPT - Direct download in Homepage.user.js │ ├── ptsearch.user.js │ └── xauat6 - Remove dead torrents.user.js ├── json │ ├── gen.json │ └── site.json ├── ptanalytics.html ├── ptboard.html ├── ptgen.html └── ptsearch.html ├── modules ├── __init__.py ├── geo │ ├── README.md │ ├── __init__.py │ ├── db │ │ ├── ipv6wry.db │ │ └── qqwry.dat │ └── utils.py ├── infogen │ ├── README.md │ ├── __init__.py │ ├── gen.py │ └── test_gen.py └── ptboard │ ├── README.md │ ├── __init__.py │ ├── db │ └── ptboard_record.sql │ └── script │ ├── analytics_gen.py │ ├── backtracking.py │ └── scrapy_6v.py ├── requirement.txt ├── run.py └── utils └── __init__.py /.gitignore: -------------------------------------------------------------------------------- 1 | # Byte-compiled / optimized / DLL files 2 | __pycache__/ 3 | *.py[cod] 4 | *$py.class 5 | 6 | # C extensions 7 | *.so 8 | 9 | # Distribution / packaging 10 | .Python 11 | env/ 12 | build/ 13 | develop-eggs/ 14 | dist/ 15 | downloads/ 16 | eggs/ 17 | .eggs/ 18 | lib/ 19 | lib64/ 20 | parts/ 21 | sdist/ 22 | var/ 23 | wheels/ 24 | *.egg-info/ 25 | .installed.cfg 26 | *.egg 27 | 28 | # PyInstaller 29 | # Usually these files are written by a python script from a template 30 | # before PyInstaller builds the exe, so as to inject date/other infos into it. 31 | *.manifest 32 | *.spec 33 | 34 | # Installer logs 35 | pip-log.txt 36 | pip-delete-this-directory.txt 37 | 38 | # Unit test / coverage reports 39 | htmlcov/ 40 | .tox/ 41 | .coverage 42 | .coverage.* 43 | .cache 44 | nosetests.xml 45 | coverage.xml 46 | *.cover 47 | .hypothesis/ 48 | 49 | # Translations 50 | *.mo 51 | *.pot 52 | 53 | # Django stuff: 54 | *.log 55 | local_settings.py 56 | 57 | # Flask stuff: 58 | instance/ 59 | .webassets-cache 60 | 61 | # Scrapy stuff: 62 | .scrapy 63 | 64 | # Sphinx documentation 65 | docs/_build/ 66 | 67 | # PyBuilder 68 | target/ 69 | 70 | # Jupyter Notebook 71 | .ipynb_checkpoints 72 | 73 | # pyenv 74 | .python-version 75 | 76 | # celery beat schedule file 77 | celerybeat-schedule 78 | 79 | # SageMath parsed files 80 | *.sage.py 81 | 82 | # dotenv 83 | .env 84 | 85 | # virtualenv 86 | .venv 87 | venv/ 88 | ENV/ 89 | 90 | # Spyder project settings 91 | .spyderproject 92 | .spyproject 93 | 94 | # Rope project settings 95 | .ropeproject 96 | 97 | # mkdocs documentation 98 | /site 99 | 100 | # mypy 101 | .mypy_cache/ 102 | 103 | # Pycharm 104 | .idea 105 | 106 | # This project 107 | userconfig.py 108 | backup/ -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2017 Rhilip 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | > repo停止维护说明: Note of archive this repo 2 | 3 | 因为以下原因: 4 | 5 | 1. Pt-Seach 长时间不做更新,且已有PT助手可以替代,本人也会将精力维护到 [ronggang/PT-Plugin-Plus](https://github.com/ronggang/PT-Plugin-Plus) 6 | 2. Pt-Board 在18年受到压力转为私有状态(仅对知道apikey的继续开放) 7 | 3. Pt-Gen 受到豆瓣关闭API的影响,虽然有apikey的替代方法,但是目前状态不明。且Pt-Gen在之前已转交ourhelp组进行更新,本人原地址`https://api.rhilip.info/tool/movieinfo/gen`,仅作反代转发。 8 | 4. 项目内其他用户脚本功能稳定且无需更新。 9 | 10 | 本repo的全部功能都处于半废状态。故repo即日起停止功能性更新。 11 | 12 | Rhilip 13 | 2019.05.14 14 | 15 | -------------------- 16 | 17 | 本人用的Pt相关辅助程序。 18 | 19 | 如果你只是想要使用本repo中的Pt-Gen部分,请考虑使用他人fork修改的repo: 20 | https://github.com/BFDZ/PT-Gen (相关更新也会优先考虑push到该repo) 21 | 22 | 本repo中的Pt-Search已经处于停更状态,接受他人pr。如果需要使用替代请考虑使用以下fork修改的repo或者`PT助手` 23 | - **https://github.com/ronggang/PT-Plugin-Plus** 24 | - https://github.com/harleybai/PT-help 25 | - https://github.com/Gamma666/PT-help 26 | 27 | 除此以外可以综合搜索的软件可见以下整理 : [PT聚合搜索](https://github.com/ylxb2016/PT-help#pt%E8%81%9A%E5%90%88%E6%90%9C%E7%B4%A2) 28 | -------------------------------------------------------------------------------- /app.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python3 2 | # -*- coding: utf-8 -*- 3 | # Copyright (c) 2017-2020 Rhilip 4 | 5 | import pymysql 6 | 7 | from flask import Flask 8 | from flaskext.mysql import MySQL 9 | from flask_cors import CORS 10 | from flask_caching import Cache 11 | 12 | app = Flask(__name__, instance_relative_config=True) 13 | app.config.from_object('config') 14 | app.config.from_pyfile('config.py') 15 | 16 | 17 | class Database(MySQL): 18 | def exec(self, sql: str, args=None, r_dict: bool = False, fetch_all: bool = False, ret_row: bool = False): 19 | db = self.get_db() 20 | cursor = db.cursor(pymysql.cursors.DictCursor) if r_dict else db.cursor() # Cursor type 21 | row = cursor.execute(sql, args) 22 | data = cursor.fetchall() if fetch_all else cursor.fetchone() # The lines of return info (one or all) 23 | 24 | return (row, data) if ret_row else data 25 | 26 | 27 | mysql = Database(app=app, autocommit=True) 28 | cache = Cache(app) 29 | 30 | CORS(app) 31 | -------------------------------------------------------------------------------- /config/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python3 2 | # -*- coding: utf-8 -*- 3 | # Copyright (c) 2017-2020 Rhilip 4 | -------------------------------------------------------------------------------- /config/default.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python3 2 | # -*- coding: utf-8 -*- 3 | # Copyright (c) 2017-2020 Rhilip 4 | 5 | # Database 6 | MYSQL_DATABASE_HOST = 'localhost' 7 | MYSQL_DATABASE_PORT = 3306 8 | MYSQL_DATABASE_USER = None 9 | MYSQL_DATABASE_PASSWORD = None 10 | MYSQL_DATABASE_DB = None 11 | MYSQL_DATABASE_CHARSET = "utf8" 12 | MYSQL_USE_UNICODE = True 13 | 14 | # PT Board 15 | PTBOARD_SEARCH = "" 16 | PTBOARD_SITE = "" 17 | PTBOARD_NO_SITE = "" 18 | PTBOARD_ORDER = "desc" 19 | PTBOARD_LIMIT = 100 20 | PTBOARD_OFFSET = 0 21 | PTBOARD_START_TIME = 0 22 | PTBOARD_END_TIME = "CURRENT_TIMESTAMP" 23 | 24 | # Cache 25 | CACHE_TYPE = 'simple' 26 | -------------------------------------------------------------------------------- /docs/js/Bangumi - Info Export.user.js: -------------------------------------------------------------------------------- 1 | // ==UserScript== 2 | // @name Bangumi Info Export 3 | // @namespace blog.rhilip.info 4 | // @version 20180306 5 | // @description Export Anime Info form Bangumi as BBCode or Html 6 | // @author Rhilip 7 | // @include /^https?:\/\/(bgm\.tv|bangumi\.tv|chii\.in)\/subject\// 8 | // @grant GM_setClipboard 9 | // @updateURL https://github.com/Rhilip/PT-help/raw/master/docs/js/Bangumi%20-%20Info%20Export.user.js 10 | // ==/UserScript== 11 | 12 | //////////////////////////////////////////////////////////////// 13 | // 以下为自定义输出参数,请按照说明修改 14 | const STAFFSTART = 4; // 读取Staff栏的起始位置(假定bgm的顺序为中文名、话数、放送开始、放送星期... ,staff从第四个 导演 起算);初始值为 4 15 | const STAFFNUMBER = 9; // 读取Staff栏数目;初始9,可加大,溢出时按最大可能的staff数读取,如需读取全部请设置值为 Number.MAX_VALUE (或一个你觉得可能最大的值 eg.20) 16 | const MENU = ["STORY : ", "STAFF : ", "CAST : "]; //输出Menu控制(大小写?) 17 | const STYLE = { 18 | "UBB": { // !--预设BBCode生成样式 19 | before: "[b]", // before && after 放在 MENU字段 前后 20 | after: "[/b]", // 请保证before after 自闭合 21 | linedivision: "\n", //行间分割控制 22 | sectiondivision: "\n\n" //段间分割控制 23 | }, 24 | "HTML": { // !--预设Html生成样式 25 | before: "", 26 | after: '', 27 | linedivision: "
", 28 | sectiondivision: "

" 29 | } 30 | }; 31 | const OUTFORMAT = "UBB"; //默认输出格式(在不点击输出格式的情况下);初始UBB,可选 "HTML" "NONE"(不自动生成,点击输出) 32 | //////////////////////////////////////////////////////////////// 33 | 34 | // Begin~ 35 | $(document).ready(function () { 36 | // 创建初始交互按钮与交互窗口 37 | $("div#headerSubject > div > ul >li:last").after(""); 38 | $('').insertBefore('#output'); 39 | tb_init('a.infogen'); //Re-init the element we just inserted. 40 | 41 | //数据获取 42 | var img = $("div#bangumiInfo > div > div:nth-child(1) > a > img").attr("src").replace(/cover\/[lcmsg]/, "cover/l"); 43 | var story = $("div#subject_summary").text(); //Story 44 | var raw_staff = [], staff_box = $("ul#infobox"); //Staff 45 | for (var staff_number = STAFFSTART; staff_number < Math.min(STAFFNUMBER + STAFFSTART, staff_box.children("li").length); staff_number++) { 46 | raw_staff[staff_number - STAFFSTART] = staff_box.children("li").eq(staff_number).text(); 47 | //console.log(raw_staff[staff_number]); 48 | } 49 | var raw_cast = [], cast_box = $("ul#browserItemList"); //Cast 50 | for (var cast_number = 0; cast_number < cast_box.children("li").length; cast_number++) { //cast_box.children("li").length 51 | var cast_name = cast_box.children("li").eq(cast_number).find("span.tip").text(); 52 | if (!(cast_name.length)) { //如果不存在中文名,则用cv日文名代替 53 | cast_name = cast_box.children("li").eq(cast_number).find("div > strong > a").text().replace(/(^\s*)|(\s*$)/g, ""); //#browserItemList > li > div > strong > a 54 | } 55 | var cv_name = cast_box.children("li").eq(cast_number).find("span.tip_j > a").text(); 56 | raw_cast[cast_number] = cast_name + ' : ' + cv_name; 57 | //console.log(raw_cast[cast_number]); 58 | } 59 | 60 | //生成输出信息 61 | $("a[id^='Outto']").click(function () { 62 | var style = $(this).attr("data-style"); 63 | var descr = ((style === "UBB") ? ("[img]" + img + "[/img]") : ("")) + STYLE[style].sectiondivision + 64 | STYLE[style].before + MENU[0] + STYLE[style].after + STYLE[style].linedivision + 65 | story + STYLE[style].sectiondivision + 66 | STYLE[style].before + MENU[1] + STYLE[style].after + STYLE[style].linedivision + 67 | raw_staff.join(STYLE[style].linedivision) + STYLE[style].sectiondivision + 68 | STYLE[style].before + MENU[2] + STYLE[style].after + STYLE[style].linedivision + 69 | raw_cast.join(STYLE[style].linedivision) + STYLE[style].sectiondivision + 70 | "(来源于 " + window.location.href + " )" + STYLE[style].linedivision; 71 | $("#Out_text").val(descr).select(); // 向输出框填入合成的信息并自动全选 72 | GM_setClipboard(descr); // 向剪贴板输出合成的信息 73 | }); 74 | 75 | $('#Outto' + OUTFORMAT).click(); 76 | }); 77 | 78 | /** 79 | * Created by Rhilip on 2016/12/21. 80 | * version: 81 | * 20161222 写出了第一个版本的,大体实现了原来想要的所有功能。 82 | * 20170105 发现没有开启点击遮罩层关闭窗口的功能,补上。其他没变~ 83 | * 20170722 使用GM_setClipboard在输出时直接复制到剪贴板中。 84 | * 20180109 修正一个未启用的功能的typeerror。 85 | * 20180305 使用Bangumi自带的tb_init来生成浮动窗口 86 | */ 87 | -------------------------------------------------------------------------------- /docs/js/Byrbt - Auto Thanks.user.js: -------------------------------------------------------------------------------- 1 | // ==UserScript== 2 | // @name Byrbt : Auto thanks torrent's uploader 3 | // @namespace http://blog.rhilip.info 4 | // @version 20180304 5 | // @description 自动感谢种子发布者 6 | // @author Rhilip 7 | // @match http*://bt.byr.cn/details.php* 8 | // @icon http://bt.byr.cn/favicon.ico 9 | // @grant none 10 | // @updateURL https://github.com/Rhilip/PT-help/raw/master/docs/js/Byrbt%20-%20Auto%20Thanks.user.js 11 | // ==/UserScript== 12 | 13 | // == Control Options == 14 | var AutoThx = 1; //Auto Click thanks button (2 - Thanks all;1 - Just thanks yourself;0 - No thanks) 15 | 16 | // == Main part == 17 | $(document).ready(function () { 18 | var thxBtn = $("#saythanks[value*='说谢谢']"); 19 | switch (AutoThx) { 20 | case 0: 21 | break; 22 | case 1: 23 | if (($("td#outer > table > tbody > tr:nth-child(1) > td.rowfollow > span > a > b").text()) === ($("table#info_block > tbody > tr > td > table > tbody > tr > td:nth-child(1) > span > span > a > b").text())) { 24 | thxBtn.parent().siblings(":last").after('
Auto_thanks Powered by Byrbt MOD help
'); 25 | thxBtn.click(); 26 | } 27 | break; 28 | case 2: 29 | thxBtn.parent().siblings(":last").after('
Auto_thanks Powered by Byrbt MOD help
'); 30 | thxBtn.click(); 31 | break; 32 | } 33 | }); 34 | 35 | /** 36 | * Created by Rhilip on 2016/11/21. 37 | */ 38 | -------------------------------------------------------------------------------- /docs/js/Byrbt - BigImg Resize.user.js: -------------------------------------------------------------------------------- 1 | // ==UserScript== 2 | // @name Byrbt : Big Img Resize 3 | // @namespace http://blog.rhilip.info 4 | // @version 20180304 5 | // @description For the too width img in byrbt 6 | // @author Rhilip 7 | // @match http*://bt.byr.cn/details.php* 8 | // @icon http://bt.byr.cn/favicon.ico 9 | // @supportURL http://bt.byr.cn/forums.php?action=viewtopic&topicid=10609 10 | // @updateURL https://github.com/Rhilip/PT-help/raw/master/docs/js/Byrbt%20-%20BigImg%20Resize.user.js 11 | // ==/UserScript== 12 | 13 | var ControlWidth = 1080; 14 | 15 | $(document).ready(function () { 16 | $("div#kdescr img").each(function () { 17 | var img = $(this); 18 | var width = img.width(); 19 | var orginstyle = img.attr("style"); 20 | if (width > ControlWidth) { 21 | img.attr("style", "max-width: 100%;"); 22 | img.click(function () { 23 | if (img.attr("style") === "max-width: 100%;") { 24 | img.attr("style", orginstyle); 25 | } else { 26 | img.attr("style", "max-width: 100%;"); 27 | } 28 | }); 29 | } 30 | }); 31 | }); 32 | 33 | 34 | /** 35 | * Created by Rhilip on 2017/1/18. 36 | */ 37 | -------------------------------------------------------------------------------- /docs/js/Byrbt - Enhanced log.user.js: -------------------------------------------------------------------------------- 1 | // ==UserScript== 2 | // @name Byrbt : Enhanced log 3 | // @namespace http://blog.rhilip.info 4 | // @version 20180304 5 | // @description 为log页面增加为有关种子(字幕)添加访问链接和快速搜索关键词,针对管理员设置种子优惠的情况能直接查询优惠类型;在种子页面的热度表中添加种子日志查询入口 6 | // @author Rhilip 7 | // @match http*://bt.byr.cn/details.php?id=* 8 | // @include /^https?:\/\/bt\.byr\.cn\/log\.php((\?query\=.+)?(\?action\=dailylog(.+?)?(\&page\=\d+)?$|$))/ 9 | // @icon http://bt.byr.cn/favicon.ico 10 | // @updateURL https://github.com/Rhilip/PT-help/raw/master/docs/js/Byrbt%20-%20Enhanced%20log.user.js 11 | // ==/UserScript== 12 | 13 | $(document).ready(function () { 14 | if (location.pathname === "/log.php") { 15 | $("form").after("常用快捷搜索关键词:" + 16 | "(Offer) was added by  " + 17 | "(Torrent) was uploaded by  " + 18 | "(Torrent) was edited by  " + 19 | "(Torrent) was deleted by  " + 20 | "首页置顶种子(竞价置顶)  " + 21 | "批量置顶了种子  " + 22 | "批量设置了种子优惠  " + 23 | "Mod Edit  " + 24 | "allowed offer  "); 25 | 26 | $("td#outer > table:last > tbody tr").each(function () { 27 | var tr = $(this); 28 | if (tr.find('td:nth-child(2) > font').length) { 29 | var logfont = tr.find('td:nth-child(2) > font'); 30 | var logtext = logfont.text(); 31 | if (logtext.match((/Torrent (\d+) \((.+)\)/)) && logtext.match(/edited|uploaded/)) { // (torrent) uploaded,edited,deleted 32 | var tid = logtext.match(/Torrent (\d+)/)[1]; 33 | logfont.html(logtext.replace(/(\((.+?])\))/, "$1")); 34 | logfont.parent().append("快速编辑"); 35 | } 36 | if (logtext.match(/批量/)) { // 批量设置了种子优惠|批量置顶了种子|批量取消了置顶 37 | logfont.html(logtext.replace(/(\d+),/g, "$1,")); 38 | logfont.parent().append("
查询优惠类型
"); 39 | } 40 | if (logtext.match(/Subtitle/)) { // subtitle 41 | logfont.html(logtext.replace(/\((.+?)\)/, "($1)")); 42 | } 43 | if (logtext.match(/首页置顶种子/)) { 44 | logfont.html(logtext.replace(/] (\[.+?])成功/, "] $1成功")); 45 | } 46 | } 47 | }); 48 | 49 | 50 | $("div.foundbuff").one("click", function () { //查询种子优惠 51 | var foundbuff = $(this); 52 | var tid = foundbuff.siblings("font").text().match(/(\d+)/)[1]; 53 | $.get('details.php?id=' + tid + '&hit=1', function (resp) { 54 | var body = resp.match(/]*>[\s\S]*<\/body>/gi)[0]; 55 | var buff = $(body).find("h1#share > b").text(); 56 | foundbuff.text(buff); 57 | }); 58 | }); 59 | $("td#outer > table:last > tbody tr:first > td:nth-child(2)").append("
批量查询该页优惠类型
"); 60 | $("div.foundbuff_all").click(function () { 61 | $("div.foundbuff").click(); 62 | }); 63 | } 64 | 65 | if (location.pathname === "/details.php") { 66 | $("td.no_border_wide:last").after("种子日志:[查看日志]") 67 | .parents("td").append(""); 68 | $("#log").click(function () { 69 | var logbtn = $(this); 70 | var loglist = $("#loglist"); 71 | if (logbtn.text() === "[查看日志]") { 72 | if (loglist.html()) { 73 | loglist.show(); 74 | } else { 75 | var tid = location.href.match(/id=(\d+)/)[1]; 76 | $.get('/log.php?query=' + tid + '&search=all&action=dailylog', function (resp) { 77 | var body = resp.match(/]*>[\s\S]*<\/body>/gi)[0]; 78 | var table = $(body).find("#outer > table:last").removeAttr("width"); 79 | loglist.html(table); 80 | }); 81 | } 82 | logbtn.text("[隐藏日志]"); 83 | } else { 84 | loglist.hide(); 85 | logbtn.text("[查看日志]"); 86 | } 87 | }); 88 | } 89 | }); 90 | 91 | 92 | /** 93 | * Created by Rhilip on 01/22/17. 94 | */ 95 | -------------------------------------------------------------------------------- /docs/js/Byrbt - Give Other Bones.user.js: -------------------------------------------------------------------------------- 1 | // ==UserScript== 2 | // @name Byrbt : Give Other Bonus 3 | // @namespace http://blog.rhilip.info 4 | // @version 20180304 5 | // @description You can give any number of Bones you want(not 25,50,100,200,400) to torrent's owner 6 | // @author Rhilip 7 | // @match http*://bt.byr.cn/details.php* 8 | // @icon http://bt.byr.cn/favicon.ico 9 | // @updateURL https://github.com/Rhilip/PT-help/raw/master/docs/js/Byrbt%20-%20Give%20Other%20Bones.user.js 10 | // ==/UserScript== 11 | 12 | $(document).ready(function () { 13 | 14 | $('td.rowfollow').find('input[id^=thankbutton]:last').after(' For Other Number: '); 15 | var torId = location.href.match(/id=(\d+)/)[1]; 16 | var bonus0 = $("#thankbutton25").attr("onclick").match(/,((\d*|0).\d*)\)/)[1]; 17 | var bonustext = $('input[type="text"][name="gift"]'); 18 | 19 | $('input#thankbuttonother').click(function () { 20 | givebonus(torId, bonustext.val(), bonus0); 21 | }); 22 | 23 | }); 24 | 25 | /** 26 | * Created by Rhilip on 2017/1/18. 27 | */ 28 | -------------------------------------------------------------------------------- /docs/js/Byrbt - IP2Loc.user.js: -------------------------------------------------------------------------------- 1 | // ==UserScript== 2 | // @name Byrbt : IP2Loc 3 | // @namespace http://blog.rhilip.info 4 | // @version 20180304 5 | // @description It's an userscript show peer's loc due to their IPv6 address(,only for uesrs who's Level is highter than Moderator) 6 | // @author Rhilip 7 | // @match http*://bt.byr.cn/* 8 | // @icon http://bt.byr.cn/favicon.ico 9 | // @updateURL https://github.com/Rhilip/PT-help/raw/master/docs/js/Byrbt%20-%20IP2Loc.user.js 10 | // ==/UserScript== 11 | 12 | function trueIp(ip) { 13 | return ip.match(/(25[0-5]|2[0-4]\d|[0-1]\d{2}|[1-9]?\d)\.(25[0-5]|2[0-4]\d|[0-1]\d{2}|[1-9]?\d)\.(25[0-5]|2[0-4]\d|[0-1]\d{2}|[1-9]?\d)\.(25[0-5]|2[0-4]\d|[0-1]\d{2}|[1-9]?\d)/) || ip.match(/^\s*((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:)))(%.+)?\s*$/); //Check IPv4 or IPv6 address 14 | } 15 | 16 | $(document).ready(function () { 17 | if (location.pathname == "/details.php") { 18 | $('span#hidepeer > a').after('
[地点查询]'); 19 | $('a#toloc').click(function () { 20 | $("div#peerlist > table > tbody > tr > td:nth-child(1) > br").remove(); //Display Peer's name in a row,Please Make sure you NEED or not! 21 | var maintable = $('div#peerlist > table > tbody > tr > td:nth-child(2)'); 22 | maintable.each(function () { 23 | var node = $(this); 24 | var ip = node.text(); 25 | if (trueIp(ip)) { 26 | var url = 'http://pytool.sinaapp.com/geo?type=json&encoding=utf-8&ip=' + ip; 27 | $.getJSON(url, function (data) { 28 | node.text(data.geo.loc); 29 | node.attr("title", data.geo.ip); 30 | }); 31 | } 32 | node.attr("width", "9%"); 33 | }); 34 | }); 35 | } 36 | //In page viewsnatches.php and iphistory.php(Automatically) 37 | if (location.pathname == "/viewsnatches.php" || location.pathname == "/iphistory.php") { 38 | var maintable = $("td#outer > table.main > tbody > tr > td > table > tbody > tr > td:nth-child(2)"); 39 | maintable.each(function () { 40 | var node = $(this); 41 | var ip = node.text(); 42 | if (trueIp(ip)) { 43 | var url = 'http://pytool.sinaapp.com/geo?type=json&encoding=utf-8&ip=' + ip; 44 | $.getJSON(url, function (data) { 45 | if (location.pathname == "/viewsnatches.php") { 46 | node.html(ip + "
" + "(" + data.geo.loc + ")"); 47 | } else if (location.pathname == "/iphistory.php") { 48 | node.after("" + data.geo.loc + ""); 49 | } 50 | }); 51 | } else { 52 | if (location.pathname == "/viewsnatches.php") { 53 | node.text("IP/地点"); 54 | } else if (location.pathname == "/iphistory.php") { 55 | node.parents("table:eq(0)").attr("width", "600"); 56 | node.after('地点'); 57 | } 58 | } 59 | }); 60 | } 61 | }); 62 | 63 | /** 64 | * Created by Rhili on 5/17/2017. 65 | */ 66 | -------------------------------------------------------------------------------- /docs/js/Byrbt - Img Check.user.js: -------------------------------------------------------------------------------- 1 | // ==UserScript== 2 | // @name Byrbt : Img Check 3 | // @namespace http://blog.rhilip.info 4 | // @version 20180304 5 | // @description 检查外链图片、未完全显示的图片数目 6 | // @author Rhilip 7 | // @match http*://bt.byr.cn/details.php?id=* 8 | // @match http*://bt.byr.cn/offers.php?id=* 9 | // @icon http://bt.byr.cn/favicon.ico 10 | // @updateURL https://github.com/Rhilip/PT-help/raw/master/docs/js/Byrbt%20-%20Img%20Check.user.js 11 | // ==/UserScript== 12 | 13 | $(document).ready(function () { 14 | 15 | var infoNode = $("div#kdescr"); 16 | 17 | var totalimg = infoNode.find("img").length; 18 | 19 | infoNode.find("img[src*='file:///']").addClass("Unupimg"); // 未完成上传的图片 20 | infoNode.find("img[src^='data:image']").addClass("Unupimg"); // 使用Base64编码的图片 21 | var unupimg = infoNode.find("img.Unupimg").length; 22 | 23 | infoNode.find("img[src*='byr.cn']").addClass("Inbyrimg"); // 域名在byr的图片 24 | infoNode.find("img[src*='ckfinder']").addClass("Inbyrimg"); // 为以防万一,使用相对地址的图片 25 | var outimg = totalimg - infoNode.find("img.Inbyrimg").length; 26 | 27 | infoNode.closest("tr").before('图片检查该种子简介共用 ' + totalimg + ' 张图片,其中可能有 ' + outimg + ' 张外链图'); 28 | if (outimg) { 29 | $('span#outimg').attr("style", "color:#ff0000;"); 30 | if (unupimg) { 31 | $('span#unupimghide').show(); 32 | } 33 | 34 | var table_html = ""; 35 | infoNode.find("img").each(function () { 36 | var src = $(this).attr("src"); 37 | table_html += "" + src + ""; 38 | }); 39 | $("table#img_check_table").html(table_html); 40 | $("span#img_check").show(); 41 | } 42 | }); 43 | 44 | /** 45 | * Created by Rhilip on 2016/11/21. 46 | * Update history: 47 | * 2017.10.15 更新判断逻辑(时隔将近一年之后233333) 48 | * 2017.10.14 在可能存在外链图的情况下,通过表格显示所有使用的图片的链接。 49 | */ 50 | -------------------------------------------------------------------------------- /docs/js/Byrbt - Quote in CKEditor.user.js: -------------------------------------------------------------------------------- 1 | // ==UserScript== 2 | // @name Byrbt : Quote in CKEditor 3 | // @namespace http://blog.rhilip.info 4 | // @version 20190223 5 | // @description 为BYRBT的编辑器添加代码(code)引用框 6 | // @author Rhilip 7 | // @match http*://bt.byr.cn/edit.php* 8 | // @match http*://bt.byr.cn/upload.php* 9 | // @match http*://bt.byr.cn/offers.php* 10 | // @icon http://bt.byr.cn/favicon.ico 11 | // @require https://cdn.jsdelivr.net/npm/jquery-simplemodal@1.0.0/src/jquery.simplemodal.js 12 | // @updateURL https://github.com/Rhilip/PT-help/raw/master/docs/js/Byrbt%20-%20Quote%20in%20CKEditor.user.js 13 | // ==/UserScript== 14 | 15 | const DEFAULT_STYLE = [ 16 | { 17 | "name": "类似其他PT站的代码格式", 18 | "style": "
{0}
{1}
", 19 | }, { 20 | "name": "类似其他PT站的引用格式", 21 | "style": "
{0}
{1}
", 22 | }, { 23 | "name": "@DoxHead个人美化版", 24 | "style": "
 {0} {1}
", 25 | "checked": true 26 | }, { 27 | "name": "类似TTG的引用格式", 28 | "style": "
{0}
{1}
", 29 | }, { 30 | "name": "本站块引用增强", 31 | "style": "

{0}

{1}
", 32 | }, { 33 | "name": "本站表格增强", 34 | "style": "
{0}
{1}
", 35 | } 36 | ]; 37 | 38 | const CODE_IMG = "data:image/svg+xml;utf8;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0iaXNvLTg4NTktMSI/Pgo8IS0tIEdlbmVyYXRvcjogQWRvYmUgSWxsdXN0cmF0b3IgMTYuMC4wLCBTVkcgRXhwb3J0IFBsdWctSW4gLiBTVkcgVmVyc2lvbjogNi4wMCBCdWlsZCAwKSAgLS0+CjwhRE9DVFlQRSBzdmcgUFVCTElDICItLy9XM0MvL0RURCBTVkcgMS4xLy9FTiIgImh0dHA6Ly93d3cudzMub3JnL0dyYXBoaWNzL1NWRy8xLjEvRFREL3N2ZzExLmR0ZCI+CjxzdmcgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB4bWxuczp4bGluaz0iaHR0cDovL3d3dy53My5vcmcvMTk5OS94bGluayIgdmVyc2lvbj0iMS4xIiBpZD0iQ2FwYV8xIiB4PSIwcHgiIHk9IjBweCIgd2lkdGg9IjE2cHgiIGhlaWdodD0iMTZweCIgdmlld0JveD0iMCAwIDUyMi40NjggNTIyLjQ2OSIgc3R5bGU9ImVuYWJsZS1iYWNrZ3JvdW5kOm5ldyAwIDAgNTIyLjQ2OCA1MjIuNDY5OyIgeG1sOnNwYWNlPSJwcmVzZXJ2ZSI+CjxnPgoJPGc+CgkJPHBhdGggZD0iTTMyNS43NjIsNzAuNTEzbC0xNy43MDYtNC44NTRjLTIuMjc5LTAuNzYtNC41MjQtMC41MjEtNi43MDcsMC43MTVjLTIuMTksMS4yMzctMy42NjksMy4wOTQtNC40MjksNS41NjhMMTkwLjQyNiw0NDAuNTMgICAgYy0wLjc2LDIuNDc1LTAuNTIyLDQuODA5LDAuNzE1LDYuOTk1YzEuMjM3LDIuMTksMy4wOSwzLjY2NSw1LjU2OCw0LjQyNWwxNy43MDEsNC44NTZjMi4yODQsMC43NjYsNC41MjEsMC41MjYsNi43MS0wLjcxMiAgICBjMi4xOS0xLjI0MywzLjY2Ni0zLjA5NCw0LjQyNS01LjU2NEwzMzIuMDQyLDgxLjkzNmMwLjc1OS0yLjQ3NCwwLjUyMy00LjgwOC0wLjcxNi02Ljk5OSAgICBDMzMwLjA4OCw3Mi43NDcsMzI4LjIzNyw3MS4yNzIsMzI1Ljc2Miw3MC41MTN6IiBmaWxsPSIjOTFEQzVBIi8+CgkJPHBhdGggZD0iTTE2Ni4xNjcsMTQyLjQ2NWMwLTIuNDc0LTAuOTUzLTQuNjY1LTIuODU2LTYuNTY3bC0xNC4yNzctMTQuMjc2Yy0xLjkwMy0xLjkwMy00LjA5My0yLjg1Ny02LjU2Ny0yLjg1NyAgICBzLTQuNjY1LDAuOTU1LTYuNTY3LDIuODU3TDIuODU2LDI1NC42NjZDMC45NSwyNTYuNTY5LDAsMjU4Ljc1OSwwLDI2MS4yMzNjMCwyLjQ3NCwwLjk1Myw0LjY2NCwyLjg1Niw2LjU2NmwxMzMuMDQzLDEzMy4wNDQgICAgYzEuOTAyLDEuOTA2LDQuMDg5LDIuODU0LDYuNTY3LDIuODU0czQuNjY1LTAuOTUxLDYuNTY3LTIuODU0bDE0LjI3Ny0xNC4yNjhjMS45MDMtMS45MDIsMi44NTYtNC4wOTMsMi44NTYtNi41NyAgICBjMC0yLjQ3MS0wLjk1My00LjY2MS0yLjg1Ni02LjU2M0w1MS4xMDcsMjYxLjIzM2wxMTIuMjA0LTExMi4yMDFDMTY1LjIxNywxNDcuMTMsMTY2LjE2NywxNDQuOTM5LDE2Ni4xNjcsMTQyLjQ2NXoiIGZpbGw9IiM5MURDNUEiLz4KCQk8cGF0aCBkPSJNNTE5LjYxNCwyNTQuNjYzTDM4Ni41NjcsMTIxLjYxOWMtMS45MDItMS45MDItNC4wOTMtMi44NTctNi41NjMtMi44NTdjLTIuNDc4LDAtNC42NjEsMC45NTUtNi41NywyLjg1N2wtMTQuMjcxLDE0LjI3NSAgICBjLTEuOTAyLDEuOTAzLTIuODUxLDQuMDktMi44NTEsNi41NjdzMC45NDgsNC42NjUsMi44NTEsNi41NjdsMTEyLjIwNiwxMTIuMjA0TDM1OS4xNjMsMzczLjQ0MiAgICBjLTEuOTAyLDEuOTAyLTIuODUxLDQuMDkzLTIuODUxLDYuNTYzYzAsMi40NzgsMC45NDgsNC42NjgsMi44NTEsNi41N2wxNC4yNzEsMTQuMjY4YzEuOTA5LDEuOTA2LDQuMDkzLDIuODU0LDYuNTcsMi44NTQgICAgYzIuNDcxLDAsNC42NjEtMC45NTEsNi41NjMtMi44NTRMNTE5LjYxNCwyNjcuOGMxLjkwMy0xLjkwMiwyLjg1NC00LjA5NiwyLjg1NC02LjU3ICAgIEM1MjIuNDY4LDI1OC43NTUsNTIxLjUxNywyNTYuNTY1LDUxOS42MTQsMjU0LjY2M3oiIGZpbGw9IiM5MURDNUEiLz4KCTwvZz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8Zz4KPC9nPgo8L3N2Zz4K"; 39 | 40 | // Add format function for string~ 41 | if (!String.prototype.format) { 42 | String.prototype.format = function () { 43 | var args = arguments; 44 | return this.replace(/{(\d+)}/g, function (match, number) { 45 | return typeof args[number] !== 'undefined' ? args[number] : match; 46 | }); 47 | }; 48 | } 49 | 50 | CKEDITOR.on('instanceReady', function (evt) { 51 | $("#cke_52").after(''.format(CODE_IMG)); 52 | var code_btn = $("#cke_55"); 53 | code_btn.click(function () { 54 | // Generate the modal code 55 | var code = '