推特工具箱 | twitter toolkit

鼠标🖱放到用户ID(.e.g @author)上时显示用户的注册(不可用)时间 - 显示更多信息以便识别网络水军

  1. // ==UserScript==
  2. // @name 推特工具箱 | twitter toolkit
  3. // @namespace https://twitter.com
  4. // @icon http://pic.baike.soso.com/ugc/baikepic2/26526/cut-20190524093048-1039431188_jpg_686_550_12779.jpg/300
  5. // @version 1.1.0
  6. // @description 鼠标🖱放到用户ID(.e.g @author)上时显示用户的注册(不可用)时间 - 显示更多信息以便识别网络水军
  7. // @author Sven
  8. // @license MIT
  9. // @note v1.1.0 修复因 ajax-hook 升级导致的报错; 参照 change list 修改引用方式
  10. // @match https://twitter.com/*
  11. // @require https://unpkg.com/ajax-hook/dist/ajaxhook.min.js
  12. // @run-at document-start
  13. // @grant none
  14. // ==/UserScript==
  15.  
  16. ; (() => {
  17. class ToolkitModule {
  18. constructor() { }
  19. isActive = true
  20. }
  21. /**
  22. * Breaking Ajax
  23. */
  24. class BreakingModule extends ToolkitModule {
  25. constructor() { super() }
  26. init(ctx) {
  27. // 添加 mouseover 事件, 在鼠标悬浮在用户头像上时显示注册(不可用)时间
  28. document.addEventListener('mouseover', evt => {
  29. if (evt.target.tagName !== 'SPAN' || evt.target.parentNode.tagName !== 'DIV' || (evt.target.nextElementSibling && evt.target.nextElementSibling.classList.contains('twitter-toolkit-user-created-at'))) return
  30. for (const id in window._$TwitterToolkit.users) {
  31. const userName = window._$TwitterToolkit.users[id].screen_name
  32. if (evt.target.innerText === '@' + userName) {
  33. ctx.log('监测到鼠标悬浮在用户头像上, 用户信息: ', window._$TwitterToolkit.users[id])
  34. // 账号注册(不可用)时间
  35. const createdAtDom = document.createElement('div')
  36. const { created_at } = window._$TwitterToolkit.users[id]
  37. const createdAtDate = new Date(created_at)
  38. createdAtDom.innerText = 'created at ' + createdAtDate.toLocaleDateString()
  39. createdAtDom.style.fontSize = '12px'
  40. createdAtDom.style.color = 'rgb(27, 149, 224)'
  41. createdAtDom.classList.add('twitter-toolkit-user-created-at')
  42. evt.target.parentNode.appendChild(createdAtDom)
  43. break
  44. }
  45. }
  46. })
  47. ah.hook({
  48. //拦截回调
  49. onreadystatechange: (xhr) => {
  50. const responseStr = (xhr.response instanceof ArrayBuffer ? String.fromCharCode.apply(null, Uint16Array) : xhr.response) || ''
  51. if (responseStr.indexOf('"users":{') === -1) return
  52. let users = null
  53. try {
  54. const res = JSON.parse(responseStr)
  55. users = (res.globalObjects && res.globalObjects.users)
  56. } catch (err) { }
  57. if (users === null) return
  58. // ctx.log('users: ', users)
  59. for (const id in users) {
  60. if (ctx.users[id]) {
  61. Object.assign(ctx.users[id], users[id])
  62. } else {
  63. ctx.users[id] = users[id]
  64. }
  65. }
  66. setTimeout(this._showUserInfo, 500)
  67. },
  68. // onload: function (xhr) {
  69. // console.log("onload called: %O", xhr)
  70. // },
  71. //拦截方法
  72. // open: function (arg, xhr) {
  73. // xhr._$request = { url: arg[1], method: arg[0] }
  74. // }
  75. })
  76. }
  77. _showUserInfo() {
  78. console.log(window._$TwitterToolkit.users)
  79. }
  80. onload(ctx) {
  81. ctx.log('onload')
  82. }
  83. }
  84. /**
  85. * 工具类
  86. */
  87. class Toolkit {
  88. debug = true
  89. options = {}
  90. users = {}
  91. constructor(options = {}) {
  92. Object.assign(this.options, options)
  93. this.emitHook('init')
  94. }
  95. /**
  96. * 工具集
  97. */
  98. static modules = []
  99. /**
  100. * 注册(不可用)工具模块
  101. */
  102. static use(moduleItem) {
  103. // 禁用未激活的模块
  104. if (!moduleItem.isActive) return
  105. Array.isArray(moduleItem) ? moduleItem.map(item => Toolkit.use(item)) : Toolkit.modules.push(moduleItem)
  106. }
  107. /**
  108. * 触发钩子函数
  109. * @param {string}} hook 钩子函数名
  110. */
  111. emitHook(hook) {
  112. this.log('触发钩子函数: ' + hook, Toolkit.modules.length)
  113. Toolkit.modules.map(module => module[hook] && typeof module[hook] === 'function' && module[hook](this))
  114. }
  115. log(...args) {
  116. console.log('%c[Twitter Toolkit] LOG: ', 'color:teal', ...args)
  117. }
  118. static delay(timeout = 200) {
  119. return new Promise(resolve => setTimeout(resolve, timeout))
  120. }
  121. }
  122. Toolkit.use(new BreakingModule())
  123. window._$TwitterToolkit = new Toolkit()
  124. window.addEventListener('DOMContentLoaded', () => window._$TwitterToolkit.emitHook('onload'))
  125. })();

QingJ © 2025

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