Files
claude-relay-service/assets/MainLayout-CNiZbAPe.js
2026-01-23 11:17:02 +00:00

2 lines
15 KiB
JavaScript

import{c as U,r as y,_ as W,q as X,V as Y,x as d,y as u,z as t,L as S,R as k,J as L,P as b,C as I,Y as V,O as _,T as G,K as M,aq as A,aW as Z,Q as q,aU as O,ac as K,o as ee,av as te,aX as se,D as ae}from"./vue-vendor-DV7DYXbz.js";import{_ as re,u as j,l as ne,s as C,m as oe}from"./index-p8cKYBY8.js";import{L as le}from"./LogoTitle-D3uO3Ady.js";import{T as ie}from"./ThemeToggle-CDMqn7Rp.js";import{C as de}from"./ConfirmModal-DjOnjOKk.js";import"./element-plus-BSjV1f9S.js";import"./vendor-Dr8jvgFu.js";const ue={class:"glass-strong mb-4 rounded-xl p-3 shadow-xl sm:mb-6 sm:rounded-2xl sm:p-4 md:mb-8 md:rounded-3xl md:p-6",style:{"z-index":"10",position:"relative"}},ce={class:"flex flex-col items-center justify-between gap-3 sm:flex-row sm:gap-4"},me={class:"flex w-full items-center justify-center gap-2 sm:w-auto sm:justify-start sm:gap-3 md:gap-4"},ge={class:"flex items-center gap-1 sm:gap-2"},pe={class:"font-mono text-xs text-gray-400 dark:text-gray-500 sm:text-sm"},fe=["href"],xe={class:"flex items-center gap-2 sm:gap-4"},ve={class:"flex items-center"},ye={class:"user-menu-container relative"},be={class:"hidden sm:inline"},he={class:"border-b border-gray-100 px-4 py-3 dark:border-gray-700"},ke={class:"flex items-center justify-between text-sm"},we={class:"font-mono text-gray-700 dark:text-gray-300"},_e={key:0,class:"mt-2"},Ce={class:"mb-2 flex items-center justify-between text-sm"},Ue={class:"font-mono text-green-600 dark:text-green-400"},Pe=["href"],Te={key:1,class:"mt-2 text-center text-xs text-gray-500 dark:text-gray-400"},Me={key:2,class:"mt-2 text-center"},Ie={key:"message",class:"inline-block rounded-lg border border-green-200 bg-green-100 px-3 py-1.5 dark:border-green-800 dark:bg-green-900/30"},$e={key:0,class:"modal fixed inset-0 z-50 flex items-center justify-center p-3 sm:p-4"},Ne={class:"modal-content mx-auto flex max-h-[90vh] w-full max-w-md flex-col p-4 sm:p-6 md:p-8"},Se=["value"],Ae={class:"relative"},qe=["type"],je={class:"flex gap-3 pt-4"},De=["disabled"],Le={key:0,class:"loading-spinner mr-2"},Ve={key:1,class:"fas fa-save mr-2"},Ke={__name:"AppHeader",setup(P){const p=O(),f=j(),g=U(()=>f.user||{username:"Admin"}),i=U(()=>f.oemSettings||{}),r=U(()=>f.oemLoading),s=y({current:"...",latest:"",hasUpdate:!1,checkingUpdate:!1,lastChecked:null,releaseInfo:null,noUpdateMessage:!1}),x=y(!1),c=y(!1),o=y(!1),l=y(!1),a=W({currentPassword:"",newPassword:"",confirmPassword:"",newUsername:""}),T=y(!1),w=y({title:"",message:"",type:"primary",confirmText:"确认",cancelText:"取消"}),h=y(null),z=(n,e,v="确认",m="取消",H="primary")=>new Promise(R=>{w.value={title:n,message:e,confirmText:v,cancelText:m,type:H},h.value=R,T.value=!0}),E=()=>{var n;T.value=!1,(n=h.value)==null||n.call(h,!0)},B=()=>{var n;T.value=!1,(n=h.value)==null||n.call(h,!1)},$=async()=>{if(!s.value.checkingUpdate){s.value.checkingUpdate=!0;try{const n=await ne();if(n.success){const e=n.data;s.value.current=e.current,s.value.latest=e.latest,s.value.hasUpdate=e.hasUpdate,s.value.releaseInfo=e.releaseInfo,s.value.lastChecked=new Date,localStorage.setItem("versionInfo",JSON.stringify({current:e.current,latest:e.latest,lastChecked:s.value.lastChecked,hasUpdate:e.hasUpdate,releaseInfo:e.releaseInfo})),e.hasUpdate||(s.value.noUpdateMessage=!0,setTimeout(()=>{s.value.noUpdateMessage=!1},3e3))}}catch(n){console.error("Error checking for updates:",n);const e=localStorage.getItem("versionInfo");if(e){const v=JSON.parse(e);s.value.current=v.current||s.value.current,s.value.latest=v.latest,s.value.hasUpdate=v.hasUpdate,s.value.releaseInfo=v.releaseInfo,s.value.lastChecked=new Date(v.lastChecked)}}finally{s.value.checkingUpdate=!1}}},F=()=>{a.currentPassword="",a.newPassword="",a.confirmPassword="",a.newUsername="",c.value=!0,x.value=!1},N=()=>{c.value=!1},J=async()=>{if(a.newPassword!==a.confirmPassword){C("两次输入的密码不一致","error");return}if(a.newPassword.length<8){C("新密码长度至少8位","error");return}o.value=!0;try{const n=await oe({currentPassword:a.currentPassword,newPassword:a.newPassword,newUsername:a.newUsername||void 0});if(n.success){const e=a.newUsername?"账户信息修改成功,请重新登录":"密码修改成功,请重新登录";C(e,"success"),N(),setTimeout(()=>{f.logout(),p.push("/login")},1500)}else C(n.message||"修改失败","error")}catch{C("修改密码失败","error")}finally{o.value=!1}},Q=async()=>{await z("退出登录","确定要退出登录吗?","确定退出","取消","warning")&&(f.logout(),p.push("/login"),C("已安全退出","success")),x.value=!1},D=n=>{!n.target.closest(".user-menu-container")&&x.value&&(x.value=!1)};return X(()=>{$(),setInterval(()=>{$()},36e5),document.addEventListener("click",D)}),Y(()=>{document.removeEventListener("click",D)}),(n,e)=>{var v;return u(),d(q,null,[t("div",ue,[t("div",ce,[t("div",me,[k(le,{loading:r.value,"logo-src":i.value.siteIconData||i.value.siteIcon,subtitle:"管理后台",title:i.value.siteName,"title-class":"text-white dark:text-gray-100"},{"after-title":L(()=>{var m;return[t("div",ge,[t("span",pe,"v"+b(s.value.current||"..."),1),s.value.hasUpdate?(u(),d("a",{key:0,class:"inline-flex animate-pulse items-center gap-1 rounded-full border border-green-600 bg-green-500 px-2 py-0.5 text-xs text-white transition-colors hover:bg-green-600",href:((m=s.value.releaseInfo)==null?void 0:m.htmlUrl)||"#",target:"_blank",title:"有新版本可用"},e[8]||(e[8]=[t("i",{class:"fas fa-arrow-up text-[10px]"},null,-1),t("span",null,"新版本",-1)]),8,fe)):S("",!0)])]}),_:1},8,["loading","logo-src","title"])]),t("div",xe,[t("div",ve,[k(ie,{mode:"dropdown"})]),e[19]||(e[19]=t("div",{class:"h-8 w-px bg-gradient-to-b from-transparent via-gray-300 to-transparent opacity-50 dark:via-gray-600"},null,-1)),t("div",ye,[t("button",{class:"user-menu-button flex items-center gap-2 rounded-2xl px-3 py-2 text-sm font-semibold text-white shadow-lg transition-all duration-200 hover:scale-105 hover:shadow-xl active:scale-95 sm:px-4 sm:py-2.5",onClick:e[0]||(e[0]=m=>x.value=!x.value)},[e[9]||(e[9]=t("i",{class:"fas fa-user-circle text-sm sm:text-base"},null,-1)),t("span",be,b(g.value.username||"Admin"),1),t("i",{class:I(["fas fa-chevron-down ml-1 text-xs transition-transform duration-200",{"rotate-180":x.value}])},null,2)]),x.value?(u(),d("div",{key:0,class:"user-menu-dropdown absolute right-0 top-full mt-2 w-48 rounded-xl border border-gray-200 bg-white py-2 shadow-xl dark:border-gray-700 dark:bg-gray-800 sm:w-56",style:{"z-index":"999999"},onClick:e[2]||(e[2]=V(()=>{},["stop"]))},[t("div",he,[t("div",ke,[e[10]||(e[10]=t("span",{class:"text-gray-500 dark:text-gray-400"},"当前版本",-1)),t("span",we,"v"+b(s.value.current||"..."),1)]),s.value.hasUpdate?(u(),d("div",_e,[t("div",Ce,[e[11]||(e[11]=t("span",{class:"font-medium text-green-600 dark:text-green-400"},[t("i",{class:"fas fa-arrow-up mr-1"}),_("有新版本 ")],-1)),t("span",Ue,"v"+b(s.value.latest),1)]),t("a",{class:"block w-full rounded-lg bg-green-500 px-3 py-1.5 text-center text-sm text-white transition-colors hover:bg-green-600",href:((v=s.value.releaseInfo)==null?void 0:v.htmlUrl)||"#",target:"_blank"},e[12]||(e[12]=[t("i",{class:"fas fa-external-link-alt mr-1"},null,-1),_("查看更新 ",-1)]),8,Pe)])):s.value.checkingUpdate?(u(),d("div",Te,e[13]||(e[13]=[t("i",{class:"fas fa-spinner fa-spin mr-1"},null,-1),_("检查更新中... ",-1)]))):(u(),d("div",Me,[k(G,{mode:"out-in",name:"fade"},{default:L(()=>[s.value.noUpdateMessage?(u(),d("div",Ie,e[14]||(e[14]=[t("p",{class:"text-xs font-medium text-green-700 dark:text-green-400"},[t("i",{class:"fas fa-check-circle mr-1"}),_("当前已是最新版本 ")],-1)]))):(u(),d("button",{key:"button",class:"text-xs text-blue-500 transition-colors hover:text-blue-700 dark:text-blue-400 dark:hover:text-blue-300",onClick:e[1]||(e[1]=m=>$())},e[15]||(e[15]=[t("i",{class:"fas fa-sync-alt mr-1"},null,-1),_("检查更新 ",-1)])))]),_:1})]))]),t("button",{class:"flex w-full items-center gap-3 px-4 py-3 text-left text-gray-700 transition-colors hover:bg-gray-50 dark:text-gray-300 dark:hover:bg-gray-700",onClick:F},e[16]||(e[16]=[t("i",{class:"fas fa-key text-blue-500"},null,-1),t("span",null,"修改账户信息",-1)])),e[18]||(e[18]=t("hr",{class:"my-2 border-gray-200 dark:border-gray-700"},null,-1)),t("button",{class:"flex w-full items-center gap-3 px-4 py-3 text-left text-gray-700 transition-colors hover:bg-gray-50 dark:text-gray-300 dark:hover:bg-gray-700",onClick:Q},e[17]||(e[17]=[t("i",{class:"fas fa-sign-out-alt text-red-500"},null,-1),t("span",null,"退出登录",-1)]))])):S("",!0)])])])]),c.value?(u(),d("div",$e,[t("div",Ne,[t("div",{class:"mb-6 flex items-center justify-between"},[e[21]||(e[21]=t("div",{class:"flex items-center gap-3"},[t("div",{class:"flex h-10 w-10 items-center justify-center rounded-xl bg-gradient-to-br from-blue-500 to-blue-600"},[t("i",{class:"fas fa-key text-white"})]),t("h3",{class:"text-xl font-bold text-gray-900 dark:text-gray-100"},"修改账户信息")],-1)),t("button",{class:"text-gray-400 transition-colors hover:text-gray-600 dark:hover:text-gray-300",onClick:N},e[20]||(e[20]=[t("i",{class:"fas fa-times text-xl"},null,-1)]))]),t("form",{class:"modal-scroll-content custom-scrollbar flex-1 space-y-6",onSubmit:V(J,["prevent"])},[t("div",null,[e[22]||(e[22]=t("label",{class:"mb-3 block text-sm font-semibold text-gray-700 dark:text-gray-300"},"当前用户名",-1)),t("input",{class:"form-input w-full cursor-not-allowed bg-gray-100 dark:bg-gray-700 dark:text-gray-300",disabled:"",type:"text",value:g.value.username||"Admin"},null,8,Se),e[23]||(e[23]=t("p",{class:"mt-2 text-xs text-gray-500 dark:text-gray-400"}," 当前用户名,输入新用户名以修改 ",-1))]),t("div",null,[e[24]||(e[24]=t("label",{class:"mb-3 block text-sm font-semibold text-gray-700 dark:text-gray-300"},"新用户名",-1)),M(t("input",{"onUpdate:modelValue":e[3]||(e[3]=m=>a.newUsername=m),class:"form-input w-full",placeholder:"输入新用户名(留空保持不变)",type:"text"},null,512),[[A,a.newUsername]]),e[25]||(e[25]=t("p",{class:"mt-2 text-xs text-gray-500 dark:text-gray-400"},"留空表示不修改用户名",-1))]),t("div",null,[e[26]||(e[26]=t("label",{class:"mb-3 block text-sm font-semibold text-gray-700 dark:text-gray-300"},"当前密码",-1)),t("div",Ae,[M(t("input",{"onUpdate:modelValue":e[4]||(e[4]=m=>a.currentPassword=m),class:"form-input w-full pr-10",placeholder:"请输入当前密码",required:"",type:l.value?"text":"password"},null,8,qe),[[Z,a.currentPassword]]),t("button",{class:"absolute right-3 top-1/2 -translate-y-1/2 text-gray-400 hover:text-gray-600 dark:text-gray-500 dark:hover:text-gray-300",type:"button",onClick:e[5]||(e[5]=m=>l.value=!l.value)},[t("i",{class:I(l.value?"fas fa-eye-slash":"fas fa-eye")},null,2)])])]),t("div",null,[e[27]||(e[27]=t("label",{class:"mb-3 block text-sm font-semibold text-gray-700 dark:text-gray-300"},"新密码",-1)),M(t("input",{"onUpdate:modelValue":e[6]||(e[6]=m=>a.newPassword=m),class:"form-input w-full",placeholder:"请输入新密码",required:"",type:"password"},null,512),[[A,a.newPassword]]),e[28]||(e[28]=t("p",{class:"mt-2 text-xs text-gray-500 dark:text-gray-400"},"密码长度至少8位",-1))]),t("div",null,[e[29]||(e[29]=t("label",{class:"mb-3 block text-sm font-semibold text-gray-700 dark:text-gray-300"},"确认新密码",-1)),M(t("input",{"onUpdate:modelValue":e[7]||(e[7]=m=>a.confirmPassword=m),class:"form-input w-full",placeholder:"请再次输入新密码",required:"",type:"password"},null,512),[[A,a.confirmPassword]])]),t("div",je,[t("button",{class:"flex-1 rounded-xl bg-gray-100 px-6 py-3 font-semibold text-gray-700 transition-colors hover:bg-gray-200 dark:bg-gray-700 dark:text-gray-300 dark:hover:bg-gray-600",type:"button",onClick:N}," 取消 "),t("button",{class:"btn btn-primary flex-1 px-6 py-3 font-semibold",disabled:o.value,type:"submit"},[o.value?(u(),d("div",Le)):(u(),d("i",Ve)),_(" "+b(o.value?"保存中...":"保存修改"),1)],8,De)])],32)])])):S("",!0),k(de,{"cancel-text":w.value.cancelText,"confirm-text":w.value.confirmText,message:w.value.message,show:T.value,title:w.value.title,type:w.value.type,onCancel:B,onConfirm:E},null,8,["cancel-text","confirm-text","message","show","title","type"])],64)}}},Oe=re(Ke,[["__scopeId","data-v-2abe1d62"]]),ze={class:"mb-4 sm:mb-6"},Ee={class:"block rounded-xl bg-white/10 p-2 backdrop-blur-sm dark:bg-gray-800/20 sm:hidden"},Be=["value"],Fe=["value"],Je={class:"hidden flex-wrap gap-2 rounded-2xl bg-white/10 p-2 backdrop-blur-sm dark:bg-gray-800/20 sm:flex"},Qe=["onClick"],He={class:"hidden md:inline"},Re={class:"md:hidden"},We={__name:"TabBar",props:{activeTab:{type:String,required:!0}},emits:["tab-change"],setup(P){const p=j(),f=U(()=>{var i;const g=[{key:"dashboard",name:"仪表板",shortName:"仪表板",icon:"fas fa-tachometer-alt"},{key:"apiKeys",name:"API Keys",shortName:"API",icon:"fas fa-key"},{key:"accounts",name:"账户管理",shortName:"账户",icon:"fas fa-user-circle"},{key:"quotaCards",name:"额度卡",shortName:"额度卡",icon:"fas fa-ticket-alt"}];return(i=p.oemSettings)!=null&&i.ldapEnabled&&g.push({key:"userManagement",name:"用户管理",shortName:"用户",icon:"fas fa-users"}),g.push({key:"settings",name:"系统设置",shortName:"设置",icon:"fas fa-cogs"}),g});return(g,i)=>(u(),d("div",ze,[t("div",Ee,[t("select",{class:"focus:ring-primary-color w-full rounded-lg bg-white/90 px-4 py-3 font-semibold text-gray-700 focus:outline-none focus:ring-2 dark:bg-gray-800/90 dark:text-gray-200 dark:focus:ring-indigo-400",value:P.activeTab,onChange:i[0]||(i[0]=r=>g.$emit("tab-change",r.target.value))},[(u(!0),d(q,null,K(f.value,r=>(u(),d("option",{key:r.key,value:r.key},b(r.name),9,Fe))),128))],40,Be)]),t("div",Je,[(u(!0),d(q,null,K(f.value,r=>(u(),d("button",{key:r.key,class:I(["tab-btn flex-1 px-3 py-2 text-xs font-semibold transition-all duration-300 sm:px-4 sm:py-3 sm:text-sm md:px-6",P.activeTab===r.key?"active":"text-gray-700 hover:bg-white/10 hover:text-gray-900 dark:text-gray-300 dark:hover:bg-gray-700/30 dark:hover:text-gray-100"]),onClick:s=>g.$emit("tab-change",r.key)},[t("i",{class:I(r.icon+" mr-1 sm:mr-2")},null,2),t("span",He,b(r.name),1),t("span",Re,b(r.shortName||r.name),1)],10,Qe))),128))])]))}},Xe={class:"min-h-screen p-3 sm:p-4 md:p-6"},Ye={class:"glass-strong rounded-xl p-3 shadow-xl sm:rounded-2xl sm:p-4 md:rounded-3xl md:p-6",style:{"z-index":"1","min-height":"calc(100vh - 120px)"}},Ge={class:"tab-content"},ot={__name:"MainLayout",setup(P){const p=se(),f=O(),g=j(),i=y("dashboard"),r=U(()=>{var o;const c={dashboard:"/dashboard",apiKeys:"/api-keys",accounts:"/accounts",quotaCards:"/quota-cards",settings:"/settings"};return(o=g.oemSettings)!=null&&o.ldapEnabled&&(c.userManagement="/user-management"),c}),s=()=>{const c=p.path,o=Object.keys(r.value).find(l=>r.value[l]===c);if(o)i.value=o;else{const l=p.name,a={Dashboard:"dashboard",ApiKeys:"apiKeys",Accounts:"accounts",QuotaCards:"quotaCards",Settings:"settings"};l&&a[l]?i.value=a[l]:i.value="dashboard"}};s(),ee(()=>p.path,c=>{const o=Object.keys(r.value).find(l=>r.value[l]===c);if(o)i.value=o;else{const l=p.name,a={Dashboard:"dashboard",ApiKeys:"apiKeys",Accounts:"accounts",QuotaCards:"quotaCards",Tutorial:"tutorial",Settings:"settings"};l&&a[l]&&(i.value=a[l])}});const x=async c=>{if(r.value[c]!==p.path){i.value=c;try{await f.push(r.value[c]),await ae()}catch(o){o.name!=="NavigationDuplicated"&&(console.error("路由切换失败:",o),s())}}};return(c,o)=>{const l=te("router-view");return u(),d("div",Xe,[k(Oe),t("div",Ye,[k(We,{"active-tab":i.value,onTabChange:x},null,8,["active-tab"]),t("div",Ge,[k(l)])])])}}};export{ot as default};