astrion-website/demo/static/dist/assets/admin.js

2 lines
24 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{d as aa,l as r,w as Ne,o as sa,a as na,m as l,c as o,f as a,t as s,u as x,b as ta,e as h,g as V,v as Ue,h as Re,F as m,r as b,n as U,s as la,x as oa,z as ra,i as ue,A as Ie,T as ia,j as u,k as c,p as da,q as ua}from"./index.js";import{S as ca,u as ha}from"./SecondaryGate.js";import{_ as va}from"./_plugin-vue_export-helper.js";const ma={key:0,class:"admin-loading"},ba={key:1,class:"admin-page"},pa={class:"admin-header"},fa={class:"header-actions"},ga=["disabled"],ka={class:"link-btn",href:"/admin/policy",target:"_blank",rel:"noopener"},Da={class:"link-btn",href:"/admin/api",target:"_blank",rel:"noopener"},ya={key:1,class:"banner-error"},wa={key:2,class:"admin-layout"},_a={class:"admin-sidebar"},$a=["onClick"],Sa={class:"admin-main"},Ca={key:"overview",class:"panel"},Ta={class:"metrics-grid"},Na={key:"usage",class:"panel"},Ua={class:"stats-row"},Ra={class:"token-summary"},Ia={class:"token-card"},Ma={class:"token-card"},Ea={class:"token-card"},Fa={class:"token-breakdown"},La={class:"token-breakdown-header"},Pa={key:0,class:"token-table-wrapper"},Ba={class:"token-table"},Aa={key:1,class:"token-empty"},ja={class:"usage-leaders"},Va={key:0,class:"muted"},Oa={key:"users",class:"panel"},qa={class:"table-wrapper"},za={key:0},Ja={colspan:"9"},Ka={class:"subtext"},Xa={class:"progress-bar"},Wa={key:"containers",class:"panel"},Ga={class:"table-wrapper"},Qa={key:0},Ha={colspan:"10"},Ya={key:"uploads",class:"panel"},Za={class:"stats-row"},xa={class:"stats-row"},es={key:0},as={class:"upload-feed"},ss={key:0,class:"upload-item"},ns={class:"upload-meta"},ts={class:"upload-meta"},ls={key:0,class:"status-badge danger"},os={key:"invites",class:"panel"},rs={class:"stats-row"},is={class:"invite-manage"},ds=["placeholder","disabled"],us=["placeholder","disabled"],cs={class:"invite-check"},hs=["disabled"],vs=["disabled"],ms={key:0,class:"secondary-error"},bs={class:"invite-grid"},ps={key:0,class:"invite-card"},fs={class:"invite-actions"},gs=["disabled","onClick"],ks=["disabled","onClick"],Ds={key:"passwords",class:"panel"},ys={class:"muted"},ws={class:"password-form"},_s={class:"password-field"},$s={key:0,class:"user-search-selected"},Ss={class:"user-search-email"},Cs={key:1,class:"user-search-placeholder"},Ts={key:0,class:"user-search-dropdown"},Ns=["placeholder"],Us={class:"user-search-list"},Rs=["onClick"],Is={class:"user-search-name"},Ms={class:"user-search-email"},Es={key:0,class:"user-search-role"},Fs={key:0,class:"user-search-empty"},Ls={class:"password-field"},Ps=["disabled","placeholder"],Bs={class:"password-actions"},As=["disabled"],js=["disabled"],Vs={key:0,class:"password-success"},Os={key:1,class:"password-error-msg"},qs={key:3,class:"admin-error"},zs=aa({__name:"AdminDashboardApp",setup(Ks){const{verified:R,configured:Ee,loading:Fe,error:Le,check:be,verify:Pe}=ha(),I=u(!0),ee=u(!1),$=u(null),ce=u(null),ae=u(null),se=u(!0),p=u("overview");let f;const v=u(!1),g=u(null),ne=u(""),te=u("1"),O=u(!1),k=u(""),M=u(""),E=u(!1),F=u(""),L=u(""),q=u(""),S=u(!1),he=u(null),pe=u(null),Be=[{id:"overview",label:r("adminDashboard.tabOverview")},{id:"usage",label:r("adminDashboard.tabUsage")},{id:"users",label:r("adminDashboard.tabUsers")},{id:"containers",label:r("adminDashboard.tabContainers")},{id:"uploads",label:r("adminDashboard.tabUploads")},{id:"invites",label:r("adminDashboard.tabInvites")},{id:"passwords",label:r("adminDashboard.passwordManagement")}],Ae=c(()=>I.value&&!$.value),D=async(e=!1)=>{if(!R.value){I.value=!1;return}e?ee.value=!0:$.value||(I.value=!0);try{const t=await fetch("/api/admin/dashboard",{credentials:"same-origin"});if(!t.ok)throw new Error(r("adminDashboard.requestFailed",{status:t.status}));const i=await t.json();if(!i.success)throw new Error(i.error||r("common.unknownError"));$.value=i.data,ce.value=null,ae.value=null}catch(t){const i=t instanceof Error?t.message:String(t);$.value?ae.value=i:ce.value=i}finally{e&&(ee.value=!1),$.value||(I.value=!1)}},le=()=>{f&&(clearInterval(f),f=void 0),se.value&&R.value&&(f=window.setInterval(()=>D(!0),3e4))},je=()=>D(!0),Ve=()=>D(!1),oe=async()=>{const e=await fetch("/api/csrf-token",{credentials:"same-origin"});if(!e.ok)throw new Error(r("adminDashboard.csrfFailed",{status:e.status}));const t=await e.json(),i=t==null?void 0:t.token;if(!i||typeof i!="string")throw new Error(r("adminDashboard.csrfNoToken"));return i},fe=e=>{const t=String(e??"").trim().toLowerCase();if(!t||t==="unlimited"||t==="null"||t==="none"||t==="不限"||t==="无限制")return null;const i=Number(t);if(!Number.isFinite(i)||i<0||!Number.isInteger(i))throw new Error(r("adminDashboard.remainingInvalid"));return i},Oe=async()=>{const e=ne.value.trim();if(!e){g.value=r("adminDashboard.inviteCodeRequired");return}v.value=!0,g.value=null;try{const t=O.value?null:fe(te.value),i=await oe(),n=await fetch("/api/admin/invites",{method:"POST",headers:{"Content-Type":"application/json","X-CSRF-Token":i},credentials:"same-origin",body:JSON.stringify({code:e,remaining:t})}),d=await n.json();if(!n.ok||!d.success)throw new Error(d.error||r("adminDashboard.requestFailed",{status:n.status}));ne.value="",te.value="1",O.value=!1,await D(!0)}catch(t){g.value=t instanceof Error?t.message:String(t)}finally{v.value=!1}},ge=async()=>{const e=k.value.trim(),t=M.value.trim();if(!(!e||!t)){if(t.length<8){L.value=r("adminDashboard.passwordTooShort"),F.value="";return}E.value=!0,F.value="",L.value="";try{const i=await oe(),n=await fetch(`/api/admin/users/${encodeURIComponent(e)}/reset-password`,{method:"POST",headers:{"Content-Type":"application/json","X-CSRF-Token":i},credentials:"same-origin",body:JSON.stringify({password:t})}),d=await n.json();if(!n.ok||!d.success)throw new Error(d.error||r("adminDashboard.requestFailed",{status:n.status}));F.value=r("adminDashboard.passwordResetSuccess",{username:e}),M.value=""}catch(i){L.value=i instanceof Error?i.message:String(i)}finally{E.value=!1}}},ke=c(()=>{const e=q.value.trim().toLowerCase();return e?A.value.filter(t=>t.username.toLowerCase().includes(e)||(t.email||"").toLowerCase().includes(e)):A.value}),qe=c(()=>{const e=A.value.find(t=>t.username===k.value);return(e==null?void 0:e.email)||""}),ze=()=>{S.value=!S.value,S.value&&(q.value="",setTimeout(()=>{var e;(e=pe.value)==null||e.focus()},50))},Je=e=>{k.value=e.username,q.value="",S.value=!1},De=e=>{he.value&&!he.value.contains(e.target)&&(S.value=!1)},Ke=async e=>{const t=e==null?void 0:e.remaining,i=t===null||typeof t>"u"?"unlimited":String(t),n=window.prompt(r("adminDashboard.promptRemaining"),i);if(n!==null){v.value=!0,g.value=null;try{const d=fe(n),w=await oe(),_=await fetch("/api/admin/invites",{method:"PUT",headers:{"Content-Type":"application/json","X-CSRF-Token":w},credentials:"same-origin",body:JSON.stringify({code:e==null?void 0:e.code,remaining:d})}),N=await _.json();if(!_.ok||!N.success)throw new Error(N.error||r("adminDashboard.requestFailed",{status:_.status}));await D(!0)}catch(d){g.value=d instanceof Error?d.message:String(d)}finally{v.value=!1}}},Xe=async e=>{if(e&&window.confirm(r("adminDashboard.deleteInviteConfirm",{code:e}))){v.value=!0,g.value=null;try{const t=await oe(),i=await fetch("/api/admin/invites",{method:"DELETE",headers:{"Content-Type":"application/json","X-CSRF-Token":t},credentials:"same-origin",body:JSON.stringify({code:e})}),n=await i.json();if(!i.ok||!n.success)throw new Error(n.error||r("adminDashboard.requestFailed",{status:i.status}));await D(!0)}catch(t){g.value=t instanceof Error?t.message:String(t)}finally{v.value=!1}}},We=async e=>{await Pe(e),R.value&&(D(!1),le())};Ne(se,()=>{le()}),sa(async()=>{document.addEventListener("click",De),await be(),R.value?(D(!1),le()):I.value=!1}),Ne(R,e=>{e?(D(!1),le()):f&&(clearInterval(f),f=void 0,I.value=!1)}),na(()=>{document.removeEventListener("click",De),f&&clearInterval(f)});const C=c(()=>$.value||null),T=c(()=>{var e;return((e=C.value)==null?void 0:e.overview)??{}}),P=c(()=>T.value.usage_totals??{}),ve=c(()=>T.value.token_totals??{}),Ge=c(()=>{const e=T.value.usage_leaders??{};return[{key:"fast",label:r("adminDashboard.leaderFast"),items:e.fast||[]},{key:"thinking",label:r("adminDashboard.leaderThinking"),items:e.thinking||[]},{key:"search",label:r("adminDashboard.leaderSearch"),items:e.search||[]}]}),re=c(()=>T.value.storage??{}),B=c(()=>{var e,t;return((t=(e=C.value)==null?void 0:e.uploads)==null?void 0:t.stats)??{}}),ye=c(()=>{var e,t;return((t=(e=C.value)==null?void 0:e.uploads)==null?void 0:t.sources)??[]}),we=c(()=>{var e,t;return((t=(e=C.value)==null?void 0:e.uploads)==null?void 0:t.recent_events)??[]}),A=c(()=>{var e;return((e=C.value)==null?void 0:e.users)??[]}),_e=c(()=>{var e;return((e=C.value)==null?void 0:e.containers)??[]}),ie=c(()=>{var e,t;return((t=(e=C.value)==null?void 0:e.invites)==null?void 0:t.summary)??{}}),$e=c(()=>{var e,t;return((t=(e=C.value)==null?void 0:e.invites)==null?void 0:t.codes)??[]}),Se=c(()=>T.value.totals??{}),z=c(()=>T.value.containers??{}),me=c(()=>T.value.invites??{}),Ce=c(()=>A.value.map(t=>{var i,n,d;return{username:t.username,role:t.role||"user",input:Number(((i=t.tokens)==null?void 0:i.input_tokens)||0),output:Number(((n=t.tokens)==null?void 0:n.output_tokens)||0),total:Number(((d=t.tokens)==null?void 0:d.total_tokens)||0)}}).sort((t,i)=>i.total-t.total)),Qe=c(()=>[{title:r("adminDashboard.metricRegisteredUsers"),value:Se.value.users||0,sub:r("adminDashboard.metricActiveUsers",{count:Se.value.active_users||0})},{title:r("adminDashboard.metricContainerUsage"),value:`${z.value.active||0}/${z.value.max_containers??"∞"}`,sub:z.value.available_slots===null||z.value.available_slots===void 0?r("adminDashboard.unlimited"):r("adminDashboard.freeSlots",{count:z.value.available_slots})},{title:r("adminDashboard.metricStorageWarnings"),value:(re.value.warning_users||[]).length,sub:r("adminDashboard.storageWarningSub")},{title:r("adminDashboard.metricUploadAudit"),value:B.value.last_24h||0,sub:r("adminDashboard.blockedCount",{count:B.value.blocked_last_24h||0})},{title:r("adminDashboard.metricQuotaCalls"),value:`${P.value.fast||0} / ${P.value.thinking||0} / ${P.value.search||0}`,sub:r("adminDashboard.windowCalls")},{title:r("adminDashboard.metricInvites"),value:me.value.total||0,sub:r("adminDashboard.inviteMetricsSub",{active:me.value.active||0,consumed:me.value.consumed||0})},{title:r("adminDashboard.metricStorage"),value:y(re.value.total_bytes||0),sub:re.value.per_user_limit_bytes?r("adminDashboard.perUserLimit",{size:y(re.value.per_user_limit_bytes)}):r("adminDashboard.noLimitSet")}]),y=e=>{if(e==null||Number(e)<=0)return"0 B";const t=["B","KB","MB","GB","TB"];let i=Number(e);const n=Math.min(Math.floor(Math.log(i)/Math.log(1024)),t.length-1);i/=1024**n;const d=i>=100?0:1;return`${i.toFixed(d)} ${t[n]}`},He=e=>e==null?"0%":`${Math.min(100,Math.max(0,Number(e)))}%`,Ye=e=>e==null||isNaN(Number(e))?"—":`${Number(e).toFixed(1)}%`,j=e=>{if(e==null)return"0";const t=Number(e);return Number.isNaN(t)?"0":t.toLocaleString()},Te=e=>e==null||isNaN(Number(e))?"—":`${Number(e).toFixed(1)}%`,de=e=>{if(!e)return r("adminDashboard.unknownTime");const t=new Date(e);if(Number.isNaN(t.getTime()))return String(e);const i=Date.now()-t.getTime();if(i<6e4)return r("adminDashboard.justNow");const n=Math.floor(i/6e4);if(n<60)return r("adminDashboard.minutesAgo",{count:n});const d=Math.floor(n/60);if(d<24)return r("adminDashboard.hoursAgo",{count:d});const w=Math.floor(d/24);return r("adminDashboard.daysAgo",{count:w})},Ze=e=>e==="critical"?"danger":e==="warning"?"warning":"online",xe=e=>e!=null&&e.error?"danger":e!=null&&e.state&&e.state.running===!1?"warning":"online",ea=e=>e==null?r("adminDashboard.unlimited"):e>0?r("adminDashboard.remainingLeft",{count:e}):r("adminDashboard.usedUp");return(e,t)=>{var i;return Ae.value?(l(),o("div",ma,[t[8]||(t[8]=a("div",{class:"spinner"},null,-1)),a("p",null,s(e.$t("adminDashboard.loadingMonitor")),1)])):(l(),o("div",ba,[x(R)?h("",!0):(l(),ta(ca,{key:0,configured:x(Ee),loading:x(Fe),error:x(Le),description:e.$t("adminDashboard.gateDescription"),onVerify:We,onRecheck:x(be)},null,8,["configured","loading","error","description","onRecheck"])),a("header",pa,[a("div",null,[a("h1",null,s(e.$t("adminDashboard.title")),1),a("p",null,s(e.$t("adminDashboard.lastUpdated",{time:de(((i=$.value)==null?void 0:i.generated_at)||T.value.generated_at)})),1)]),a("div",fa,[a("label",null,[V(a("input",{type:"checkbox","onUpdate:modelValue":t[0]||(t[0]=n=>se.value=n)},null,512),[[Ue,se.value]]),Re(" "+s(e.$t("adminDashboard.autoRefresh")),1)]),a("button",{type:"button",disabled:ee.value,onClick:je},s(ee.value?e.$t("common.refreshing"):e.$t("adminDashboard.refreshNow")),9,ga),a("a",ka,s(e.$t("adminDashboard.policyConfig")),1),a("a",Da,s(e.$t("adminDashboard.apiAdmin")),1)])]),ae.value?(l(),o("section",ya,[a("strong",null,s(e.$t("adminDashboard.refreshFailed")),1),a("span",null,s(ae.value),1)])):h("",!0),$.value?(l(),o("div",wa,[a("aside",_a,[(l(),o(m,null,b(Be,n=>a("button",{key:n.id,type:"button",class:U(["sidebar-tab",{active:p.value===n.id}]),onClick:d=>p.value=n.id},s(n.label),11,$a)),64))]),a("main",Sa,[la(ia,{name:"fade",mode:"out-in"},{default:oa(()=>[p.value==="overview"?(l(),o("section",Ca,[a("div",Ta,[(l(!0),o(m,null,b(Qe.value,n=>(l(),o("div",{key:n.title,class:"metric-card"},[a("h3",null,s(n.title),1),a("strong",null,s(n.value),1),a("span",null,s(n.sub),1)]))),128))])])):p.value==="usage"?(l(),o("section",Na,[a("h2",null,s(e.$t("adminDashboard.usageTitle")),1),a("div",Ua,[a("span",null,s(e.$t("adminDashboard.fastMode",{count:P.value.fast||0})),1),a("span",null,s(e.$t("adminDashboard.thinkingMode",{count:P.value.thinking||0})),1),a("span",null,s(e.$t("adminDashboard.searchMode",{count:P.value.search||0})),1)]),a("div",Ra,[a("div",Ia,[a("p",null,s(e.$t("adminDashboard.totalInputTokens")),1),a("strong",null,s(j(ve.value.input_tokens)),1)]),a("div",Ma,[a("p",null,s(e.$t("adminDashboard.totalOutputTokens")),1),a("strong",null,s(j(ve.value.output_tokens)),1)]),a("div",Ea,[a("p",null,s(e.$t("adminDashboard.totalTokens")),1),a("strong",null,s(j(ve.value.total_tokens)),1)])]),a("div",Fa,[a("div",La,[a("h3",null,s(e.$t("adminDashboard.tokenBreakdownTitle")),1),a("span",null,s(e.$t("adminDashboard.tokenBreakdownSub")),1)]),Ce.value.length?(l(),o("div",Pa,[a("table",Ba,[a("thead",null,[a("tr",null,[a("th",null,s(e.$t("adminDashboard.tableUser")),1),a("th",null,s(e.$t("adminDashboard.tableRole")),1),a("th",null,s(e.$t("adminDashboard.tableInputTokens")),1),a("th",null,s(e.$t("adminDashboard.tableOutputTokens")),1),a("th",null,s(e.$t("adminDashboard.tableTotalTokens")),1)])]),a("tbody",null,[(l(!0),o(m,null,b(Ce.value,n=>(l(),o("tr",{key:n.username},[a("td",null,s(n.username),1),a("td",null,s(n.role),1),a("td",null,s(j(n.input)),1),a("td",null,s(j(n.output)),1),a("td",null,[a("strong",null,s(j(n.total)),1)])]))),128))])])])):(l(),o("p",Aa,s(e.$t("adminDashboard.noTokenStats")),1))]),a("div",ja,[(l(!0),o(m,null,b(Ge.value,n=>(l(),o("div",{key:n.key,class:"leader-card"},[a("h3",null,s(n.label),1),a("ul",null,[n.items.length?h("",!0):(l(),o("li",Va,s(e.$t("common.noData")),1)),(l(!0),o(m,null,b(n.items,d=>(l(),o("li",{key:d.username},[a("strong",null,s(d.username),1),a("span",null,s(d.count)+" / "+s(d.limit??"∞"),1)]))),128))])]))),128))])])):p.value==="users"?(l(),o("section",Oa,[a("h2",null,s(e.$t("adminDashboard.usersTitle")),1),a("div",qa,[a("table",null,[a("thead",null,[a("tr",null,[a("th",null,s(e.$t("adminDashboard.tableUser")),1),a("th",null,s(e.$t("adminDashboard.tableRole")),1),a("th",null,s(e.$t("adminDashboard.tableStatus")),1),a("th",null,s(e.$t("adminDashboard.tableProjectUsage")),1),t[9]||(t[9]=a("th",null,"Fast",-1)),t[10]||(t[10]=a("th",null,"Thinking",-1)),t[11]||(t[11]=a("th",null,"Search",-1)),a("th",null,s(e.$t("adminDashboard.tableProjectSize")),1),a("th",null,s(e.$t("adminDashboard.tableLastActive")),1)])]),a("tbody",null,[A.value.length?h("",!0):(l(),o("tr",za,[a("td",Ja,s(e.$t("adminDashboard.emptyUsers")),1)])),(l(!0),o(m,null,b(A.value,n=>{var d,w,_,N,J,K,X,W,G,Q,H,Y,Z;return l(),o("tr",{key:n.username},[a("td",null,[a("strong",null,s(n.username),1),a("div",Ka,s(n.email||"—"),1)]),a("td",null,s(n.role||"user"),1),a("td",null,[a("span",{class:U(["status-badge",(d=n.status)!=null&&d.online?"online":"offline"])},s((w=n.status)!=null&&w.online?e.$t("adminDashboard.online"):e.$t("adminDashboard.offline")),3)]),a("td",null,[a("span",{class:U(["status-badge",Ze((_=n.storage)==null?void 0:_.status)])},s(Ye((N=n.storage)==null?void 0:N.usage_percent)),3),a("div",Xa,[a("span",{style:ra({width:He((J=n.storage)==null?void 0:J.usage_percent)})},null,4)])]),a("td",null,s(((X=(K=n.usage)==null?void 0:K.fast)==null?void 0:X.count)||0),1),a("td",null,s(((G=(W=n.usage)==null?void 0:W.thinking)==null?void 0:G.count)||0),1),a("td",null,s(((H=(Q=n.usage)==null?void 0:Q.search)==null?void 0:H.count)||0),1),a("td",null,s(y((Y=n.storage)==null?void 0:Y.project_bytes)),1),a("td",null,s(de((Z=n.status)==null?void 0:Z.last_active)),1)])}),128))])])])])):p.value==="containers"?(l(),o("section",Wa,[a("h2",null,s(e.$t("adminDashboard.containersTitle")),1),a("div",Ga,[a("table",null,[a("thead",null,[a("tr",null,[a("th",null,s(e.$t("adminDashboard.tableUser")),1),a("th",null,s(e.$t("adminDashboard.tableMode")),1),a("th",null,s(e.$t("adminDashboard.tableContainerName")),1),a("th",null,s(e.$t("adminDashboard.tableCpu")),1),a("th",null,s(e.$t("adminDashboard.tableMemPercent")),1),a("th",null,s(e.$t("adminDashboard.tableMemUsage")),1),a("th",null,s(e.$t("adminDashboard.tableMemLimit")),1),a("th",null,s(e.$t("adminDashboard.tableNetIo")),1),a("th",null,s(e.$t("adminDashboard.tableStatus")),1),a("th",null,s(e.$t("adminDashboard.tableLastActive")),1)])]),a("tbody",null,[_e.value.length?h("",!0):(l(),o("tr",Qa,[a("td",Ha,s(e.$t("adminDashboard.emptyContainers")),1)])),(l(!0),o(m,null,b(_e.value,n=>{var d,w,_,N,J,K,X,W,G,Q,H,Y,Z;return l(),o("tr",{key:n.username},[a("td",null,s(n.username),1),a("td",null,s(n.mode||"host"),1),a("td",null,s(n.container_name||"—"),1),a("td",null,s(Te((d=n.stats)==null?void 0:d.cpu_percent)),1),a("td",null,s(Te((_=(w=n.stats)==null?void 0:w.memory)==null?void 0:_.percent)),1),a("td",null,s(y((J=(N=n.stats)==null?void 0:N.memory)==null?void 0:J.used_bytes)),1),a("td",null,s(y((X=(K=n.stats)==null?void 0:K.memory)==null?void 0:X.limit_bytes)),1),a("td",null,s(y((G=(W=n.stats)==null?void 0:W.net_io)==null?void 0:G.rx_bytes))+" / "+s(y((H=(Q=n.stats)==null?void 0:Q.net_io)==null?void 0:H.tx_bytes)),1),a("td",null,[a("span",{class:U(["status-badge",xe(n)])},s(((Y=n.state)==null?void 0:Y.status)||((Z=n.state)!=null&&Z.running?e.$t("common.running"):e.$t("adminDashboard.unknown"))),3)]),a("td",null,s(de(n.last_active)),1)])}),128))])])])])):p.value==="uploads"?(l(),o("section",Ya,[a("h2",null,s(e.$t("adminDashboard.uploadsTitle")),1),a("div",Za,[a("span",null,s(e.$t("adminDashboard.last24h",{count:B.value.last_24h||0})),1),a("span",null,s(e.$t("adminDashboard.blocked",{count:B.value.blocked_last_24h||0})),1),a("span",null,s(e.$t("adminDashboard.skippedScan",{count:B.value.skipped_scan_last_24h||0})),1),a("span",null,s(e.$t("adminDashboard.quarantineUsage",{size:y(B.value.quarantine_bytes)})),1)]),a("div",xa,[ye.value.length?h("",!0):(l(),o("span",es,s(e.$t("adminDashboard.noSourceStats")),1)),(l(!0),o(m,null,b(ye.value,n=>(l(),o("span",{key:n.source},s(n.source)+""+s(n.count),1))),128))]),a("ul",as,[we.value.length?h("",!0):(l(),o("li",ss,s(e.$t("adminDashboard.noRecentUploads")),1)),(l(!0),o(m,null,b(we.value,n=>{var d;return l(),o("li",{key:n.upload_id,class:"upload-item"},[a("div",null,[a("strong",null,s(n.original_name||e.$t("adminDashboard.unnamedFile")),1),a("div",ns,[a("span",null,s(e.$t("adminDashboard.uploadUser",{name:n.username})),1),a("span",null,s(e.$t("adminDashboard.uploadSource",{name:n.source||"unknown"})),1),a("span",null,s(e.$t("adminDashboard.uploadSize",{size:y(n.size)})),1)])]),a("div",ts,[a("span",null,s(de(n.timestamp)),1),a("span",{class:U(["status-badge",n.accepted?"online":"danger"])},s(n.accepted?e.$t("adminDashboard.accepted"):e.$t("adminDashboard.blockedBadge")),3),(d=n.error)!=null&&d.message?(l(),o("span",ls,s(n.error.message),1)):h("",!0)])])}),128))])])):p.value==="invites"?(l(),o("section",os,[a("h2",null,s(e.$t("adminDashboard.invitesTitle")),1),a("div",rs,[a("span",null,s(e.$t("adminDashboard.inviteTotal",{count:ie.value.total||0})),1),a("span",null,s(e.$t("adminDashboard.inviteActive",{count:ie.value.active||0})),1),a("span",null,s(e.$t("adminDashboard.inviteConsumed",{count:ie.value.consumed||0})),1),a("span",null,s(e.$t("adminDashboard.inviteUnlimited",{count:ie.value.unlimited||0})),1)]),a("div",is,[V(a("input",{"onUpdate:modelValue":t[1]||(t[1]=n=>ne.value=n),class:"invite-input",type:"text",placeholder:e.$t("adminDashboard.newInvitePlaceholder"),disabled:v.value},null,8,ds),[[ue,ne.value,void 0,{trim:!0}]]),V(a("input",{"onUpdate:modelValue":t[2]||(t[2]=n=>te.value=n),class:"invite-input short",type:"number",min:"0",placeholder:e.$t("adminDashboard.remainingPlaceholder"),disabled:v.value||O.value},null,8,us),[[ue,te.value]]),a("label",cs,[V(a("input",{type:"checkbox","onUpdate:modelValue":t[3]||(t[3]=n=>O.value=n),disabled:v.value},null,8,hs),[[Ue,O.value]]),Re(" "+s(e.$t("adminDashboard.unlimitedLabel")),1)]),a("button",{type:"button",disabled:v.value,onClick:Oe},s(v.value?e.$t("adminDashboard.processing"):e.$t("adminDashboard.addInvite")),9,vs)]),g.value?(l(),o("p",ms,s(g.value),1)):h("",!0),a("div",bs,[$e.value.length?h("",!0):(l(),o("div",ps,s(e.$t("adminDashboard.noInviteData")),1)),(l(!0),o(m,null,b($e.value,n=>(l(),o("div",{key:n.code,class:"invite-card"},[a("h4",null,s(n.code),1),a("span",null,s(ea(n.remaining)),1),a("div",fs,[a("button",{type:"button",class:"mini-btn",disabled:v.value,onClick:d=>Ke(n)},s(e.$t("adminDashboard.adjustRemaining")),9,gs),a("button",{type:"button",class:"mini-btn danger",disabled:v.value,onClick:d=>Xe(n.code)},s(e.$t("common.delete")),9,ks)])]))),128))])])):p.value==="passwords"?(l(),o("section",Ds,[a("h2",null,s(e.$t("adminDashboard.passwordManagement")),1),a("p",ys,s(e.$t("adminDashboard.passwordHint")),1),a("div",ws,[a("div",_s,[a("label",null,s(e.$t("adminDashboard.selectUser")),1),a("div",{class:"user-search-wrapper",ref_key:"userSearchRef",ref:he},[a("div",{class:U(["user-search-trigger",{open:S.value,filled:k.value}]),onClick:ze},[k.value?(l(),o("span",$s,[a("strong",null,s(k.value),1),a("span",Ss,s(qe.value),1)])):(l(),o("span",Cs,s(e.$t("adminDashboard.userSearchPlaceholder")),1)),t[12]||(t[12]=a("span",{class:"user-search-arrow"},"▾",-1))],2),S.value?(l(),o("div",Ts,[V(a("input",{ref_key:"passwordSearchInputRef",ref:pe,class:"user-search-input",type:"text","onUpdate:modelValue":t[4]||(t[4]=n=>q.value=n),placeholder:e.$t("adminDashboard.filterPlaceholder"),onKeydown:t[5]||(t[5]=Ie(n=>S.value=!1,["escape"]))},null,40,Ns),[[ue,q.value]]),a("div",Us,[(l(!0),o(m,null,b(ke.value,n=>(l(),o("div",{key:n.username,class:U(["user-search-item",{active:k.value===n.username}]),onClick:d=>Je(n)},[a("span",Is,s(n.username),1),a("span",Ms,s(n.email||"—"),1),n.role==="admin"?(l(),o("span",Es,s(e.$t("adminDashboard.adminRole")),1)):h("",!0)],10,Rs))),128)),ke.value.length?h("",!0):(l(),o("div",Fs,s(e.$t("adminDashboard.noMatchingUsers")),1))])])):h("",!0)],512)]),a("div",Ls,[a("label",null,s(e.$t("adminDashboard.newPasswordLabel")),1),V(a("input",{class:"password-input",type:"password","onUpdate:modelValue":t[6]||(t[6]=n=>M.value=n),disabled:E.value,placeholder:e.$t("adminDashboard.newPasswordPlaceholder"),onKeyup:Ie(ge,["enter"])},null,40,Ps),[[ue,M.value]])]),a("div",Bs,[a("button",{type:"button",disabled:!k.value||!M.value||E.value,onClick:ge},s(E.value?e.$t("adminDashboard.resetting"):e.$t("adminDashboard.resetPassword")),9,As),a("button",{type:"button",class:"ghost-btn",disabled:E.value,onClick:t[7]||(t[7]=n=>{k.value="",M.value="",F.value="",L.value=""})},s(e.$t("adminDashboard.clear")),9,js)]),F.value?(l(),o("p",Vs,s(F.value),1)):h("",!0),L.value?(l(),o("p",Os,s(L.value),1)):h("",!0)])])):h("",!0)]),_:1})])])):(l(),o("div",qs,[a("strong",null,s(e.$t("common.loadFailed")),1),a("p",null,s(ce.value||e.$t("adminDashboard.cannotLoadData")),1),a("button",{type:"button",onClick:Ve},s(e.$t("common.retry")),1)]))]))}}}),Js=va(zs,[["__scopeId","data-v-c82f8fd3"]]),Me=da(Js);ua(Me);Me.mount("#admin-app");