Files
zsglpt/static/admin/assets/SystemPage-eaCcaVxM.js
yuyx 7007f5f6f5 feat: 完成 Passkey 能力与前后台加载优化
更新说明:\n1. 新增用户端与管理员端 Passkey 登录/注册/设备管理(最多3台,支持设备备注、删除设备)。\n2. 修复 Passkey 注册与登录流程中的浏览器/证书/CSRF相关问题,增强错误提示。\n3. 前台登录页改为独立入口,首屏仅加载必要资源,其他页面按需加载。\n4. 系统配置页改为静默获取金山文档状态,避免首屏阻塞,并优化状态展示为“检测中/已登录/未登录/异常”。\n5. 补充后端接口与页面渲染适配,修复多入口下样式依赖注入问题。\n6. 同步更新前后台构建产物与相关静态资源。
2026-02-15 23:51:46 +08:00

7 lines
14 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import{f as Ce,u as ne}from"./system-CeJP0y2Z.js";import{a as C,_ as Se}from"./index-BMIn4N2u.js";import{E as me,a as m}from"./vendor-element-B5S5pUKo.js";import{r as n,c as le,l as Pe,R as Ie,o as Ae,aj as p,ap as Ne,F as De,q as P,n as I,t as o,L as a,E as s,I as f,G as ae,y as Ke,J as te}from"./vendor-vue-CVxSw_oJ.js";import"./vendor-axios-B9ygI19o.js";import"./vendor-misc-BeoNyvBp.js";async function ue(r={},c={}){const{data:v}=await C.get("/kdocs/status",{params:r,...c});return v}async function Ee(r={}){const c={force:!0,...r},{data:v}=await C.post("/kdocs/qr",c);return v}async function Le(){const{data:r}=await C.post("/kdocs/clear-login",{});return r}async function Qe(){const{data:r}=await C.get("/proxy/config");return r}async function Te(r){const{data:c}=await C.post("/proxy/config",r);return c}async function qe(r){const{data:c}=await C.post("/proxy/test",r);return c}const Be={class:"page-stack"},$e={class:"config-grid"},Re={class:"row-actions"},Me={class:"row-actions"},Fe={class:"row-actions"},he={class:"section-head"},ze={class:"status-inline app-muted"},He={key:0,class:"status-dots","aria-hidden":"true"},Ge={class:"kdocs-inline"},Oe={class:"kdocs-range"},je={class:"row-actions"},Je={key:0,class:"help"},We={key:1,class:"help"},Xe={class:"kdocs-qr"},Ye=["src"],Ze={__name:"SystemPage",setup(r){const c=n(!1),v=n(2),A=n(1),N=n(3),D=n(120),S=n(!1),_=n(""),K=n(3),E=n(!1),L=n(10),Q=n(7),T=n(!1),q=n(""),B=n(""),$=n(""),R=n(0),M=n("A"),F=n("D"),h=n(0),z=n(0),H=n(!1),G=n(""),y=n({}),k=n(!1),b=n(""),oe=n(!1),x=n(!1),w=n(!1),U=n(!1),O=n(!1),j=n("");let J=null;const de=le(()=>x.value||w.value||U.value),se=le(()=>O.value||x.value||oe.value),W=le(()=>{if(se.value)return"检测中";const l=y.value||{};return l?.logged_in===!0||l?.last_login_ok===!0?"已登录":l?.logged_in===!1||l?.last_login_ok===!1||l?.login_required===!0?"未登录":l?.last_error?"异常":"未知"}),ce=le(()=>se.value?"is-checking":W.value==="已登录"?"is-online":W.value==="未登录"?"is-offline":W.value==="异常"?"is-error":"is-unknown");function d(l){if(!l){j.value="";return}const e=new Date().toLocaleTimeString("zh-CN",{hour12:!1});j.value=`${l} (${e})`}async function ve(){c.value=!0;try{const[l,e]=await Promise.all([Ce(),Qe()]);v.value=l.max_concurrent_global??2,A.value=l.max_concurrent_per_account??1,N.value=l.max_screenshot_concurrent??3,D.value=l.db_slow_query_ms??120,E.value=(l.auto_approve_enabled??0)===1,L.value=l.auto_approve_hourly_limit??10,Q.value=l.auto_approve_vip_days??7,S.value=(e.proxy_enabled??0)===1,_.value=e.proxy_api_url||"",K.value=e.proxy_expire_minutes??3,T.value=(l.kdocs_enabled??0)===1,q.value=l.kdocs_doc_url||"",B.value=l.kdocs_default_unit||"",$.value=l.kdocs_sheet_name||"",R.value=l.kdocs_sheet_index??0,M.value=(l.kdocs_unit_column||"A").toUpperCase(),F.value=(l.kdocs_image_column||"D").toUpperCase(),h.value=l.kdocs_row_start??0,z.value=l.kdocs_row_end??0,H.value=(l.kdocs_admin_notify_enabled??0)===1,G.value=l.kdocs_admin_notify_email||""}catch{}finally{c.value=!1}pe()}async function pe(){if(!(O.value||x.value)){O.value=!0;try{const l=await ue({},{__silent:!0,__no_retry:!0,timeout:8e3});y.value=l||{}}catch{}finally{O.value=!1}}}async function fe(){const l={max_concurrent_global:Number(v.value),max_concurrent_per_account:Number(A.value),max_screenshot_concurrent:Number(N.value),db_slow_query_ms:Number(D.value)};try{await me.confirm(`确定更新并发配置吗?
全局并发数: ${l.max_concurrent_global}
单账号并发数: ${l.max_concurrent_per_account}
截图并发数: ${l.max_screenshot_concurrent}
慢 SQL 阈值: ${l.db_slow_query_ms}ms`,"保存并发配置",{confirmButtonText:"保存",cancelButtonText:"取消",type:"warning"})}catch{return}try{const e=await ne(l);m.success(e?.message||"并发配置已更新")}catch{}}async function _e(){if(S.value&&!_.value.trim()){m.error("启用代理时API地址不能为空");return}const l={proxy_enabled:S.value?1:0,proxy_api_url:_.value.trim(),proxy_expire_minutes:Number(K.value)||3};try{const e=await Te(l);m.success(e?.message||"代理配置已更新")}catch{}}async function ye(){if(!_.value.trim()){m.error("请先输入代理API地址");return}try{const l=await qe({api_url:_.value.trim()});await me.alert(l?.message||"测试完成","代理测试",{confirmButtonText:"知道了"})}catch{}}async function ge(){const l=Number(L.value),e=Number(Q.value);if(!Number.isFinite(l)||l<1){m.error("每小时注册限制必须大于0");return}if(!Number.isFinite(e)||e<0){m.error("VIP天数不能为负数");return}const i={auto_approve_enabled:E.value?1:0,auto_approve_hourly_limit:l,auto_approve_vip_days:e};try{const u=await ne(i);m.success(u?.message||"注册设置已保存")}catch{}}async function Ve(){const l={kdocs_enabled:T.value?1:0,kdocs_doc_url:q.value.trim(),kdocs_default_unit:B.value.trim(),kdocs_sheet_name:$.value.trim(),kdocs_sheet_index:Number(R.value)||0,kdocs_unit_column:M.value.trim().toUpperCase(),kdocs_image_column:F.value.trim().toUpperCase(),kdocs_row_start:Number(h.value)||0,kdocs_row_end:Number(z.value)||0,kdocs_admin_notify_enabled:H.value?1:0,kdocs_admin_notify_email:G.value.trim()};try{const e=await ne(l);m.success(e?.message||"表格配置已更新")}catch{}}async function re(){if(!x.value){x.value=!0,d("正在刷新状态");try{y.value=await ue({live:1}),d("状态已刷新")}catch{d("刷新失败,请稍后重试")}finally{x.value=!1}}}async function ie(){try{const l=await ue({live:1});y.value=l,(l?.logged_in===!0||l?.last_login_ok===!0)&&(m.success("扫码成功,已登录"),d("扫码成功,已登录"),k.value=!1,X())}catch{}}function ke(){X(),oe.value=!0,d("扫码检测中"),ie(),J=setInterval(ie,2e3)}function X(){J&&(clearInterval(J),J=null),oe.value=!1}async function be(){if(!w.value){w.value=!0,d("正在获取二维码");try{b.value="";const l=await Ee();if(b.value=l?.qr_image||"",!b.value){if(l?.logged_in){m.success("当前已登录,无需扫码"),d("当前已登录,无需扫码"),await re();return}m.warning("未获取到二维码"),d("未获取到二维码");return}d("二维码已获取"),k.value=!0}catch{d("获取二维码失败")}finally{w.value=!1}}}async function xe(){if(!U.value){U.value=!0,d("正在清除登录态");try{await Le(),k.value=!1,b.value="",m.success("登录态已清除"),d("登录态已清除"),await re()}catch{d("清除登录态失败")}finally{U.value=!1}}}return Pe(k,l=>{l?ke():X()}),Ie(()=>{X()}),Ae(ve),(l,e)=>{const i=p("el-input-number"),u=p("el-form-item"),Y=p("el-form"),g=p("el-button"),Z=p("el-card"),ee=p("el-switch"),V=p("el-input"),we=p("el-dialog"),Ue=Ne("loading");return De((P(),I("div",Be,[e[50]||(e[50]=o("div",{class:"app-page-title"},[o("h2",null,"系统配置")],-1)),o("div",$e,[a(Z,{shadow:"never","body-style":{padding:"16px"},class:"card section-card"},{default:s(()=>[e[27]||(e[27]=o("h3",{class:"section-title"},"并发配置",-1)),e[28]||(e[28]=o("div",{class:"section-sub app-muted"},"控制任务与截图的并发资源上限",-1)),a(Y,{"label-width":"122px"},{default:s(()=>[a(u,{label:"全局最大并发数"},{default:s(()=>[a(i,{modelValue:v.value,"onUpdate:modelValue":e[0]||(e[0]=t=>v.value=t),min:1,max:200},null,8,["modelValue"]),e[22]||(e[22]=o("div",{class:"help"},"同时最多运行账号数(浏览任务 API 执行,资源占用较低)。",-1))]),_:1}),a(u,{label:"单账号最大并发数"},{default:s(()=>[a(i,{modelValue:A.value,"onUpdate:modelValue":e[1]||(e[1]=t=>A.value=t),min:1,max:50},null,8,["modelValue"]),e[23]||(e[23]=o("div",{class:"help"},"建议保持为 1避免同账号任务抢占。",-1))]),_:1}),a(u,{label:"截图最大并发数"},{default:s(()=>[a(i,{modelValue:N.value,"onUpdate:modelValue":e[2]||(e[2]=t=>N.value=t),min:1,max:50},null,8,["modelValue"]),e[24]||(e[24]=o("div",{class:"help"},"截图资源占用较低,可按机器性能逐步提高。",-1))]),_:1}),a(u,{label:"慢 SQL 阈值(ms)"},{default:s(()=>[a(i,{modelValue:D.value,"onUpdate:modelValue":e[3]||(e[3]=t=>D.value=t),min:0,max:6e4},null,8,["modelValue"]),e[25]||(e[25]=o("div",{class:"help"},"低于该阈值不会计入慢 SQL0 表示关闭慢 SQL 采样)。",-1))]),_:1})]),_:1}),o("div",Re,[a(g,{type:"primary",onClick:fe},{default:s(()=>[...e[26]||(e[26]=[f("保存并发配置",-1)])]),_:1})])]),_:1}),a(Z,{shadow:"never","body-style":{padding:"16px"},class:"card section-card"},{default:s(()=>[e[33]||(e[33]=o("h3",{class:"section-title"},"代理设置",-1)),e[34]||(e[34]=o("div",{class:"section-sub app-muted"},"用于任务出网代理与连接有效期管理",-1)),a(Y,{"label-width":"122px"},{default:s(()=>[a(u,{label:"启用 IP 代理"},{default:s(()=>[a(ee,{modelValue:S.value,"onUpdate:modelValue":e[4]||(e[4]=t=>S.value=t)},null,8,["modelValue"]),e[29]||(e[29]=o("div",{class:"help"},"开启后,浏览任务通过代理访问,失败自动重试。",-1))]),_:1}),a(u,{label:"代理 API 地址"},{default:s(()=>[a(V,{modelValue:_.value,"onUpdate:modelValue":e[5]||(e[5]=t=>_.value=t),placeholder:"http://api.xxx/Tools/IP.ashx?..."},null,8,["modelValue"]),e[30]||(e[30]=o("div",{class:"help"},"API 应返回 `IP:PORT`123.45.67.89:8888。",-1))]),_:1}),a(u,{label:"有效期(分钟)"},{default:s(()=>[a(i,{modelValue:K.value,"onUpdate:modelValue":e[6]||(e[6]=t=>K.value=t),min:1,max:60},null,8,["modelValue"])]),_:1})]),_:1}),o("div",Me,[a(g,{type:"primary",onClick:_e},{default:s(()=>[...e[31]||(e[31]=[f("保存代理配置",-1)])]),_:1}),a(g,{onClick:ye},{default:s(()=>[...e[32]||(e[32]=[f("测试代理",-1)])]),_:1})])]),_:1}),a(Z,{shadow:"never","body-style":{padding:"16px"},class:"card section-card"},{default:s(()=>[e[37]||(e[37]=o("h3",{class:"section-title"},"注册设置",-1)),e[38]||(e[38]=o("div",{class:"section-sub app-muted"},"控制注册节流与新用户赠送 VIP",-1)),a(Y,{"label-width":"122px"},{default:s(()=>[a(u,{label:"注册赠送 VIP"},{default:s(()=>[a(ee,{modelValue:E.value,"onUpdate:modelValue":e[7]||(e[7]=t=>E.value=t)},null,8,["modelValue"]),e[35]||(e[35]=o("div",{class:"help"},"开启后,新用户注册成功自动赠送下方设定的 VIP 天数。",-1))]),_:1}),a(u,{label:"每小时注册限制"},{default:s(()=>[a(i,{modelValue:L.value,"onUpdate:modelValue":e[8]||(e[8]=t=>L.value=t),min:1,max:1e4},null,8,["modelValue"])]),_:1}),a(u,{label:"赠送 VIP 天数"},{default:s(()=>[a(i,{modelValue:Q.value,"onUpdate:modelValue":e[9]||(e[9]=t=>Q.value=t),min:0,max:999999},null,8,["modelValue"])]),_:1})]),_:1}),o("div",Fe,[a(g,{type:"primary",onClick:ge},{default:s(()=>[...e[36]||(e[36]=[f("保存注册设置",-1)])]),_:1})])]),_:1})]),a(Z,{shadow:"never","body-style":{padding:"16px"},class:"card kdocs-card"},{default:s(()=>[o("div",he,[e[41]||(e[41]=o("h3",{class:"section-title"},"金山文档上传",-1)),o("div",ze,[e[40]||(e[40]=o("span",null,"登录状态:",-1)),o("span",{class:Ke(["status-chip",ce.value])},[f(te(W.value)+" ",1),se.value?(P(),I("span",He,[...e[39]||(e[39]=[o("i",null,null,-1),o("i",null,null,-1),o("i",null,null,-1)])])):ae("",!0)],2),o("span",null,"· 待上传 "+te(y.value.queue_size||0),1)])]),a(Y,{"label-width":"118px",class:"kdocs-form"},{default:s(()=>[a(u,{label:"启用上传"},{default:s(()=>[a(ee,{modelValue:T.value,"onUpdate:modelValue":e[10]||(e[10]=t=>T.value=t)},null,8,["modelValue"]),e[42]||(e[42]=o("div",{class:"help"},"表格结构变化时可先关闭,避免错误上传。",-1))]),_:1}),a(u,{label:"文档链接"},{default:s(()=>[a(V,{modelValue:q.value,"onUpdate:modelValue":e[11]||(e[11]=t=>q.value=t),placeholder:"https://kdocs.cn/..."},null,8,["modelValue"])]),_:1}),a(u,{label:"默认县区"},{default:s(()=>[a(V,{modelValue:B.value,"onUpdate:modelValue":e[12]||(e[12]=t=>B.value=t),placeholder:"如:道县(用户可覆盖)"},null,8,["modelValue"])]),_:1}),a(u,{label:"Sheet 名称"},{default:s(()=>[a(V,{modelValue:$.value,"onUpdate:modelValue":e[13]||(e[13]=t=>$.value=t),placeholder:"留空使用第一个 Sheet"},null,8,["modelValue"])]),_:1}),a(u,{label:"Sheet 序号"},{default:s(()=>[a(i,{modelValue:R.value,"onUpdate:modelValue":e[14]||(e[14]=t=>R.value=t),min:0,max:50},null,8,["modelValue"]),e[43]||(e[43]=o("div",{class:"help"},"0 表示第一个 Sheet。",-1))]),_:1}),a(u,{label:"列配置"},{default:s(()=>[o("div",Ge,[a(V,{modelValue:M.value,"onUpdate:modelValue":e[15]||(e[15]=t=>M.value=t),placeholder:"县区列,如 A"},null,8,["modelValue"]),a(V,{modelValue:F.value,"onUpdate:modelValue":e[16]||(e[16]=t=>F.value=t),placeholder:"图片列,如 D"},null,8,["modelValue"])])]),_:1}),a(u,{label:"有效行范围"},{default:s(()=>[o("div",Oe,[a(i,{modelValue:h.value,"onUpdate:modelValue":e[17]||(e[17]=t=>h.value=t),min:0,max:1e4,placeholder:"起始行",style:{width:"140px"}},null,8,["modelValue"]),e[44]||(e[44]=o("span",{class:"app-muted"},"至",-1)),a(i,{modelValue:z.value,"onUpdate:modelValue":e[18]||(e[18]=t=>z.value=t),min:0,max:1e4,placeholder:"结束行",style:{width:"140px"}},null,8,["modelValue"])]),e[45]||(e[45]=o("div",{class:"help"},"用于限制上传区间(如 50-1000 表示不限制。",-1))]),_:1}),a(u,{label:"管理员通知"},{default:s(()=>[a(ee,{modelValue:H.value,"onUpdate:modelValue":e[19]||(e[19]=t=>H.value=t)},null,8,["modelValue"])]),_:1}),a(u,{label:"通知邮箱"},{default:s(()=>[a(V,{modelValue:G.value,"onUpdate:modelValue":e[20]||(e[20]=t=>G.value=t),placeholder:"admin@example.com"},null,8,["modelValue"])]),_:1})]),_:1}),o("div",je,[a(g,{type:"primary",onClick:Ve},{default:s(()=>[...e[46]||(e[46]=[f("保存表格配置",-1)])]),_:1}),a(g,{type:"success",plain:"",loading:w.value,disabled:de.value&&!w.value,onClick:be},{default:s(()=>[...e[47]||(e[47]=[f(" 获取二维码 ",-1)])]),_:1},8,["loading","disabled"]),a(g,{type:"danger",plain:"",loading:U.value,disabled:de.value&&!U.value,onClick:xe},{default:s(()=>[...e[48]||(e[48]=[f(" 清除登录 ",-1)])]),_:1},8,["loading","disabled"])]),y.value.last_error?(P(),I("div",Je,"最近错误:"+te(y.value.last_error),1)):ae("",!0),j.value?(P(),I("div",We,"操作提示:"+te(j.value),1)):ae("",!0)]),_:1}),a(we,{modelValue:k.value,"onUpdate:modelValue":e[21]||(e[21]=t=>k.value=t),title:"扫码登录",width:"min(420px, 92vw)"},{default:s(()=>[o("div",Xe,[b.value?(P(),I("img",{key:0,src:`data:image/png;base64,${b.value}`,alt:"KDocs QR"},null,8,Ye)):ae("",!0),e[49]||(e[49]=o("div",{class:"help"},"请使用管理员微信扫码登录。",-1))])]),_:1},8,["modelValue"])])),[[Ue,c.value]])}}},nl=Se(Ze,[["__scopeId","data-v-cef111cd"]]);export{nl as default};