Block_Zhihu_Users

Block users on a website by clicking a button

  1. // ==UserScript==
  2. // @name Block_Zhihu_Users
  3. // @namespace your-namespace
  4. // @version 1.1
  5. // @description Block users on a website by clicking a button
  6. // @match https://www.zhihu.com/question/*
  7. // @grant GM_addStyle
  8. // ==/UserScript==
  9.  
  10. (function () {
  11. 'use strict';
  12.  
  13. function sleep(ms) {
  14. return new Promise(resolve => setTimeout(resolve, ms));
  15. }
  16.  
  17. let executedUrls = [];
  18.  
  19. async function blockUsers() {
  20. console.log('blockUsers...')
  21.  
  22. let arr = document.querySelectorAll("div.ContentItem-meta > div.AuthorInfo.AnswerItem-authorInfo.AnswerItem-authorInfo--related")
  23. console.log(`加载完成...arr:${arr.length}`)
  24. let k = 0;
  25. let count = 0;
  26. let index = 0;
  27. for (let a of arr) {
  28. index += 1;
  29.  
  30. let userUrl = null;
  31. try {
  32. let crr = a.querySelectorAll("a");
  33. if (crr.length == 0) {
  34. k++;
  35. a.parentElement.parentElement.parentElement.remove();
  36. } else {
  37. userUrl = crr[0].href;
  38. }
  39. } catch (e) {
  40. //a.remove();
  41. continue;
  42. }
  43.  
  44. let end = index >= arr.length - k - 3;
  45.  
  46. let urlToken = '';
  47. try {
  48. urlToken = userUrl.substring(userUrl.lastIndexOf('/') + 1);
  49. } catch (e) {
  50. console.log(`err:url:${userUrl}`);
  51. continue;
  52. }
  53.  
  54. if (executedUrls.includes(urlToken)) {
  55. //console.log(`${index}/${arr.length}:Skipping ${userUrl} as it has already been blocked`);
  56. console.log(`${index}/${arr.length}`);
  57. try {
  58. let b = a.parentElement.parentElement.parentElement.parentElement;
  59. if (end) {
  60. b.style = 'display:none';
  61. } else {
  62. b.remove();
  63. }
  64.  
  65. } catch (e) {}
  66. continue;
  67. }
  68.  
  69. // 检查是否已执行过该 urlToken
  70. if (localStorage.getItem(urlToken)) {
  71. //console.log(`${index}/${arr.length}:Skipping ${userUrl} as it has already been blocked`);
  72. console.log(`${index}/${arr.length}`);
  73. try {
  74. let b = a.parentElement.parentElement.parentElement.parentElement;
  75. if (end) {
  76. b.style = 'display:none';
  77. } else {
  78. b.remove();
  79. }
  80. } catch (e) {}
  81. continue;
  82. }
  83.  
  84. console.log(`${index}:${count}/${arr.length},屏蔽用户:${userUrl}`);
  85. const response = await fetch(`/api/v4/members/${urlToken}/actions/block`, {
  86. method: 'POST',
  87. headers: new Headers({
  88. 'x-xsrftoken': document.cookie.match(/(?<=_xsrf=)[\w-]+(?=;)/)[0],
  89. }),
  90. });
  91. try {
  92. let b = a.parentElement.parentElement.parentElement.parentElement;
  93. if (end) {
  94. b.style = 'display:none';
  95. } else {
  96. b.remove();
  97. }
  98. } catch (e) {}
  99. count += 1;
  100. executedUrls.push(urlToken);
  101. localStorage.setItem(urlToken, 'blocked'); // 将已执行过的 urlToken 存入 localStorage
  102. await sleep(200);
  103. }
  104.  
  105. //debugger
  106. if (arr.length === 0 || executedUrls.length === 0 || executedUrls.length === arr.length) {
  107. console.log('No more data or all urlTokens have been blocked. Simulating page scroll to load more data...');
  108. showMessage(`Block ${count} users,total:${executedUrls.length}! \n No more data or all urlTokens have been blocked. Click button or page scroll to load more data...`);
  109. }
  110.  
  111. // 移动鼠标到最下面
  112. //window.scrollTo(0, document.body.scrollHeight);
  113. window.focus(); // 聚焦到当前页面
  114. for (let i = 0; i < 5; i++) {
  115. const event = new KeyboardEvent('keydown', {
  116. key: 'G',
  117. code: 'KeyG',
  118. shiftKey: true
  119. });
  120. document.dispatchEvent(event);
  121. await sleep(10);
  122.  
  123. }
  124. }
  125.  
  126. // 创建消息框元素
  127. function createAlertElement() {
  128. var alertElement = document.createElement('div');
  129. alertElement.setAttribute('id', 'alert-box');
  130. alertElement.style.display = 'none';
  131.  
  132. GM_addStyle(`
  133. #alert-box {
  134. position: fixed;
  135. top: 0;
  136. left: 0;
  137. width: 100%;
  138. padding: 10px;
  139. background-color: #f44336;
  140. color: white;
  141. font-size: 18px;
  142. text-align: center;
  143. z-index: 9999;
  144. opacity: 0;
  145. transition: opacity 0.3s ease-in-out;
  146. }
  147. #alert-box.show {
  148. opacity: 1;
  149. }
  150. `);
  151.  
  152. document.body.appendChild(alertElement);
  153. return alertElement;
  154. }
  155.  
  156. // 弹出消息框
  157. function showMessage(message, timeout) {
  158. var alertElement = document.getElementById('alert-box') || createAlertElement();
  159. alertElement.textContent = message;
  160. alertElement.style.display = 'block';
  161. alertElement.classList.add('show');
  162. setTimeout(function () {
  163. alertElement.classList.remove('show');
  164. setTimeout(function () {
  165. alertElement.style.display = 'none';
  166. }, 300);
  167. }, timeout || 1000);
  168. }
  169.  
  170. // 创建悬浮按钮元素
  171. const button = document.createElement('button');
  172. button.textContent = '屏蔽用户';
  173. button.style.position = 'fixed';
  174. button.style.bottom = '20px';
  175. button.style.right = '20px';
  176. button.style.zIndex = '9999';
  177. button.style.padding = '10px 20px';
  178. button.style.border = 'none';
  179. button.style.borderRadius = '10px';
  180. button.style.color = '#fff';
  181. button.style.fontSize = '16px';
  182. button.style.fontWeight = 'bold';
  183. button.style.background = 'red';
  184. button.style.cursor = 'pointer';
  185.  
  186. // 添加点击事件监听器
  187. button.addEventListener('click', async() => {
  188. await blockUsers();
  189. });
  190.  
  191. // 将按钮添加到页面中
  192. document.body.appendChild(button);
  193.  
  194. document.addEventListener('keydown', async function (event) {
  195. if (event.key === 'b' || event.key === 'B') {
  196. await blockUsers();
  197. }
  198. });
  199.  
  200. })();

QingJ © 2025

镜像随时可能失效,请加Q群300939539或关注我们的公众号极客氢云获取最新地址