您需要先安装一个扩展,例如 篡改猴、Greasemonkey 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 Userscripts ,之后才能安装此脚本。
您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。
您需要先安装用户脚本管理器扩展后才能安装此脚本。
add button to douban to delete follower
// ==UserScript== // @name douban one click blacklist // @namespace https://github.com/harryhare/ // @version 0.0.4 // @description add button to douban to delete follower // @author harryhare // @license GPL 3.0 // @icon https://raw.githubusercontent.com/harryhare/userscript/master/index.png // @match https://www.douban.com/** // @grant none // ==/UserScript== var buttons_map = {};//userid,buttons list var user_id_map = {}; var blacklist_set = new Set(); var ck = ""; var page_url = ""; const url_ban = "https://www.douban.com/j/contact/addtoblacklist"; const url_unban = "https://www.douban.com/j/contact/unban"; //time delay var interval = 2000; var interval_id; const ban_text = "加入黑名单"; const unban_text = "移出黑名单"; const banning_text = "正在加入黑名单..."; const unbanning_text = "正在移出黑名单..."; const error_text = "失败请重试"; function getCookie(c_name) { if (document.cookie.length > 0) { var c_start = document.cookie.indexOf(c_name + "="); if (c_start !== -1) { c_start = c_start + c_name.length + 1; var c_end = document.cookie.indexOf(";", c_start); if (c_end === -1) c_end = document.cookie.length; return unescape(document.cookie.substring(c_start, c_end)); } } return ""; } async function ban_simple(user_name) { let user_id = await get_real_user_id(user_name); var xmlhttp = new XMLHttpRequest(); var data = "people=" + user_id + "&ck=" + ck; xmlhttp.open("POST", url_ban, true); xmlhttp.setRequestHeader("Content-Type", "application/x-www-form-urlencoded"); xmlhttp.onload = function () { if (this.status === 200) { console.log(`拉黑${user_name}成功`); } else { console.log(`拉黑${user_name}失败`); } }; xmlhttp.onerror = function () { console.log(`拉黑${user_name}失败`); }; xmlhttp.send(data); } async function ban(user_name, node) { let user_id = await get_real_user_id(user_name); var xmlhttp = new XMLHttpRequest(); var url = url_ban; var data = "people=" + user_id + "&ck=" + ck; console.log('ban:', data); node.innerHTML = banning_text; xmlhttp.open("POST", url, true); xmlhttp.setRequestHeader("Content-Type", "application/x-www-form-urlencoded"); xmlhttp.onreadystatechange = function () { if (xmlhttp.readyState === 4) { if (xmlhttp.status === 200) { //node.innerHTML = "已加入黑名单"; let buttons = buttons_map[user_name]; blacklist_set.add(user_name); for (let i = 0; i < buttons.length; i++) { buttons[i].innerHTML = unban_text; } } else { node.innerHTML = error_text; } } }; xmlhttp.send(data); } async function unban(user_name, node) { let user_id = await get_real_user_id(user_name); var xmlhttp = new XMLHttpRequest(); var url = url_unban; var data = "people=" + user_id + "&ck=" + ck; console.log('unban:', data); node.innerHTML = unbanning_text; xmlhttp.open("POST", url, true); xmlhttp.setRequestHeader("Content-Type", "application/x-www-form-urlencoded"); xmlhttp.onreadystatechange = function () { if (xmlhttp.readyState === 4) { if (xmlhttp.status === 200) { //node.innerHTML = "已加入黑名单"; let buttons = buttons_map[user_name]; blacklist_set.delete(user_name); for (let i = 0; i < buttons.length; i++) { buttons[i].innerHTML = ban_text; } } else { node.innerHTML = error_text; } } }; xmlhttp.send(data); } async function add_to_blacklist(e) { if (e.target.innerHTML === unban_text) { await unban(e.target.getAttribute("user-id"), e.target); } else { await ban(e.target.getAttribute("user-id"), e.target); } } function get_blacklist_button(user_id, style) { let b = document.createElement('a'); b.setAttribute("user-id", user_id); if (blacklist_set.has(user_id)) { b.innerHTML = unban_text; } else { b.innerHTML = ban_text; } b.style = style; b.onclick = add_to_blacklist; if (user_id in buttons_map) { buttons_map[user_id].push(b); } else { buttons_map[user_id] = [b]; } return b } function check_user_link(href) { const status_reg = /https:\/\/www\.douban\.com\/people\/[^\/]+\/?$/; return status_reg.test(href); } function get_user_id_from_url(href) { if (href[href.length - 1] === "/") { href = href.substr(0, href.length - 1) } const j = href.lastIndexOf("/"); return href.substr(j + 1, href.length - j); } // 评论,日志和广播 function process_comment() { function process_item(item) { let a = item.children[0]; let href = a.href; let name = a.title; let user_id = get_user_id_from_url(a.href); let b = get_blacklist_button(user_id, "margin-left:10px"); // 如果回复已被投诉则没有投诉那一排按钮 let action_bars = item.parentElement.querySelectorAll("div.action-bar-group"); if (action_bars.length > 0) { action_bars[0].append(b); } } let items = document.querySelectorAll("div.item .meta-header"); for (let i = 0; i < items.length; i++) { process_item(items[i]); } function callback(records) { records.map(function (record) { if (record.addedNodes.length !== 0) { for (var i = 0; i < record.addedNodes.length; i++) { var node = record.addedNodes[i]; if (node.className === "item reply-item") {//meta-head不行 //console.log(node); var items = node.querySelectorAll("div.item .meta-header"); //console.log(items); for (let i = 0; i < items.length; i++) { process_item(items[i]); } } } } }); } var mo = new MutationObserver(callback); var option = { 'childList': true, 'subtree': true, }; mo.observe(document.body, option); } // 小组 回复 function process_comment_group() { let items = document.querySelectorAll("div.operation-div"); for (let i = 0; i < items.length; i++) { let item = items[i]; let user_id = item.id; let b = get_blacklist_button(user_id, "color: #aaa; margin-right:10px"); let containers = item.querySelectorAll("div.operation-more"); if(containers.length>0) { containers[0].append(b); } } } function sleep(ms) { return new Promise(resolve => setTimeout(resolve, ms)); } function makeRequest(url) { return new Promise(function (resolve, reject) { let xhr = new XMLHttpRequest(); xhr.open("GET", url); xhr.onload = function () { if (this.status === 200) { resolve(xhr.response); } else { reject({ status: this.status, statusText: xhr.statusText }); } }; xhr.onerror = function () { reject({ status: this.status, statusText: xhr.statusText }); }; xhr.send(); }); } async function get_real_user_id(user_name) { const user_id_reg = /^\d{6,}$/; if (user_id_reg.test(user_name)) { return user_name; } if (user_name in user_id_map) { return user_id_map[user_name]; } let url = `https://www.douban.com/people/${user_name}/`; let response = await makeRequest(url); let parser = new window.DOMParser(); let xmlDoc = parser.parseFromString(response, "text/html"); let user_id = xmlDoc.querySelector("div.user-opt a").id; if (user_id === "ban-cancel") { const user_id_reg2 = /\d{6,}/; let div = xmlDoc.querySelector("div.user-opt script"); user_id = user_id_reg2.exec(div.text)[0]; } user_id_map[user_name] = user_id; return user_id; } async function do_blacklist_page(url, t) { let response = await makeRequest(url); let parser = new window.DOMParser(); let xmlDoc = parser.parseFromString(response, "text/html"); let items = xmlDoc.querySelectorAll("li div.content"); let str = t.innerHTML; for (let i = 0; i < items.length; i++) { let item = items[i]; let a = item.children[0]; // 如果不是 https://www.douban/people/xxx 的形式,那么就是匿名用户 if (check_user_link(a.href) === false) { continue; } let user_id = get_user_id_from_url(a.href); //console.log(`拉黑${user_id}`); await ban_simple(user_id); t.innerHTML = `${str}, 该页已完成 ${i + 1}/${items.length}`; await sleep(interval); } return items.length;// 返回该页的人数 } async function do_blacklist_all_status_like(e) { let b = e.target; console.log("blacklist all..."); for (let i = 0; ; i += 20) { b.innerHTML = `正在拉黑第 ${i / 20 + 1} 页`; let url = `${page_url}?start=${i}&tab=like#like`; let n = await do_blacklist_page(url, e.target); if (n === 0) { b.innerHTML = `已全部拉黑`; break; } else if (n === -1) { b.innerHTML = '失败请重试'; break; } await sleep(interval); } } async function do_blacklist_all_note_like(e) { let b = e.target; console.log("blacklist all..."); for (let i = 0; ; i += 100) { b.innerHTML = `正在拉黑第 ${i / 100 + 1} 页`; let url = `${page_url}?start=${i}&type=like#sep`; let n = await do_blacklist_page(url, e.target); if (n === 0) { b.innerHTML = `已全部拉黑`; break; } else if (n === -1) { b.innerHTML = '失败请重试'; break; } } } async function do_blacklist_all_note_donate(e) { let b = e.target; console.log("blacklist all..."); for (let i = 0; ; i += 100) { b.innerHTML = `正在拉黑第 ${i / 100 + 1} 页`; let url = `${page_url}?start=${i}&type=donate#sep`; let n = await do_blacklist_page(url, e.target); if (n === 0) { b.innerHTML = `已全部拉黑`; break; } else if (n === -1) { b.innerHTML = '失败请重试'; break; } } } // 打赏 - 日志 function process_note_donate() { let tabs = document.querySelector("div.tabs"); let b = document.createElement('a'); b.innerHTML = "一键拉黑所有赞赏的人"; b.style = "float: right; font-size: 13px; line-height: 1.2; color: #fff; background:#bbb; opacity: 1;"; // b.onmouseover = (e) => { // e.target.style.opacity = 1; // }; // b.onmouseout = (e) => { // e.target.style.opacity = 0; // }; b.onclick = do_blacklist_all_note_donate; tabs.append(b); } // 点赞 - 日志 function process_note_like() { let tabs = document.querySelector("div.tabs"); let b = document.createElement('a'); b.innerHTML = "一键拉黑所有点赞的人"; b.style = "float: right; font-size: 13px; line-height: 1.2; color: #fff; background:#bbb; opacity: 1;"; // b.onmouseover = (e) => { // e.target.style.opacity = 1; // }; // b.onmouseout = (e) => { // e.target.style.opacity = 0; // }; b.onclick = do_blacklist_all_note_like; tabs.append(b); } // 点赞 - 广播 function process_status_like() { let tabs = document.querySelector("div.tabs"); let b = document.createElement('a'); b.innerHTML = "一键拉黑所有点赞的人"; b.style = "float: right; font-size: 13px; line-height: 1.2; color: #fff; background:#bbb; opacity: 1;"; // b.onmouseover = (e) => { // e.target.style.opacity = 1; // }; // b.onmouseout = (e) => { // e.target.style.opacity = 0; // }; b.onclick = do_blacklist_all_status_like; tabs.append(b); } // 转发 - 广播 function process_reshare() { let items = document.querySelectorAll("li .content"); for (let i = 0; i < items.length; i++) { let item = items[i]; let a = item.children[0]; let user_id = get_user_id_from_url(a.href); let b = get_blacklist_button(user_id, "margin-left:10px"); b.className = "go-status"; item.insertBefore(b, item.children[2]); } } // 转发 - 日志 function process_rec() { let items = document.querySelectorAll("li .content"); for (let i = 0; i < items.length; i++) { let item = items[i]; let a = item.children[0]; let user_id = get_user_id_from_url(a.href); let b = get_blacklist_button( user_id, "position: absolute; top: 10px; right: 140px; color: #fff; background:#bbb; opacity: 0;" ); b.onmouseover = (e) => { e.target.style.opacity = 1; }; b.onmouseout = (e) => { e.target.style.opacity = 0; }; item.insertBefore(b, item.children[2]); } } // 收藏-日志, 日志的收藏是动态加载的 function process_note_collect() { function process_item(item) { let a = item.children[0]; let user_id = get_user_id_from_url(a.href); let b = get_blacklist_button( user_id, "position: absolute; top: 10px; right: 140px; color: #fff; background:#bbb; opacity: 0;" ); b.onmouseover = (e) => { e.target.style.opacity = 1; }; b.onmouseout = (e) => { e.target.style.opacity = 0; }; item.insertBefore(b, item.children[2]); } let items = document.querySelectorAll("li div.content"); for (let i = 0; i < items.length; i++) { process_item(items[i]); } function callback(records) { records.map(function (record) { if (record.addedNodes.length !== 0) { for (var i = 0; i < record.addedNodes.length; i++) { var node = record.addedNodes[i]; //console.log(node.tagName); if (node.tagName && node.tagName.toLowerCase() === "ul") { //console.log(node); var items = node.querySelectorAll("li div.content"); //console.log(items); for (let i = 0; i < items.length; i++) { process_item(items[i]); } } } } }); } var mo = new MutationObserver(callback); var option = { 'childList': true, 'subtree': true, }; mo.observe(document.body, option); } // 收藏-广播,广播的收藏也是动态的 function process_status_collect() { function process_item(item) { let a = item.children[0]; let user_id = get_user_id_from_url(a.href); let b = get_blacklist_button( user_id, "float: right; color: #fff; background:#bbb; opacity: 0;" ); b.onmouseover = (e) => { e.target.style.opacity = 1; }; b.onmouseout = (e) => { e.target.style.opacity = 0; }; item.append(b); } let items = document.querySelectorAll("li div.content"); for (let i = 0; i < items.length; i++) { process_item(items[i]); } function callback(records) { records.map(function (record) { if (record.addedNodes.length !== 0) { for (var i = 0; i < record.addedNodes.length; i++) { var node = record.addedNodes[i]; //console.log(node.tagName); if (node.tagName && node.tagName.toLowerCase() === "ul") { //console.log(node); var items = node.querySelectorAll("li div.content"); //console.log(items); for (let i = 0; i < items.length; i++) { process_item(items[i]); } } } } }); } var mo = new MutationObserver(callback); var option = { 'childList': true, 'subtree': true, }; mo.observe(document.body, option); } (function () { 'use strict'; ck = getCookie("ck"); let url = window.location.href; url = url.replace("#sep", ""); let i = url.indexOf("?"); if (i === -1) { i = url.length; } const page = url.substr(0, i); const arg = url.substr(i + 1, url.length - i); const status_reg = /^https:\/\/www\.douban\.com\/people\/[^\/]+\/status\/\d+\/$/; const note_reg = /^https:\/\/www\.douban\.com\/note\/\d+\/$/; const group_reg = /^https:\/\/www\.douban\.com\/group\/topic\/\d+\/$/; let page_mode = "None"; if (status_reg.test(page)) { page_mode = "status"; } else if (note_reg.test(page)) { page_mode = "node"; } else if (group_reg.test(page)) { page_mode = "group"; } else { return; } page_url = page; let tab_mode = "comment"; if (arg.indexOf("comment") !== -1) { tab_mode = "comment"; } else if (arg.indexOf("type=like") !== -1) { tab_mode = "note_like"; } else if (arg.indexOf("tab=like") !== -1) { tab_mode = "status_like"; } else if (arg.indexOf("tab=reshare") !== -1) { tab_mode = "reshare"; //for status } else if (arg.indexOf("type=rec") !== -1) { tab_mode = "rec"; // for note } else if (arg.indexOf("type=collect") !== -1) { tab_mode = "note_collect"; } else if (arg.indexOf("tab=collect") !== -1) { tab_mode = "status_collect"; } else if (arg.indexOf("type=donate") !== -1) { tab_mode = "note_donate"; } console.log(tab_mode); if (tab_mode === "comment") { if (page_mode === "group") { process_comment_group(); } else { process_comment(); } } else if (tab_mode === "note_like") { process_note_like(); } else if (tab_mode === "status_like") { process_status_like(); } else if (tab_mode === "reshare") { process_reshare(); } else if (tab_mode === "rec") { process_rec(); } else if (tab_mode === "note_collect") { process_note_collect(); } else if (tab_mode === "status_collect") { process_status_collect(); } else if (tab_mode === "note_donate") { process_note_donate(); } })();
QingJ © 2025
镜像随时可能失效,请加Q群300939539或关注我们的公众号极客氢云获取最新地址