[{"articleStyle":1,"cacheFirst":false,"concurrentRate":"1\/300","coverDecodeJs":"\/\/ ==================== 订阅源「封面解密 Js」(coverDecodeJs) v2 ====================\n\/\/ pic.hdhwqx.cn 全站图片 = AES-128-CBC 加密字节（站点 image.0821.js 实锤）\n\/\/   KEY='f5d965df75336270'  IV='97b60394abc2fbe1'  PKCS7 → 解密后即 JPEG\/PNG\/WebP\/GIF\n\/\/ 绑定：java \/ source \/ src \/ result \/ book，要求返回 **ByteArray**。\n\/\/\n\/\/ ★★ v2 修复「大部分封面不显示」：v1 里对每张封面用 java.get(src) **重新发一次请求**，\n\/\/    Glide 并发加载 32 张时大量超时 ⇒ 只有少数成功。v2 直接使用 Glide 已给到的 result 字节，\n\/\/    零额外网络请求。\n\/\/ ★ result 通常是 InputStream（OkHttpStreamFetcher 传 responseBody.byteStream()）：\n\/\/    用 java.base64DecodeToByteArray 造 Java byte[] 缓冲，read(buf) 循环读到 -1。\n\/\/    若是 ByteArray（另一重载）则直接用。\n\/\/ ★ 解密用 java.createSymmetricCrypto 原生 API（LT 实测 359ms\/66KB；纯 JS AES 在 Rhino 60s 超时不可用）。\n\/\/    E 版若无此 API，try\/catch 返回原字节（不崩，只是不解密）。\n(function () {\n  \/\/ ★ 关键提速：java.strToBytes(str, 'ISO-8859-1') 把 0-255 的 JS 字符串直接转 Java byte[]\n  \/\/   （实测 7ms\/66KB，而纯 JS toB64 + base64DecodeToByteArray 要 876ms）。\n  var CH = String.fromCharCode;\n  try {\n    var cipher = null, i, n, v, s, buf;\n    if (result == null) return result;\n    \/\/ ① result 是 ByteArray \/ byte[]（有 length、可下标、无 read 方法）\n    if (typeof result.length === 'number' && typeof result.read !== 'function') {\n      cipher = result;\n    } else if (typeof result.read === 'function') {\n      \/\/ ② result 是 InputStream：read(byte[]) 循环，边读边拼 0-255 字符串\n      s = '';\n      try {\n        buf = java.base64DecodeToByteArray(new Array(8193).join('A'));  \/\/ 6144B Java byte[] 缓冲\n        var guard = 0;\n        while (guard < 2048) {\n          guard++;\n          n = result.read(buf);\n          if (n <= 0) break;\n          for (i = 0; i < n; i++) { v = buf[i]; s += CH(v < 0 ? v + 256 : v); }\n        }\n      } catch (e2) {}\n      if (s.length) {\n        try { cipher = java.strToBytes(s, 'ISO-8859-1'); }\n        catch (e3) { try { cipher = java.strToBytes(s); } catch (e4) {} }\n      }\n    }\n    if (!cipher || !cipher.length || cipher.length % 16) return result;\n    if (typeof java.createSymmetricCrypto !== 'function') return result;\n    var out = java.createSymmetricCrypto(\n      'AES\/CBC\/PKCS5Padding', 'f5d965df75336270', '97b60394abc2fbe1'\n    ).decrypt(cipher);\n    if (out && out.length) return out;   \/\/ 已是 Java byte[]\n  } catch (e) {}\n  return result;\n})()","customOrder":0,"enableJs":true,"enabled":true,"enabledCookieJar":true,"header":"{\"User-Agent\": \"Mozilla\/5.0 (Linux; Android 13; Pixel 7) AppleWebKit\/537.36 (KHTML, like Gecko) Chrome\/124.0.0.0 Mobile Safari\/537.36\", \"Referer\": \"https:\/\/abandon.yixuiyyj.cc\/\"}","injectJs":"(function() {\n    \/\/ 播放器增强（原脚本 by 网友，经 91爆料订阅源多视频适配）\n    \/\/ 功能：①自动识别横\/竖屏全屏切换 ②长按 3 倍速 ③拖动调进度 ④直播保护(duration 无效时不 seek)\n    \/\/ 适配点：原版只绑 querySelector('video') 第一个；本源正文含 6 个视频 → 全部绑定。\n    \/\/        injectJs 每次 onPageFinished 都会执行 → 加全局守卫，避免重复注入\/轮询叠加。\n    if (window.__jyPlayerEnhanced) return;\n    window.__jyPlayerEnhanced = true;\n\n    var st = document.createElement('style');\n    st.textContent = 'body.fs-ls{transform:rotate(90deg) translateY(-100%);transform-origin:top left;width:100vh!important;height:100vw!important;overflow:hidden!important;position:fixed!important;top:0!important;left:0!important}';\n    document.head.appendChild(st);\n\n    \/\/ 按「当前处于全屏的那个 video」判断横竖，而不是固定取第一个\n    function currentFsVideo() {\n        var f = document.fullscreenElement || document.webkitFullscreenElement;\n        if (f && f.tagName === 'VIDEO') return f;\n        if (f && f.querySelector) return f.querySelector('video');\n        var vs = document.querySelectorAll('video');\n        for (var i = 0; i < vs.length; i++) {\n            if (vs[i] === document.fullscreenElement || vs[i] === document.webkitFullscreenElement) return vs[i];\n        }\n        return vs[0] || null;\n    }\n    function isLS() {\n        var v = currentFsVideo();\n        return (!v || !v.videoWidth) ? true : v.videoWidth >= v.videoHeight;\n    }\n    function fsHandler() {\n        var full = document.fullscreenElement || document.webkitFullscreenElement;\n        if (full && isLS()) {\n            document.body.classList.add('fs-ls');\n            if (screen.orientation && screen.orientation.lock)\n                screen.orientation.lock('landscape').catch(function(){});\n        } else {\n            document.body.classList.remove('fs-ls');\n            if (screen.orientation && screen.orientation.unlock)\n                screen.orientation.unlock();\n        }\n    }\n    document.addEventListener('fullscreenchange', fsHandler);\n    document.addEventListener('webkitfullscreenchange', fsHandler);\n    if (document.fullscreenElement || document.webkitFullscreenElement) fsHandler();\n\n    \/\/ ============ 手势（逐视频绑定） ============\n    function bind(v) {\n        if (v.__gestureBound) return;\n        v.__gestureBound = true;\n\n        \/\/ ===== 可调参数（长按倍速在这里改） =====\n        var LONG_PRESS_MS = 500;    \/\/ 长按判定时长（毫秒）\n        var FAST_RATE     = 3.0;    \/\/ 长按时的播放倍速\n        var SWIPE_SENS    = 1.0;    \/\/ 滑动灵敏度：划满一屏 = 完整时长\n        var SEEK_THROTTLE = 24;     \/\/ seek 节流（毫秒）\n\n        var sx = 0, st0 = 0, lp = null, ff = false, wasPaused = false, origRate = 1;\n        var pendT = 0, seekTimer = null, seekPending = false, tipEl = null, speedTipEl = null;\n\n        function fmt(t){var m=Math.floor(t\/60),s=Math.floor(t%60);return(m<10?'0':'')+m+':'+(s<10?'0':'')+s;}\n        function showTip(t){\n            if(!tipEl){tipEl=document.createElement('div');tipEl.style.cssText='position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);background:rgba(0,0,0,.75);color:#fff;padding:10px 20px;border-radius:8px;font-size:16px;font-weight:bold;z-index:99999;pointer-events:none;';document.body.appendChild(tipEl);}\n            tipEl.textContent = fmt(t)+' \/ '+fmt(v.duration||0);\n            tipEl.style.display = 'block';\n        }\n        function hideTip(){ if(tipEl) tipEl.style.display='none'; }\n        function showSpeedTip(){\n            if(!speedTipEl){speedTipEl=document.createElement('div');speedTipEl.style.cssText='position:fixed;top:20px;left:50%;transform:translateX(-50%);background:rgba(0,0,0,.8);color:#fff;padding:8px 16px;border-radius:20px;font-size:14px;z-index:99999;pointer-events:none;';document.body.appendChild(speedTipEl);}\n            speedTipEl.textContent = v.playbackRate + 'x 倍速中';\n            speedTipEl.style.display = 'block';\n        }\n        function hideSpeedTip(){ if(speedTipEl) speedTipEl.style.display='none'; }\n\n        function stopLong(){ if(lp){clearTimeout(lp);lp=null;} }\n        function resetFF(){ if(ff){v.playbackRate=origRate;ff=false;hideSpeedTip();if(wasPaused)v.pause();} }\n        function flushSeek(){ if(seekPending){seekPending=false;if(isFinite(pendT))v.currentTime=pendT;} clearTimeout(seekTimer); }\n\n        v.addEventListener('touchstart', function(e){\n            if(e.touches.length!==1) { stopLong(); return; }\n            sx = e.touches[0].clientX;\n            st0 = v.currentTime || 0;\n            wasPaused = v.paused;\n            origRate = v.playbackRate || 1;\n            stopLong();\n            lp = setTimeout(function(){\n                lp = null;\n                ff = true;\n                v.playbackRate = FAST_RATE;\n                if(wasPaused) { var p = v.play(); if(p && p.catch) p.catch(function(){}); }\n                showSpeedTip();\n                hideTip();\n            }, LONG_PRESS_MS);\n        }, {passive:true});\n\n        v.addEventListener('touchmove', function(e){\n            if(e.touches.length!==1) return;\n            stopLong();\n            var dx = e.touches[0].clientX - sx;\n            if(Math.abs(dx) > 15){\n                if(ff){v.playbackRate=origRate;ff=false;hideSpeedTip();}\n                e.preventDefault();\n                var dur = v.duration;\n                if(!isFinite(dur) || dur <= 0) return;   \/\/ ★ 直播保护：duration 无效不 seek\n                var nt = st0 + (dx \/ (window.innerWidth * SWIPE_SENS)) * dur;\n                if(nt<0) nt=0; if(nt>dur) nt=dur;\n                pendT = nt;\n                showTip(nt);\n                if(!seekPending){\n                    seekPending = true;\n                    seekTimer = setTimeout(function(){ seekPending=false; if(isFinite(pendT)) v.currentTime=pendT; }, SEEK_THROTTLE);\n                }\n            }\n        }, {passive:false});\n\n        function endTouch(){\n            stopLong();\n            if(ff){ resetFF(); return; }\n            flushSeek();\n            hideTip();\n        }\n        v.addEventListener('touchend', endTouch);\n        v.addEventListener('touchcancel', endTouch);\n    }\n\n    function tryBind(){\n        try {\n            var vs = document.querySelectorAll('video');\n            for (var i = 0; i < vs.length; i++) bind(vs[i]);\n        } catch (e) {}\n        setTimeout(tryBind, 800);   \/\/ 兼容 hls.js 后建\/动态插入的 video\n    }\n    tryBind();\n    console.log('[注入] 播放器增强已启用（多视频适配版）');\n})();\n","lastUpdateTime":1794038155951,"loadWithBaseUrl":true,"loginUi":"[{\"name\": \"jyPub\", \"type\": \"text\", \"viewName\": \"'发布页地址(默认jybl26)'\"}, {\"name\": \"🧭获取发布页线路\", \"type\": \"button\", \"action\": \"JY_fetchPub()\", \"viewName\": \"'🧭 一键从发布页获取网址路线'\"}, {\"name\": \"⏱测试延时\", \"type\": \"button\", \"action\": \"JY_testAll()\", \"viewName\": \"'⏱ 测试延时(ms写入各线路按钮)'\"}, {\"name\": \"🔍检查登录状态\", \"type\": \"button\", \"action\": \"JY_checkLogin()\", \"viewName\": \"'🔍 检查登录状态 \/ 线路可用性'\"}, {\"name\": \"━━━ 点击切换线路（延时见按钮名）━━━\", \"type\": \"button\", \"action\": \"\", \"viewName\": \"'━━━ 点击切换线路 ━━━'\"}, {\"name\": \"线路1\", \"type\": \"button\", \"action\": \"JY_switch(1)\", \"viewName\": \"JY_lineBtn(1)\"}, {\"name\": \"线路2\", \"type\": \"button\", \"action\": \"JY_switch(2)\", \"viewName\": \"JY_lineBtn(2)\"}, {\"name\": \"线路3\", \"type\": \"button\", \"action\": \"JY_switch(3)\", \"viewName\": \"JY_lineBtn(3)\"}, {\"name\": \"线路4\", \"type\": \"button\", \"action\": \"JY_switch(4)\", \"viewName\": \"JY_lineBtn(4)\"}, {\"name\": \"线路5\", \"type\": \"button\", \"action\": \"JY_switch(5)\", \"viewName\": \"JY_lineBtn(5)\"}, {\"name\": \"线路6\", \"type\": \"button\", \"action\": \"JY_switch(6)\", \"viewName\": \"JY_lineBtn(6)\"}]","loginUrl":"\/\/ ==================== 91爆料订阅源 · 线路管理面板（LT\/E 双版本兼容 V1 静态 loginUi） ====================\n\/\/ 用途：发布页(jybl26.com, Base64 编码) → 解析 zz_line 三条基础域 → 泛子域线路池\n\/\/       → 测速(java.connect 返回真 StrResponse, callTime() 取 ms) → 逐线路按钮切换\n\/\/ 全部函数挂在 loginUrl，SourceLoginDialog 拼接 \"$loginJS\\n$jsStr\" 后 loginUi\/action\/viewName 环境均可用。\n\/\/ 各阶段一律 Toast 反馈（java.longToast，E 版无 longToast 时降级 java.toast）。\n\nvar JY_MAX = 6;                       \/\/ 线路按钮位数（当前发布页 3 条，留余量）\nvar JY_DEFAULT = 'https:\/\/abandon.yixuiyyj.cc';\nvar JY_DEFAULT_PUB = 'https:\/\/jybl26.com';\nvar JY_UA = 'Mozilla\/5.0 (Linux; Android 13; Pixel 7) AppleWebKit\/537.36 (KHTML, like Gecko) Chrome\/124.0.0.0 Mobile Safari\/537.36';\n\/\/ 发布页 words 词表抽样（306 词，泛解析任意词均可用；每次获取随机挑一个，避免单前缀被针对）\nvar JY_WORDS = ['abandon', 'ability', 'able', 'above', 'abroad', 'access', 'account', 'action', 'active'];\n\nfunction JY_toast(t) {\n  try { java.longToast(String(t)); } catch (e) { try { java.toast(String(t)); } catch (e2) {} }\n}\nfunction JY_gv(k, def) {\n  var v = '';\n  try { v = String(source.get(k)); } catch (e) { v = ''; }\n  if (v === 'null' || v === 'undefined' || v === '') v = def || '';\n  return v;\n}\nfunction JY_pub() {\n  var p = JY_gv('jyPub', JY_DEFAULT_PUB).replace(\/\\\/+$\/, '');\n  if (p.indexOf('http') !== 0) p = 'https:\/\/' + p;\n  return p;\n}\nfunction JY_line() {\n  var d = JY_gv('jyLine', JY_DEFAULT).replace(\/\\\/+$\/, '');\n  if (d.indexOf('http') !== 0) d = JY_DEFAULT;\n  return d;\n}\nfunction JY_hdr() { return JSON.stringify({ 'User-Agent': JY_UA }); }\nfunction JY_word() { return JY_WORDS[Math.floor(Math.random() * JY_WORDS.length)]; }\n\n\/\/ 把发布页 zz_line 的基础域还原成可访问线路\nfunction JY_build(bases) {\n  var out = [], i, b, w = JY_word();\n  for (i = 0; i < bases.length; i++) {\n    b = String(bases[i]).trim().toLowerCase().replace(\/\\.$\/, '');\n    if (!b || b.indexOf('..') > -1) continue;\n    if (!\/^[a-z0-9](?:[a-z0-9.-]*[a-z0-9])?$\/.test(b)) continue;\n    \/\/ 发布页逻辑：第 3 条(cloudfront)不加随机前缀；前两条是泛子域\n    var u = (i === 2 || b.indexOf('cloudfront') > -1) ? ('https:\/\/' + b) : ('https:\/\/' + w + '.' + b);\n    if (out.indexOf(u) < 0) out.push(u);\n  }\n  return out;\n}\n\n\/\/ 内置兜底（发布页抓不到时用，来自 261107 实测 zz_line）\n\/\/ ★ 固定词 'ability' 而非随机：JY_found() 每次调用必须返回同一组线路，\n\/\/   否则 viewName 显示的域名与 JY_switch() 实际切换的域名会对不上（用户判为 bug）。\nfunction JY_fallbackFixed() {\n  return ['https:\/\/abandon.yixuiyyj.cc', 'https:\/\/abandon.cvcmneja.cc',\n          'https:\/\/d3hw80p8c34pat.cloudfront.net'];\n}\nfunction JY_fallback() {\n  \/\/ 仅在 jyFound 为空时被调用：生成固定兜底线路并持久化，\n  \/\/ 保证后续 viewName \/ action \/ sortUrl 每次读到的都是同一组域名。\n  var list = JY_fallbackFixed();\n  JY_setFound(list);\n  return list;\n}\n\nfunction JY_setFound(list) {\n  source.put('jyFound', list.join(' '));\n  var i;\n  for (i = 0; i < JY_MAX; i++) source.put('jyDelay' + i, '');\n}\nfunction JY_found() {\n  var s = JY_gv('jyFound', '');\n  if (s === '') return JY_fallback();\n  var a = s.split(\/\\s+\/), out = [], i;\n  for (i = 0; i < a.length; i++) if (a[i].indexOf('http') === 0 && out.indexOf(a[i]) < 0) out.push(a[i]);\n  return out.length ? out : JY_fallback();\n}\n\n\/\/ ---------- 🧭 一键从发布页获取网址路线 ----------\nfunction JY_fetchPub() {\n  JY_toast('🧭 开始获取：正在打开发布页 ' + JY_pub());\n  var raw = '', err = '';\n  try {\n    var r = java.connect(JY_pub() + '\/', JY_hdr(), 20000);\n    raw = String(r.body());\n    if (r.code && r.code() !== 200) err = 'HTTP ' + r.code();\n  } catch (e) { err = String(e).substring(0, 80); }\n  if (err === '' && (raw.length < 1000 || raw.indexOf('Exception') === 0)) err = '发布页内容异常';\n  if (err !== '') {\n    JY_toast('⚠ 发布页抓取失败(' + err + ')，改用内置 3 条兜底线路');\n    var fb = JY_fallback(); JY_setFound(fb);\n    JY_toast('✅ 已载入内置线路 ' + fb.length + ' 条，请点「⏱测试延时」');\n    JY_refresh(); return;\n  }\n  JY_toast('🔓 发布页已获取(' + raw.length + 'B)，正在 Base64 解码…');\n  var html = raw, dec = '';\n  var m = \/Base64\\.decode\\(['\"]([A-Za-z0-9+\/=]+)['\"]\\)\/.exec(raw);\n  if (m) {\n    try { dec = String(java.base64Decode(m[1])); } catch (e) { dec = ''; }\n    if (dec.length > 1000) html = dec;\n  }\n  var zz = \/zz_line\\s*=\\s*\"([^\"]+)\"\/.exec(html);\n  var bases = [];\n  if (zz) {\n    var ls = zz[1].replace(\/\\\\n\/g, '\\n').replace(\/\\\\r\/g, '').split(\/\\r?\\n\/), i;\n    for (i = 0; i < ls.length; i++) if (ls[i].trim()) bases.push(ls[i].trim());\n  }\n  if (!bases.length) {\n    JY_toast('⚠ 未解析到 zz_line（发布页可能改版），改用内置 3 条兜底线路');\n    var fb2 = JY_fallback(); JY_setFound(fb2);\n    JY_toast('✅ 已载入内置线路 ' + fb2.length + ' 条');\n    JY_refresh(); return;\n  }\n  JY_toast('🔍 解码成功，提取到 ' + bases.length + ' 条基础域：' + bases.join(' \/ '));\n  var lines = JY_build(bases);\n  JY_setFound(lines);\n  JY_toast('✅ 共生成 ' + lines.length + ' 条线路，已写入各线路按钮；请点「⏱测试延时」测速');\n  JY_refresh();\n}\n\n\/\/ ---------- ⏱ 测试延时（只回填 ms，不自动切换，避免误切） ----------\nfunction JY_testAll() {\n  var list = JY_found();\n  JY_toast('⏱ 开始测速：共 ' + list.length + ' 条线路，逐个请求 \/usr\/themes\/ping.gif…');\n  var best = -1, bestMs = 999999, i, r, b, ms, tag;\n  for (i = 0; i < list.length && i < JY_MAX; i++) {\n    ms = -1; tag = '✗ 不可达';\n    try {\n      r = java.connect(list[i] + '\/usr\/themes\/ping.gif', JY_hdr(), 12000);\n      b = String(r.body());\n      if (b.indexOf('Exception') > -1 || b.indexOf('timeout') > -1 || (r.code && r.code() !== 200)) {\n        tag = '✗ HTTP\/' + (r.code ? r.code() : '异常');\n      } else if (b.length < 20) {\n        tag = '✗ 内容异常';\n      } else {\n        ms = r.callTime ? Number(r.callTime()) : -1;\n        if (ms < 0) ms = 0;\n        tag = ms + 'ms';\n        if (ms < bestMs) { bestMs = ms; best = i; }\n      }\n    } catch (e) { tag = '✗ ' + String(e).substring(0, 40); }\n    source.put('jyDelay' + i, tag);\n    JY_toast('  [' + (i + 1) + '\/' + list.length + '] ' + JY_host(list[i]) + ' → ' + tag);\n  }\n  if (best >= 0) {\n    for (i = 0; i < list.length && i < JY_MAX; i++) {\n      if (i === best) source.put('jyDelay' + i, '⚡' + bestMs + 'ms');\n    }\n    JY_toast('🏁 测速完成：最快 ' + JY_host(list[best]) + ' ' + bestMs + 'ms（点对应线路按钮即可切换）');\n  } else {\n    JY_toast('⚠ 测速完成：没有可用线路，请点「🧭获取发布页线路」刷新后重试');\n  }\n  JY_refresh();\n}\n\n\/\/ ---------- 🔍 检查登录状态 \/ 线路可用性（本站免登录，做连通性 + 登录墙检测） ----------\nfunction JY_checkLogin() {\n  var d = JY_line();\n  JY_toast('🔍 正在检查当前线路状态：' + JY_host(d));\n  var b = '', code = 0;\n  try {\n    var r = java.connect(d + '\/', JY_hdr(), 15000);\n    b = String(r.body()); code = r.code ? r.code() : 0;\n  } catch (e) { JY_toast('❌ 检查失败：' + String(e).substring(0, 80)); return; }\n  if (b.indexOf('Exception') > -1 || code !== 200 || b.length < 5000) {\n    JY_toast('❌ 当前线路不可用(HTTP ' + code + ', ' + b.length + 'B)，建议测速后切换线路'); return;\n  }\n  var needLogin = \/(请先登录|登录后查看|需要登录|会员专享|VIP专属)\/.test(b);\n  var hasUser = \/(退出登录|wc-header-user-logged|side-toolbar-logout)\/.test(b);\n  JY_toast('✅ 线路正常(' + b.length + 'B)；' + (needLogin ? '⚠ 检测到登录墙（部分内容需登录）' : '本站内容免登录，可直接阅读全部图文') + (hasUser ? '；已检测到登录态' : '；当前为游客态'));\n}\n\n\/\/ ---------- ▶ 各线路切换（索引制，每站一个按钮） ----------\nfunction JY_switch(n) {\n  var list = JY_found();\n  var i = Number(n) - 1;\n  if (i < 0 || i >= list.length) { JY_toast('⚠ 线路 ' + n + ' 尚未获取，请先点「🧭获取发布页线路」'); return; }\n  var old = JY_line(), nw = list[i];\n  JY_toast('🔄 正在切换：' + JY_host(old) + ' → ' + JY_host(nw));\n  source.put('jyLine', nw);\n  JY_toast('✅ 已切换到 ' + JY_host(nw) + '；请重新进入订阅\/发现页生效（如分类未刷新，用排序菜单「清理排序缓存」）');\n  JY_refresh();\n}\n\n\/\/ ---------- 按钮动态文字：▶当前 \/ ⚡最快 \/ 域名 + 延时ms ----------\nfunction JY_host(u) {\n  var m = \/^https?:\\\/\\\/([^\/]+)\/.exec(String(u));\n  return m ? m[1] : String(u);\n}\nfunction JY_lineBtn(n) {\n  var list = JY_found(), i = Number(n) - 1;\n  if (i < 0 || i >= list.length) return \"'━━ 线路\" + n + \" 未获取 ━━'\";\n  var cur = JY_line(), mark = (list[i].replace(\/\\\/+$\/, '') === cur.replace(\/\\\/+$\/, '')) ? '▶ ' : '　 ';\n  var dl = JY_gv('jyDelay' + i, '');\n  if (dl !== '') mark += dl + ' ';\n  return \"'\" + mark + JY_host(list[i]) + \"'\";\n}\nfunction JY_refresh() {\n  try { java.reLoginView(); } catch (e) {\n    try { java.reLoginView(false); } catch (e2) { JY_toast('（若按钮文字未刷新，请重新打开本面板）'); }\n  }\n}\n\n\/\/ loginUrl 必须定义 login()，否则点击「登录」抛 Function login not implements\nfunction login(e) {\n  if (e != undefined) { JY_toast(String(e)); return; }\n  JY_toast('91爆料 · 线路管理面板（本站免登录）｜先「🧭获取发布页线路」→「⏱测试延时」→ 点线路按钮切换');\n}\n","preload":false,"ruleArticles":"article[itemtype=\"http:\/\/schema.org\/BlogPosting\"]","ruleContent":"@js:\n(function () {\n  var NL = String.fromCharCode(10);\n  var UA = 'Mozilla\/5.0 (Linux; Android 13; Pixel 7) AppleWebKit\/537.36 (KHTML, like Gecko) Chrome\/124.0.0.0 Mobile Safari\/537.36';\n  var HDR = JSON.stringify({ 'User-Agent': UA });\n  var pageUrl = String(baseUrl);\n  \/\/ 线路自愈：文章链接可能落在旧线路域，正文请求改用当前选中线路重取同路径\n  var cur = '';\n  try { cur = String(source.get('jyLine')); } catch (e) { cur = ''; }\n  if (cur === 'null' || cur === 'undefined' || cur === '' || cur.indexOf('http') !== 0) {\n    cur = 'https:\/\/abandon.yixuiyyj.cc';\n  }\n  cur = cur.replace(\/\\\/+$\/, '');\n  var path = \/^https?:\\\/\\\/[^\/]+(\\\/.*)$\/.exec(pageUrl);\n  var fetchUrl = pageUrl;\n  if (path && path[1]) fetchUrl = cur + path[1];\n\n  var body = '';\n  try {\n    var r = java.connect(fetchUrl, HDR, 20000);\n    body = String(r.body());\n  } catch (e) { body = ''; }\n  if (!body || body.length < 1000 || body.indexOf('Exception') === 0) {\n    \/\/ 兜底：直接用文章原链接再取一次\n    try {\n      var r2 = java.connect(pageUrl, HDR, 20000);\n      body = String(r2.body());\n    } catch (e2) { body = ''; }\n  }\n  if (!body || body.length < 1000) {\n    return '<div style=\"padding:16px;color:#c33\">正文加载失败：线路不可用或已失效，请到登录面板测速切换线路后重试。<\/div>';\n  }\n\n  \/\/ 定位正文容器（indexOf 边界扫描，避免正则把导航\/推荐区一起吞进去）\n  var anchor = 'itemprop=\"articleBody\"';\n  var st = body.indexOf(anchor);\n  if (st < 0) {\n    return '<div style=\"padding:16px;color:#c33\">正文容器未找到（站点可能改版），原页面：<a href=\"' + fetchUrl + '\">' + fetchUrl + '<\/a><\/div>';\n  }\n  var divStart = body.lastIndexOf('<div', st);\n  var end = body.indexOf('<\/article>', st);\n  if (end < 0) end = body.indexOf('id=\"body-bottom\"', st);\n  if (end < 0) end = Math.min(body.length, st + 60000);\n  var html = body.substring(divStart, end);\n\n  \/\/ ① 懒加载图还原：把 z-image-loader-url 提为 src，保留 alt\/title\n  html = html.replace(\/<img\\b([^>]*?)>\/gi, function (tag, attrs) {\n    var m = \/z-image-loader-url\\s*=\\s*[\"']([^\"']+)[\"']\/i.exec(attrs);\n    if (!m) return tag;\n    var alt = \/alt\\s*=\\s*[\"']([^\"']*)[\"']\/i.exec(attrs);\n    var title = \/title\\s*=\\s*[\"']([^\"']*)[\"']\/i.exec(attrs);\n    var a = alt ? alt[1] : '';\n    var t = title ? title[1] : a;\n    return '<img data-jy-enc=\"' + m[1] + '\" alt=\"' + a + '\" title=\"' + t + '\" style=\"max-width:100%;height:auto;display:block;margin:8px auto;min-height:80px;background:#f0f0f0\">';\n  });\n  \/\/ ② 站点占位图（无 z-image-loader-url 的 zw.png）直接删\n  html = html.replace(\/<img\\b[^>]*\\\/usr\\\/plugins\\\/tbxw\\\/zw\\.png[^>]*>\/gi, '');\n\n  \/\/ ③ 剔除广告\/导航\/推荐\/播放器\/分享块\n  \/\/ 实测(261107)关键结构：Typecho 主题把「猜你喜欢 \/ 热门推荐」插在正文**中段**（不是尾部），\n  \/\/ 之后还有正文继续 ⇒ 绝不能「命中即从该处截断」（会丢掉后半篇文章）。\n  \/\/ 定式 = ① div 配平删除法（从 <div class=...> 起数 <div \/ <\/div> 直到配平，整块删除，正文后半段保留）\n  \/\/        ② 简单标记对删除（blockquote \/ style \/ script \/ 顶部广告位 \/ dplayer 容器）\n  var jyReDiv = \/<div\\b|<\\\/div>\/gi;\n  function JY_removeBalancedDiv(txt, startMark) {\n    var guard = 0;\n    while (guard < 12) {\n      guard++;\n      var s = txt.indexOf(startMark);\n      if (s < 0) break;\n      jyReDiv.lastIndex = s;\n      var m, depth = 0, end = -1;\n      while ((m = jyReDiv.exec(txt)) !== null) {\n        if (m[0].toLowerCase() === '<\/div>') {\n          depth--;\n          if (depth === 0) { end = m.index + 6; break; }\n        } else {\n          depth++;\n        }\n      }\n      if (end < 0) { txt = txt.substring(0, s) + txt.substring(s + startMark.length); break; }\n      txt = txt.substring(0, s) + txt.substring(end);\n    }\n    return txt;\n  }\n  \/\/ ★★ 视频块：服务端用 java.ajaxAll 两轮并行取全部直链（彻底去掉 postAwait\/JS桥依赖）\n  \/\/   背景：页内 postAwait 依赖 preloadJs 注入 JS_INJECTION，链路易碎 → 用户报「视频获取失败」。\n  \/\/   ajaxAll 实测 6 张票并行 ≈2.6s（串行 6 次 ≈21s），返回 Response 对象，.body 属性即正文字符串。\n  \/\/   POST 通过 URL 选项 ,{\"method\":\"POST\"} 走 AnalyzeUrl（已实测 ticket 接口接受）。\n  var JY_CID_M = \/\\\/archives\\\/(\\d+)\\\/\/.exec(fetchUrl);\n  var jyCid = JY_CID_M ? JY_CID_M[1] : '0';\n  var jyVideos = [];\n  var jyCfgRe = \/data-config='([^']+)'\/g, jyCm;\n  while ((jyCm = jyCfgRe.exec(body.substring(st, end))) !== null) {\n    var cfgTxt = jyCm[1].replace(\/\\\\\\\/\/g, '\/');\n    var idx = 0, poster = '';\n    var im2 = \/[?&]idx=(\\d+)\/.exec(cfgTxt); if (im2) idx = Number(im2[1]);\n    var pm2 = \/\"poster\"\\s*:\\s*\"([^\"]+)\"\/.exec(cfgTxt); if (pm2) poster = pm2[1];\n    jyVideos.push({ idx: idx, poster: poster, src: '' });\n  }\n  \/\/ 第一轮：并行取全部一次性票\n  var jyOpt = ',{\"method\":\"POST\"}';\n  var jyTicketUrls = [], ji;\n  for (ji = 0; ji < jyVideos.length; ji++) {\n    jyTicketUrls.push(cur + '\/action\/player\/ticket?cid=' + jyCid + '&idx=' + jyVideos[ji].idx\n      + '&_=' + Date.now().toString(36) + Math.random().toString(36).slice(2, 8) + ji + jyOpt);\n  }\n  var jyTickets = [];\n  try {\n    var jyTr = java.ajaxAll(jyTicketUrls, true);\n    if (jyTr && jyTr.length !== undefined) {\n      for (ji = 0; ji < jyTr.length; ji++) {\n        var tk = '';\n        try {\n          var jb = jyTr[ji].body;\n          var jbs = (typeof jb === 'function') ? String(jb.call(jyTr[ji])) : String(jb);\n          tk = JSON.parse(jbs).data.ticket;\n        } catch (e) {}\n        jyTickets.push(tk);\n      }\n    }\n  } catch (e) {}\n  \/\/ 第二轮：并行换直链（每张票独立，表单 ticket + env={} + _ver=v0）\n  var jyPlayUrls = [], jyBodies = [];\n  for (ji = 0; ji < jyVideos.length; ji++) {\n    if (!jyTickets[ji]) continue;\n    var pBody = 'ticket=' + encodeURIComponent(jyTickets[ji]) + '&env=%7B%7D&_ver=v0';\n    \/\/ ajax 的 POST body 走 URL 选项 {\"method\":\"POST\",\"body\":\"...\"}（AnalyzeUrl 支持）\n    var popt = ',{\"method\":\"POST\",\"body\":' + JSON.stringify(pBody) + '}';\n    jyPlayUrls.push(cur + '\/action\/player\/get_play_url?cid=' + jyCid + '&idx=' + jyVideos[ji].idx + popt);\n    jyBodies.push(ji);\n  }\n  try {\n    var jyPr = java.ajaxAll(jyPlayUrls, true);\n    if (jyPr && jyPr.length !== undefined) {\n      for (ji = 0; ji < jyPr.length; ji++) {\n        try {\n          var pb = jyPr[ji].body;\n          var pbs = (typeof pb === 'function') ? String(pb.call(jyPr[ji])) : String(pb);\n          var pj = JSON.parse(pbs);\n          if (pj.status !== 0) continue;\n          var pd = pj.data, pu = '';\n          if (typeof pd === 'string' && pd.indexOf('http') === 0) pu = pd;\n          else if (pd && pd.primary) pu = pd.primary;\n          if (pu && jyBodies[ji] !== undefined) jyVideos[jyBodies[ji]].src = pu;\n        } catch (e) {}\n      }\n    }\n  } catch (e) {}\n  \/\/ 把 <div class=\"vodplayer-container\">...<\/div><\/p> 替换为视频卡片（按出现顺序对应 jyVideos）\n  var jyVidIdx = 0;\n  html = html.replace(\/<div class=\"vodplayer-container\"[\\s\\S]*?<\\\/div>\\s*<\\\/div>\\s*<\\\/p>\/g, function (m0) {\n    var n = jyVideos[jyVidIdx++];\n    if (!n) return '';\n    var pic = n.poster ? ' data-jy-poster=\"' + n.poster + '\"' : '';\n    return '<div class=\"jy-vwrap\" style=\"position:relative\">'\n      + '<video class=\"jy-v\" playsinline preload=\"none\"' + pic\n      + ' style=\"width:100%;max-height:60vh;background:#000;display:block;border-radius:6px\"><\/video>'\n      + '<button class=\"jy-playbtn\" type=\"button\" style=\"position:absolute;top:50%;left:50%;transform:translate(-50%,-50%);'\n      + 'background:rgba(0,0,0,.6);color:#fff;border:2px solid #fff;border-radius:40px;padding:12px 26px;'\n      + 'font-size:16px;cursor:pointer;z-index:5\">▶ 点击播放<\/button>'\n      + '<div class=\"jy-tip\" style=\"display:none;color:#0a58ca;font-size:13px;padding:6px 2px\">'\n      + '视频 ' + (n.idx + 1) + ' · 直链有时效，失效请退出重进本文刷新<\/div>'\n      + '<\/div>';\n  });\n  html = JY_removeBalancedDiv(html, '<div class=\"guess-like-post\"');\n  html = JY_removeBalancedDiv(html, '<div class=\"hot-recommend-post\"');\n  html = JY_removeBalancedDiv(html, '<div class=\"a2a_kit');\n  html = JY_removeBalancedDiv(html, '<div class=\"flash\"');\n  html = JY_removeBalancedDiv(html, '<div id=\"top-slot-btn\"');\n  html = JY_removeBalancedDiv(html, '<div id=\"top-slot-img\"');\n  \/\/ 简单标记对（无嵌套）\n  var cuts = [['<blockquote>', '<\/blockquote>'], ['<style>', '<\/style>'], ['<script', '<\/script>']];\n  var ci, from, to;\n  for (ci = 0; ci < cuts.length; ci++) {\n    var safe = 0;\n    while (safe < 40) {\n      safe++;\n      from = html.indexOf(cuts[ci][0]);\n      if (from < 0) break;\n      to = html.indexOf(cuts[ci][1], from + cuts[ci][0].length);\n      if (to < 0) { html = html.substring(0, from) + html.substring(from + cuts[ci][0].length); break; }\n      html = html.substring(0, from) + html.substring(to + cuts[ci][1].length);\n    }\n  }\n  \/\/ ④ 残留内联样式\/事件\/空壳\/分享尾巴清理\n  html = html.replace(\/\\sonclick\\s*=\\s*[\"'][^\"']*[\"']\/gi, '');\n  html = html.replace(\/\\sdata-config\\s*=\\s*'[^']*'\/gi, '');\n  html = html.replace(\/\\sdata-video_[a-z_]+\\s*=\\s*\"[^\"]*\"\/gi, '');\n  html = html.replace(\/<div class=\"bling\"[\\s\\S]*?<\\\/div>\/gi, '');\n  html = html.replace(\/<!--[\\s\\S]*?-->\/g, '');\n  html = html.replace(\/<p>\\s*<\\\/p>\/gi, '');\n  html = html.replace(\/<aside\\b[^>]*>[\\s\\S]*?<\\\/aside>\/gi, '');\n  \/\/ 收尾：若末尾残留未闭合的容器 div，截到最后一个 <\/p> 或 <\/h2> 之后\n  var lastP = html.lastIndexOf('<\/p>'), lastH = html.lastIndexOf('<\/h2>');\n  var cut = Math.max(lastP, lastH);\n  if (cut > 0 && html.indexOf('<div class=\"bling\"') < 0) {\n    \/\/ 只在尾部确属站点残留时截断（保持正文完整）\n    var tail = html.substring(cut);\n    if (\/^\\s*(?:<\\\/div>\\s*|<div\\b[^>]*>\\s*)*$\/i.test(tail)) html = html.substring(0, cut + 4);\n  }\n\n  \/\/ 标题 + 来源行 + 正文 + 视频播放器\n  var tm = \/<title>([^<]*)<\\\/title>\/.exec(body);\n  var tt = tm ? tm[1].replace(\/\\s*-\\s*91爆料\\s*$\/, '') : '';\n  \/\/ 页内播放器脚本：只替换视频数据（JSON.stringify 保证转义安全）\n  var jyPageJs = \"\/\/ 页内播放器 JS（直链已由 ruleContent 服务端 ajaxAll 并行取好，写进 JY_VIDEOS[i].src）\\n\/\/ ★ 用户要求：**只有用户点击才播放**，绝不全部一起自动播。\\n\/\/   做法：video 初始无 src、无 controls、preload=none，上面盖一个「▶ 点击播放」按钮；\\n\/\/         点按钮 → jyAttach(hls) + startLoad + play()，并暂停其它视频。\\nvar JY_VIDEOS = __JY_VIDEOS__;\\nvar JY_HLSES = [], JY_ATTACHED = [];\\nfunction jyTip(el, t) {\\n  try { var n = el.parentNode.querySelector('.jy-tip'); if (n) { n.textContent = t; n.style.display = 'block'; } } catch (e) {}\\n}\\nfunction jyPauseOthers(except) {\\n  try {\\n    var vs = document.querySelectorAll('video.jy-v');\\n    for (var i = 0; i < vs.length; i++) if (vs[i] !== except && !vs[i].paused) vs[i].pause();\\n  } catch (e) {}\\n}\\nfunction jyAttach(v, src, i) {\\n  if (!src || JY_ATTACHED[i]) return;\\n  JY_ATTACHED[i] = true;\\n  if (window.Hls && Hls.isSupported() && src.indexOf('.m3u8') > -1) {\\n    try {\\n      var h = new Hls({ enableSoftwareAES: true, maxBufferLength: 30, maxMaxBufferLength: 60, autoStartLoad: false });\\n      h.loadSource(src); h.attachMedia(v);\\n      h.on(Hls.Events.ERROR, function (e, d) {\\n        if (!d.fatal) return;\\n        if (d.type === Hls.ErrorTypes.NETWORK_ERROR) jyTip(v, '直链过期或网络失败，退出重进本文刷新');\\n        else if (d.type === Hls.ErrorTypes.MEDIA_ERROR) { try { h.recoverMediaError(); } catch (x) {} }\\n        else jyTip(v, '播放出错，退出重进本文刷新');\\n      });\\n      JY_HLSES[i] = h;\\n      return;\\n    } catch (e) {}\\n  }\\n  v.src = src;\\n}\\nfunction jyPlayOnClick(v, i) {\\n  try {\\n    var n = JY_VIDEOS[i];\\n    if (!n || !n.src) { jyTip(v, '该视频直链获取失败，退出重进本文可刷新'); return; }\\n    jyPauseOthers(v);                       \/\/ 同一时刻只播一个\\n    jyAttach(v, n.src, i);\\n    if (JY_HLSES[i]) { try { JY_HLSES[i].startLoad(); } catch (e) {} }\\n    v.controls = true;                      \/\/ 播放后才给原生控件\\n    var p = v.play();\\n    if (p && p.catch) p.catch(function () {});\\n    var btn = v.parentNode.querySelector('.jy-playbtn');\\n    if (btn) btn.style.display = 'none';\\n  } catch (e) {}\\n}\\nfunction jyBoot() {\\n  try {\\n    var vids = document.querySelectorAll('video.jy-v');\\n    for (var i = 0; i < vids.length; i++) {\\n      (function (v, i) {\\n        try {\\n          var btn = v.parentNode.querySelector('.jy-playbtn');\\n          if (btn) btn.addEventListener('click', function (e) { e.preventDefault(); e.stopPropagation(); jyPlayOnClick(v, i); });\\n          \/\/ 点视频区域（poster 区）也等同点按钮\\n          v.addEventListener('click', function (e) { e.preventDefault(); jyPlayOnClick(v, i); });\\n        } catch (e) {}\\n      })(vids[i], i);\\n    }\\n  } catch (e) {}\\n}\\n\/\/ hls.js 用 async 加载，但绑定点击不依赖它（用户点击时若还没就绪，jyAttach 会走原生兜底；\\n\/\/ 8 秒后补一次，保证点击晚于脚本加载的场景能用 hls）\\nfunction jyEnsureHls() {\\n  jyBoot();\\n  var h = document.getElementById('jy-hls');\\n  if (h && !window.Hls) {\\n    h.addEventListener('error', function () {\\n      var s = document.createElement('script');\\n      s.src = 'https:\/\/s4.zstatic.net\/ajax\/libs\/hls.js\/1.6.13\/hls.min.js';\\n      (document.head || document.body).appendChild(s);\\n    });\\n  }\\n}\\nif (document.readyState === 'complete' || document.readyState === 'interactive') {\\n  setTimeout(jyEnsureHls, 0);\\n} else {\\n  document.addEventListener('DOMContentLoaded', function () { setTimeout(jyEnsureHls, 0); });\\n}\\n\".replace('__JY_VIDEOS__', JSON.stringify(jyVideos));\n  var out = '<!DOCTYPE html><html><head><meta charset=\"utf-8\"><meta name=\"viewport\" content=\"width=device-width,initial-scale=1\">'\n    + '<style>body{margin:0;padding:12px 14px;background:#fff;color:#222;font-size:16px;line-height:1.85;word-wrap:break-word}'\n    + 'img{max-width:100%!important;height:auto!important}h1{font-size:20px;line-height:1.5;margin:6px 0 14px}'\n    + 'h2{font-size:18px;margin:18px 0 8px}p{margin:10px 0}a{color:#0a58ca;word-break:break-all}'\n    + '.jy-src{color:#888;font-size:12px;border-bottom:1px solid #eee;padding-bottom:8px;margin-bottom:14px}'\n    + '.jy-vwrap{margin:14px 0;background:#000;border-radius:6px;overflow:hidden}'\n    + 'blockquote{margin:8px 0;padding:8px 12px;background:#f7f7f7;border-left:3px solid #ddd}<\/style>'\n    + '<script id=\"jy-hls\" async src=\"' + cur + '\/usr\/plugins\/ArtPlayer\/assets\/hls.min.js?v=1.6.7\"><\\\/script>'\n    + '<\/head><body>'\n    + (tt ? '<h1>' + tt + '<\/h1>' : '')\n    + '<div class=\"jy-src\">91爆料 · 当前线路 ' + cur + ' · 含 ' + jyVideos.length + ' 段视频（点击视频下方文字可刷新直链）<\/div>'\n    + html\n    + '<script>' + \"\/\/ 正文图片页内解密（pic.hdhwqx.cn AES-128-CBC）\\n\/\/ 优先 Web Crypto crypto.subtle（原生毫秒级），不可用时回退纯 JS AES。\\n\/\/ 不依赖 preloadJs \/ JS 桥：本脚本直接内联在 ruleContent 输出的 HTML 里（由 script 标签包裹）。\\n\/\/ 图片域 ACAO:* 已实测，fetch 可跨域；baseUrl 为 https → 安全上下文，subtle 可用。\\n(function () {\\n  var KEY = 'f5d965df75336270', IV = '97b60394abc2fbe1';\\n  function sb(x){var a=new Uint8Array(x.length);for(var i=0;i<x.length;i++)a[i]=x.charCodeAt(i)&255;return a}\\n  var KB = sb(KEY), IVB = sb(IV);\\n  function mime(u8){\\n    if(u8.length>=3&&u8[0]===0x47&&u8[1]===0x49&&u8[2]===0x46)return 'image\/gif';\\n    if(u8.length>=2&&u8[0]===0xff&&u8[1]===0xd8)return 'image\/jpeg';\\n    if(u8.length>=4&&u8[0]===0x89&&u8[1]===0x50)return 'image\/png';\\n    if(u8.length>=12&&u8[8]===0x57&&u8[9]===0x45&&u8[10]===0x42&&u8[11]===0x50)return 'image\/webp';\\n    return 'image\/jpeg';\\n  }\\n  function setImg(img, u8){\\n    try{\\n      var blob=new Blob([u8],{type:mime(u8)});\\n      var u=URL.createObjectURL(blob);\\n      img.src=u; img.removeAttribute('data-jy-enc');\\n    }catch(e){}\\n  }\\n  \/\/ ---- 纯 JS AES 兜底（Web Crypto 不可用时）----\\n  var SBOX=[0x63,0x7c,0x77,0x7b,0xf2,0x6b,0x6f,0xc5,0x30,0x01,0x67,0x2b,0xfe,0xd7,0xab,0x76,0xca,0x82,0xc9,0x7d,0xfa,0x59,0x47,0xf0,0xad,0xd4,0xa2,0xaf,0x9c,0xa4,0x72,0xc0,0xb7,0xfd,0x93,0x26,0x36,0x3f,0xf7,0xcc,0x34,0xa5,0xe5,0xf1,0x71,0xd8,0x31,0x15,0x04,0xc7,0x23,0xc3,0x18,0x96,0x05,0x9a,0x07,0x12,0x80,0xe2,0xeb,0x27,0xb2,0x75,0x09,0x83,0x2c,0x1a,0x1b,0x6e,0x5a,0xa0,0x52,0x3b,0xd6,0xb3,0x29,0xe3,0x2f,0x84,0x53,0xd1,0x00,0xed,0x20,0xfc,0xb1,0x5b,0x6a,0xcb,0xbe,0x39,0x4a,0x4c,0x58,0xcf,0xd0,0xef,0xaa,0xfb,0x43,0x4d,0x33,0x85,0x45,0xf9,0x02,0x7f,0x50,0x3c,0x9f,0xa8,0x51,0xa3,0x40,0x8f,0x92,0x9d,0x38,0xf5,0xbc,0xb6,0xda,0x21,0x10,0xff,0xf3,0xd2,0xcd,0x0c,0x13,0xec,0x5f,0x97,0x44,0x17,0xc4,0xa7,0x7e,0x3d,0x64,0x5d,0x19,0x73,0x60,0x81,0x4f,0xdc,0x22,0x2a,0x90,0x88,0x46,0xee,0xb8,0x14,0xde,0x5e,0x0b,0xdb,0xe0,0x32,0x3a,0x0a,0x49,0x06,0x24,0x5c,0xc2,0xd3,0xac,0x62,0x91,0x95,0xe4,0x79,0xe7,0xc8,0x37,0x6d,0x8d,0xd5,0x4e,0xa9,0x6c,0x56,0xf4,0xea,0x65,0x7a,0xae,0x08,0xba,0x78,0x25,0x2e,0x1c,0xa6,0xb4,0xc6,0xe8,0xdd,0x74,0x1f,0x4b,0xbd,0x8b,0x8a,0x70,0x3e,0xb5,0x66,0x48,0x03,0xf6,0x0e,0x61,0x35,0x57,0xb9,0x86,0xc1,0x1d,0x9e,0xe1,0xf8,0x98,0x11,0x69,0xd9,0x8e,0x94,0x9b,0x1e,0x87,0xe9,0xce,0x55,0x28,0xdf,0x8c,0xa1,0x89,0x0d,0xbf,0xe6,0x42,0x68,0x41,0x99,0x2d,0x0f,0xb0,0x54,0xbb,0x16];\\n  var INV=new Uint8Array(256),RCON=[1,2,4,8,16,32,64,128,27,54],q;for(q=0;q<256;q++)INV[SBOX[q]]=q;\\n  function xt(a){return ((a<<1)^((a&128)?27:0))&255}\\n  function mul(a,b){var r=0;while(b){if(b&1)r^=a;a=xt(a);b>>=1}return r}\\n  function expK(k){var w=[],i,j,t,r;for(i=0;i<16;i++)w.push(k[i]);for(i=16;i<176;i+=4){t=[w[i-4],w[i-3],w[i-2],w[i-1]];if(i%16===0){var z=t[0];t[0]=SBOX[t[1]]^RCON[i\/16-1];t[1]=SBOX[t[2]];t[2]=SBOX[t[3]];t[3]=SBOX[z]}for(j=0;j<4;j++)w.push((w[i+j-16]^t[j])&255)}var R=[];for(r=0;r<=10;r++){var s=[];for(i=0;i<16;i++)s.push(w[r*16+i]);R.push(s)}return R}\\n  function ark(s,k){for(var i=0;i<16;i++)s[i]^=k[i]}\\n  function isr(s){var t=s.slice(0);s[1]=t[13];s[5]=t[1];s[9]=t[5];s[13]=t[9];s[2]=t[10];s[6]=t[14];s[10]=t[2];s[14]=t[6];s[3]=t[7];s[7]=t[11];s[11]=t[15];s[15]=t[3]}\\n  function isb(s){for(var i=0;i<16;i++)s[i]=INV[s[i]]}\\n  function imc(s){for(var c=0;c<4;c++){var i=c*4,a0=s[i],a1=s[i+1],a2=s[i+2],a3=s[i+3];s[i]=mul(a0,14)^mul(a1,11)^mul(a2,13)^mul(a3,9);s[i+1]=mul(a0,9)^mul(a1,14)^mul(a2,11)^mul(a3,13);s[i+2]=mul(a0,13)^mul(a1,9)^mul(a2,14)^mul(a3,11);s[i+3]=mul(a0,11)^mul(a1,13)^mul(a2,9)^mul(a3,14)}}\\n  function decB(b,R){var s=b.slice(0),r;ark(s,R[10]);for(r=9;r>=0;r--){isr(s);isb(s);ark(s,R[r]);if(r>0)imc(s)}return s}\\n  function jsDec(u8){var n=u8.length,i,j;if(!n||n%16)return null;var R=expK(Array.prototype.slice.call(KB)),out=new Uint8Array(n),prev=Array.prototype.slice.call(IVB);\\n    for(i=0;i<n;i+=16){var blk=Array.prototype.slice.call(u8.subarray(i,i+16)),d=decB(blk,R);\\n      for(j=0;j<16;j++)out[i+j]=d[j]^prev[j];prev=blk}\\n    var pad=out[n-1];if(pad<1||pad>16)return null;\\n    for(i=n-pad;i<n;i++)if(out[i]!==pad)return null;\\n    return out.subarray(0,n-pad)}\\n\\n  function decryptOne(img){\\n    var u=img.getAttribute('data-jy-enc');\\n    if(!u)return;\\n    fetch(u,{mode:'cors'}).then(function(r){return r.arrayBuffer()}).then(function(buf){\\n      var enc=new Uint8Array(buf);\\n      if(enc.length%16)throw new Error('len');\\n      if(window.crypto&&window.crypto.subtle&&window.crypto.subtle.importKey){\\n        return window.crypto.subtle.importKey('raw',KB,{name:'AES-CBC'},false,['decrypt'])\\n          .then(function(k){return window.crypto.subtle.decrypt({name:'AES-CBC',iv:IVB},k,buf)})\\n          .then(function(d){return new Uint8Array(d)});\\n      }\\n      return jsDec(enc);\\n    }).then(function(u8){if(u8&&u8.length)setImg(img,u8)}).catch(function(){});\\n  }\\n  function boot(){\\n    var imgs=document.querySelectorAll('img[data-jy-enc]');\\n    for(var i=0;i<imgs.length;i++)decryptOne(imgs[i]);\\n    \/\/ video 的 poster 也是加密图：借用临时 img 解密后把 blob URL 赋给 video.poster\\n    var vs=document.querySelectorAll('video[data-jy-poster]');\\n    for(var k=0;k<vs.length;k++){\\n      (function(v){\\n        var tmp=new Image();\\n        tmp.setAttribute('data-jy-enc',v.getAttribute('data-jy-poster'));\\n        decryptOne(tmp);\\n        \/\/ decryptOne 是异步，轮询等 tmp.src 变成 blob:\\n        var n=0,t=setInterval(function(){\\n          n++;\\n          if(tmp.src&&tmp.src.indexOf('blob:')===0){v.poster=tmp.src;clearInterval(t)}\\n          else if(n>100)clearInterval(t);\\n        },100);\\n      })(vs[k]);\\n    }\\n  }\\n  if(document.readyState==='complete'||document.readyState==='interactive')setTimeout(boot,0);\\n  else document.addEventListener('DOMContentLoaded',function(){setTimeout(boot,0)});\\n})();\" + '<\\\/script>'\n    + '<script>' + jyPageJs + '<\\\/script>'\n    + '<\/body><\/html>';\n  return out;\n})()","ruleImage":"@js:(function(){try{var e=result.select('img[z-image-loader-url]');var u=e.size()>0?String(e.get(0).attr('z-image-loader-url')):'';if(!u){var i=result.select('img[src]');if(i.size()>0)u=String(i.get(0).attr('src'))}if(!u)return '';var k=u.indexOf(':\/\/');if(k<0)return u;var head=u.substring(0,k+3);var rest=u.substring(k+3);while(rest.indexOf('\/\/')===0)rest=rest.substring(1);while(rest.indexOf('\/\/')>-1)rest=rest.split('\/\/').join('\/');return head+rest}catch(e){return ''}})()","ruleLink":"@js:(function(){try{var e=result.select('a[href]');if(e.size()>0){return e.get(0).attr('href')}return ''}catch(e){return ''}})()","ruleNextPage":"PAGE","rulePubDate":"@js:(function(){try{var e=result.select('[itemprop=datePublished]');if(e.size()>0){var c=e.get(0).attr('content');if(c)return c;return e.get(0).text()}return ''}catch(e){return ''}})()","ruleTitle":"@js:(function(){try{var e=result.select('.post-card-title');if(e.size()>0){return e.get(0).ownText()}return ''}catch(e){return ''}})()","searchUrl":"{{(function(){var d='';try{d=String(source.get('jyLine'))}catch(e){d=''}if(d==='null'||d==='undefined'||d===''||d.indexOf('http')!==0){d='https:\/\/abandon.yixuiyyj.cc'}d=d.replace(\/\\\/+$\/,'');var p=(page&&page>1)?page:1;return d+'\/search\/'+encodeURIComponent(key)+'\/'+p+'\/'})()}}","shouldOverrideUrlLoading":"if (\/^https?:\\\/\\\/\/.test(url)) {\n  var ok = \/(yixuiyyj\\.cc|cvcmneja\\.cc|cloudfront\\.net|pic\\.hdhwqx\\.cn|op\\.udhhzr\\.cn|oolrvd\\.cn|udhhzr\\.cn|s4\\.zstatic\\.net|jybl2[0-9]\\.com|91bl[a-z0-9]*\\.com|abandon\\.)\/.test(url);\n  if (!ok) { java.toast('已拦截外部跳转：' + url); true; } else { false; }\n} else { false; }","showWebLog":false,"singleUrl":false,"sortUrl":"@js:\n(function () {\n  var d = '';\n  try { d = String(source.get('jyLine')); } catch (e) { d = ''; }\n  if (d === 'null' || d === 'undefined' || d === '' || d.indexOf('http') !== 0) {\n    d = 'https:\/\/abandon.yixuiyyj.cc';\n  }\n  d = d.replace(\/\\\/+$\/, '');\n  var C = [\n    ['📰 最新', ''],\n    ['🍉 今日吃瓜', 'jrcg1'], ['🏆 每日大赛', 'mrds'], ['🤖 AI短剧', 'aiduanju'],\n    ['🎀 萝莉jk', 'lljk'], ['🌐 网黄资源', 'ylgx'], ['🔥 热门大瓜', 'rgjx'],\n    ['🌊 海角伦理', 'llzq'], ['💥 反差爆料', 'fcsj'], ['📺 st站直播回放', 'stzzb'],\n    ['🏫 校园爆料', 'xyrg'], ['📷 探花偷拍', 'lpzq'], ['🎬 AV动漫', 'gcqs'],\n    ['🔍 全网疯求', 'qwfq'], ['⭐ 明星爆料', 'whbg'], ['🎭 奇闻异事', 'qwys'],\n    ['🎨 AI成人漫剧', 'aimj'], ['🌐 体育直播', 'tycg']\n  ];\n  var out = [], i, name, seg, line;\n  for (i = 0; i < C.length; i++) {\n    name = C[i][0]; seg = C[i][1];\n    if (seg === '') {\n      line = name + '::' + d + '\/page\/{{page}}\/';\n    } else {\n      line = name + '::' + d + '\/category\/' + seg + '\/{{page}}\/';\n    }\n    out.push(line);\n  }\n  return out.join('\\n');\n})()","sourceComment":"发布页 https:\/\/jybl26.com（Base64编码，zz_line 3条泛子域线路）；内容站 Typecho Mirages，17分类，路径式分页；免登录。正文含图文+多视频：两步票据协议取 AES-128 HLS 直链，hls.js 播放，页内 postAwait 自愈（直链短时效+正文缓存）。登录面板可获取发布页线路\/测速\/切换\/检查登录状态。兼容 LegadoTeam 与 legado-E。","sourceGroup":"R18,AI","sourceIcon":"https:\/\/jybl26.com\/favicon.ico?v=1","sourceName":"91爆料·吃瓜","sourceUrl":"https:\/\/abandon.yixuiyyj.cc\/","style":"img{max-width:100%!important;height:auto!important;display:block;margin:8px auto;}video{max-width:100%!important;background:#000}body{padding:0 12px;word-wrap:break-word;}","type":0,"variableComment":"jyLine=当前线路(默认 https:\/\/abandon.yixuiyyj.cc)；jyPub=发布页地址；jyFound=已获取线路列表；jyDelay0..5=各线路测速结果"}]