PageSourceSearch

https://sangbutiken.se/assets/Admin-CuNpDjqV.js

js sangbutiken.se collected 2026-10-09 22:03:52 UTC 46,515 bytes, 31 lines download raw bytes

1import{n as K,j as e,B as C,bI as Z,U as ke,E as X,v as Ne,s as N,bJ as Se,bK as _e,bk as O,L,b3 as Y,bm as ve,A as je,g as Me,bL as Ie,aS as Ce,az as H,bB as De,aA as ee,bA as te,bG as Ee,F as Oe,S as Le,ap as se,bM as re,bN as Ae,bO as Te,x as Fe,bF as ae,bP as Re,aT as Ke,p as Pe,aq as Be,bC as He}from"./index-B0RymvlI.js";import{r as f,f as $e,A as Ve,C as ze,X as We,Y as ne,T as qe,h as ie}from"./charts-DAQo80Uz.js";import{C as Q}from"./card-atbkx2k_.js";import{S as Ge,a as Ue,b as Ye,c as Xe,d as Qe}from"./select-BqpjCFNc.js";import{S as Je,e as Ze,p as et,d as tt,t as st}from"./exportUtils-1GBLr-m7.js";import{F as rt}from"./file-down-CcXwz-hl.js";import{P as at}from"./printer-Bx9GS2do.js";import{S as R}from"./shopping-cart-CWYKu9JI.js";import{T as z}from"./trending-up-DtSsrfDD.js";import{M as be}from"./mouse-pointer-click-CjGk4e1S.js";import{a as nt}from"./addMonths-BZzM13X1.js";import{f as B,s as F}from"./format-BP7ThvXg.js";import{s as ye}from"./sv-CCRm9mwl.js";import{e as D}from"./endOfDay-Oj5F0dBZ.js";import{s as _,a as oe}from"./subDays-BaWy4M-4.js";import{e as it}from"./endOfMonth-BqyHCjVs.js";import{e as ot}from"./eachDayOfInterval-C_r1dXpn.js";import{E as lt}from"./external-link-9u1PhXpE.js";import{e as ct,t as $,g as le,m as ce,a as de,b as me,c as dt,d as ue}from"./en-US-C7VwNmUA.js";import{c as mt,g as ut,a as pt}from"./getRoundingMethod-DeC0xejf.js";import{B as V}from"./bed-DEBqdXtv.js";import{B as xt,S as gt}from"./settings-CtelvUFm.js";import{M as ht}from"./message-square-CV72nxWl.js";import{L as pe}from"./layout-grid-CPJsE0ux.js";import{F as q}from"./factory-B_ajyMcx.js";import{S as ft}from"./store-CaSwhA_s.js";import{C as kt}from"./credit-card-D48WPcND.js";import{I as vt}from"./inbox-BMJ_q6d4.js";import{C as jt}from"./cookie-C7ovKrx8.js";import"./pdf-DlF9gChH.js";import"./chevron-up-DlnIpn04.js";/**
2 * @license lucide-react v0.462.0 - ISC
3 *
4 * This source code is licensed under the ISC license.
5 * See the LICENSE file in the root directory of this source tree.
6 */const bt=K("Activity",[["path",{d:"M22 12h-2.48a2 2 0 0 0-1.93 1.46l-2.35 8.36a.25.25 0 0 1-.48 0L9.24 2.18a.25.25 0 0 0-.48 0l-2.35 8.36A2 2 0 0 1 4.49 12H2",key:"169zse"}]]);/**
7 * @license lucide-react v0.462.0 - ISC
8 *
9 * This source code is licensed under the ISC license.
10 * See the LICENSE file in the root directory of this source tree.
11 */const yt=K("CircleDot",[["circle",{cx:"12",cy:"12",r:"10",key:"1mglay"}],["circle",{cx:"12",cy:"12",r:"1",key:"41hilf"}]]);/**
12 * @license lucide-react v0.462.0 - ISC
13 *
14 * This source code is licensed under the ISC license.
15 * See the LICENSE file in the root directory of this source tree.
16 */const G=K("Gauge",[["path",{d:"m12 14 4-4",key:"9kzdfg"}],["path",{d:"M3.34 19a10 10 0 1 1 17.32 0",key:"19p75a"}]]);/**
17 * @license lucide-react v0.462.0 - ISC
18 *
19 * This source code is licensed under the ISC license.
20 * See the LICENSE file in the root directory of this source tree.
21 */const wt=K("Monitor",[["rect",{width:"20",height:"14",x:"2",y:"3",rx:"2",key:"48i651"}],["line",{x1:"8",x2:"16",y1:"21",y2:"21",key:"1svkeh"}],["line",{x1:"12",x2:"12",y1:"17",y2:"21",key:"vw1qmm"}]]);/**
22 * @license lucide-react v0.462.0 - ISC
23 *
24 * This source code is licensed under the ISC license.
25 * See the LICENSE file in the root directory of this source tree.
26 */const Nt=K("Smartphone",[["rect",{width:"14",height:"20",x:"5",y:"2",rx:"2",ry:"2",key:"1yt0o3"}],["path",{d:"M12 18h.01",key:"mhygvu"}]]);/**
27 * @license lucide-react v0.462.0 - ISC
28 *
29 * This source code is licensed under the ISC license.
30 * See the LICENSE file in the root directory of this source tree.
31 */const St=K("Tablet",[["rect",{width:"16",height:"20",x:"4",y:"2",rx:"2",ry:"2",key:"76otgf"}],["line",{x1:"12",x2:"12.01",y1:"18",y2:"18",key:"1dp563"}]]);function _t(t,s,r){const m=dt(),i=r?.locale??m.locale??ct,g=mt(t,s);if(isNaN(g))throw new RangeError("Invalid time value");const c=Object.assign({},r,{addSuffix:r?.addSuffix,comparison:g});let v,p;g>0?(v=$(s),p=$(t)):(v=$(t),p=$(s));const k=ut(r?.roundingMethod??"round"),o=p.getTime()-v.getTime(),n=o/ue,l=le(p)-le(v),h=(o-l)/ue,u=r?.unit;let a;if(u?a=u:n<1?a="second":n<60?a="minute":n<ce?a="hour":h<de?a="day":h<me?a="month":a="year",a==="second"){const x=k(o/1e3);return i.formatDistance("xSeconds",x,c)}else if(a==="minute"){const x=k(n);return i.formatDistance("xMinutes",x,c)}else if(a==="hour"){const x=k(n/60);return i.formatDistance("xHours",x,c)}else if(a==="day"){const x=k(h/ce);return i.formatDistance("xDays",x,c)}else if(a==="month"){const x=k(h/de);return x===12&&u!=="month"?i.formatDistance("xYears",1,c):i.formatDistance("xMonths",x,c)}else{const x=k(h/me);return i.formatDistance("xYears",x,c)}}function Mt(t,s){return _t(t,pt(t),s)}function It(t,s){return nt(t,-s)}const P={today:"Idag","7d":"Senaste 7 dagarna",month:"Denna månad","30d":"Senaste 30 dagarna"},S={today:"vs igår","7d":"vs föregående 7 dagar",month:"vs förra månaden","30d":"vs föregående 30 dagar"};function Ct(t){const s=new Date;if(t==="today"){const i=F(s),g=D(s);return{from:i,to:g,prevFrom:F(_(s,1)),prevTo:D(_(s,1))}}if(t==="7d"){const i=D(s);return{from:F(_(s,6)),to:i,prevFrom:F(_(s,13)),prevTo:D(_(s,7))}}if(t==="month"){const i=oe(s),g=D(s),c=It(s,1);return{from:i,to:g,prevFrom:oe(c),prevTo:it(c)}}const r=D(s);return{from:F(_(s,29)),to:r,prevFrom:F(_(s,59)),prevTo:D(_(s,30))}}const xe={revenue:0,orders:0,visitors:0,pageViews:0,productClicks:0,avgDurationMs:0,conversion:0,daily:[]};async function ge(t,s,r){const m=t.toISOString(),i=s.toISOString(),[g,c]=await Promise.all([N.from("orders").select("total_amount, created_at, payment_status").gte("created_at",m).lte("created_at",i),N.from("page_events").select("event_type, session_id, duration_ms, created_at").gte("created_at",m).lte("created_at",i).limit(5e4)]),v=(g.data??[]).filter(j=>j.payment_status==="paid"),p=v.reduce((j,A)=>j+(A.total_amount??0),0),k=v.length,o=c.data??[],n=new Set;let l=0,h=0,u=0,a=0;for(const j of o)j.event_type==="page_view"&&(l++,j.session_id&&n.add(j.session_id)),j.event_type==="product_click"&&h++,j.event_type==="session_end"&&j.duration_ms&&j.duration_ms>0&&j.duration_ms<30*60*1e3&&(u+=j.duration_ms,a++);const x=n.size,y=a>0?u/a:0,W=x>0?k/x*100:0;let J=[];
31if(r){const j=ot({start:t,end:s}),A=new Map;for(const b of j)A.set(B(b,"yyyy-MM-dd"),{revenue:0,visitors:new Set,orders:0});for(const b of v){const T=B(new Date(b.created_at),"yyyy-MM-dd"),w=A.get(T);w&&(w.revenue+=b.total_amount??0,w.orders+=1)}for(const b of o){if(b.event_type!=="page_view")continue;const T=B(new Date(b.created_at),"yyyy-MM-dd"),w=A.get(T);w&&b.session_id&&w.visitors.add(b.session_id)}J=j.map(b=>{const T=B(b,"yyyy-MM-dd"),w=A.get(T);return{date:T,revenue:w.revenue,visitors:w.visitors.size,orders:w.orders}})}return{revenue:p,orders:k,visitors:x,pageViews:l,productClicks:h,avgDurationMs:y,conversion:W,daily:J}}function M(t,s){return s===0?t===0?0:null:(t-s)/s*100}function Dt(t){if(!t)return"0s";const s=Math.round(t/1e3);if(s<60)return`${s}s`;const r=Math.floor(s/60),m=s%60;return`${r}m ${m}s`}const I=({icon:t,label:s,value:r,delta:m,compareLabel:i,invertColor:g=!1})=>{const c=m!==null&&m>=0,v=g?!c:c;return e.jsxs(Q,{className:"p-5",children:[e.jsxs("div",{className:"flex items-center justify-between",children:[e.jsx("span",{className:"font-mono-label text-xs text-muted-foreground",children:s}),e.jsx("span",{className:"text-muted-foreground",children:t})]}),e.jsx("p",{className:"mt-3 font-display text-3xl tracking-tight",children:r}),e.jsx("div",{className:"mt-2 flex items-center gap-1.5 text-xs",children:m===null?e.jsx("span",{className:"text-muted-foreground",children:"— ingen jämförelsedata"}):e.jsxs(e.Fragment,{children:[e.jsxs("span",{className:Se("inline-flex items-center gap-1 rounded-full px-1.5 py-0.5 font-medium",v?"bg-green-500/10 text-green-600 dark:text-green-400":"bg-destructive/10 text-destructive"),children:[c?e.jsx(z,{className:"h-3 w-3"}):e.jsx(_e,{className:"h-3 w-3"}),Math.abs(m).toFixed(1),"%"]}),e.jsx("span",{className:"text-muted-foreground",children:i})]})})]})},Et=()=>{const[t,s]=f.useState("7d"),[r,m]=f.useState(!0),[i,g]=f.useState(xe),[c,v]=f.useState(xe),p=f.useRef(null),[k,o]=f.useState(!1);f.useEffect(()=>{let a=!1;m(!0);const x=Ct(t);return Promise.all([ge(x.from,x.to,!0),ge(x.prevFrom,x.prevTo,!1)]).then(([y,W])=>{a||(g(y),v(W))}).finally(()=>!a&&m(!1)),()=>{a=!0}},[t]);const n=f.useMemo(()=>i.daily.map(a=>({...a,label:B(new Date(a.date),t==="today"?"HH:mm":"d MMM",{locale:ye})})),[i.daily,t]),l=async()=>{if(p.current){o(!0);try{await Ze(p.current,`oversikt-${P[t].toLowerCase().replace(/\s+/g,"-")}.pdf`)}finally{o(!1)}}},h=()=>p.current&&et(p.current,`Översikt — ${P[t]}`),u=()=>{const a=i.daily.map(y=>({datum:y.date,forsaljning_kr:y.revenue,besokare:y.visitors})),x=[{datum:`Totalt (${P[t]})`,forsaljning_kr:i.revenue,besokare:i.visitors}];tt(st([...a,...x]),`oversikt-${t}.csv`)};return e.jsxs("section",{ref:p,className:"rounded-xl border border-border bg-card/50 p-6",children:[e.jsxs("div",{className:"flex items-end justify-between gap-4 flex-wrap",children:[e.jsxs("div",{children:[e.jsx("p",{className:"font-mono-label text-accent",children:"Översikt"}),e.jsx("h2",{className:"mt-1 font-display text-2xl tracking-tight",children:"Hur går det för butiken?"}),e.jsxs("p",{className:"mt-1 text-sm text-muted-foreground",children:["Realtidsdata för försäljning, besökare och beteende — ",S[t],"."]})]}),e.jsxs("div",{className:"flex items-center gap-2 flex-wrap no-print",children:[e.jsxs(Ge,{value:t,onValueChange:a=>s(a),children:[e.jsx(Ue,{className:"w-[230px]",children:e.jsx(Ye,{})}),e.jsx(Xe,{children:Object.keys(P).map(a=>e.jsx(Qe,{value:a,children:P[a]},a))})]}),e.jsxs(C,{variant:"outline",size:"sm",onClick:l,disabled:k,className:"gap-1.5",children:[e.jsx(rt,{className:"h-4 w-4"})," PDF"]}),e.jsxs(C,{variant:"outline",size:"sm",onClick:h,className:"gap-1.5",children:[e.jsx(at,{className:"h-4 w-4"})," Skriv ut"]}),e.jsxs(C,{variant:"outline",size:"sm",onClick:u,className:"gap-1.5",children:[e.jsx(Je,{className:"h-4 w-4"})," CSV"]})]})]}),e.jsxs("div",{className:"mt-6 grid gap-3 grid-cols-2 lg:grid-cols-4",children:[e.jsx(I,{icon:e.jsx(Z,{className:"h-4 w-4"}),label:"Försäljning",value:`${i.revenue.toLocaleString("sv-SE")} kr`,delta:M(i.revenue,c.revenue),compareLabel:S[t]}),e.jsx(I,{icon:e.jsx(R,{className:"h-4 w-4"}
31),label:"Ordrar",value:i.orders.toLocaleString("sv-SE"),delta:M(i.orders,c.orders),compareLabel:S[t]}),e.jsx(I,{icon:e.jsx(ke,{className:"h-4 w-4"}),label:"Unika besökare",value:i.visitors.toLocaleString("sv-SE"),delta:M(i.visitors,c.visitors),compareLabel:S[t]}),e.jsx(I,{icon:e.jsx(z,{className:"h-4 w-4"}),label:"Konvertering",value:`${i.conversion.toFixed(2)}%`,delta:M(i.conversion,c.conversion),compareLabel:S[t]}),e.jsx(I,{icon:e.jsx(X,{className:"h-4 w-4"}),label:"Sidvisningar",value:i.pageViews.toLocaleString("sv-SE"),delta:M(i.pageViews,c.pageViews),compareLabel:S[t]}),e.jsx(I,{icon:e.jsx(be,{className:"h-4 w-4"}),label:"Produktklick",value:i.productClicks.toLocaleString("sv-SE"),delta:M(i.productClicks,c.productClicks),compareLabel:S[t]}),e.jsx(I,{icon:e.jsx(Ne,{className:"h-4 w-4"}),label:"Snittid på sida",value:Dt(i.avgDurationMs),delta:M(i.avgDurationMs,c.avgDurationMs),compareLabel:S[t]}),e.jsx(I,{icon:e.jsx(Z,{className:"h-4 w-4"}),label:"Snittordervärde",value:`${(i.orders>0?Math.round(i.revenue/i.orders):0).toLocaleString("sv-SE")} kr`,delta:M(i.orders>0?i.revenue/i.orders:0,c.orders>0?c.revenue/c.orders:0),compareLabel:S[t]})]}),e.jsxs(Q,{className:"mt-6 p-5",children:[e.jsxs("div",{className:"flex items-center justify-between flex-wrap gap-2",children:[e.jsxs("div",{children:[e.jsx("p",{className:"font-mono-label text-xs text-muted-foreground",children:"Trend"}),e.jsx("h3",{className:"font-display text-lg",children:"Försäljning & besökare"})]}),e.jsxs("div",{className:"flex items-center gap-4 text-xs text-muted-foreground",children:[e.jsxs("span",{className:"inline-flex items-center gap-1.5",children:[e.jsx("span",{className:"h-2 w-2 rounded-full bg-primary"})," Försäljning (kr)"]}),e.jsxs("span",{className:"inline-flex items-center gap-1.5",children:[e.jsx("span",{className:"h-2 w-2 rounded-full bg-accent"})," Unika besökare"]})]})]}),e.jsx("div",{className:"mt-4 h-[280px]",children:r?e.jsx("div",{className:"h-full flex items-center justify-center text-muted-foreground text-sm",children:"Laddar data…"}):n.length===0?e.jsx("div",{className:"h-full flex items-center justify-center text-muted-foreground text-sm",children:"Ingen data för perioden"}):e.jsx($e,{width:"100%",height:"100%",children:e.jsxs(Ve,{data:n,margin:{top:10,right:10,left:0,bottom:0},children:[e.jsxs("defs",{children:[e.jsxs("linearGradient",{id:"rev",x1:"0",y1:"0",x2:"0",y2:"1",children:[e.jsx("stop",{offset:"0%",stopColor:"hsl(var(--primary))",stopOpacity:.4}),e.jsx("stop",{offset:"100%",stopColor:"hsl(var(--primary))",stopOpacity:0})]}),e.jsxs("linearGradient",{id:"vis",x1:"0",y1:"0",x2:"0",y2:"1",children:[e.jsx("stop",{offset:"0%",stopColor:"hsl(var(--accent))",stopOpacity:.4}),e.jsx("stop",{offset:"100%",stopColor:"hsl(var(--accent))",stopOpacity:0})]})]}),e.jsx(ze,{strokeDasharray:"3 3",stroke:"hsl(var(--border))"}),e.jsx(We,{dataKey:"label",stroke:"hsl(var(--muted-foreground))",fontSize:11}),e.jsx(ne,{yAxisId:"left",stroke:"hsl(var(--muted-foreground))",fontSize:11}),e.jsx(ne,{yAxisId:"right",orientation:"right",stroke:"hsl(var(--muted-foreground))",fontSize:11}),e.jsx(qe,{contentStyle:{background:"hsl(var(--background))",border:"1px solid hsl(var(--border))",borderRadius:8,fontSize:12},formatter:(a,x)=>x==="revenue"?[`${a.toLocaleString("sv-SE")} kr`,"Försäljning"]:x==="visitors"?[a.toLocaleString("sv-SE"),"Besökare"]:[a,x]}),e.jsx(ie,{yAxisId:"left",type:"monotone",dataKey:"revenue",stroke:"hsl(var(--primary))",fill:"url(#rev)",strokeWidth:2}),e.jsx(ie,{yAxisId:"right",type:"monotone",dataKey:"visitors",stroke:"hsl(var(--accent))",fill:"url(#vis)",strokeWidth:2})]})})})]})]})},U=5*60*1e3;function Ot(t){if(!t)return{source:"Direkt / bookmark",isInternal:!1};try{const r=new URL(t).hostname.replace(/^www\./,""),m=typeof window<"u"?window.location.hostname.replace(/^www\./,""):"";return r===m||r.endsWith(".lovable.app")||r.endsWith(".lovable.dev")?{source:"Internt",isInternal:!0}:/google\./i.test(r)?{source:"Google",isInternal:!1}:/bing\./i.test(r)?{source:"Bing",isInternal:!1}:/duckduckgo\./i.test(r)?{source:"DuckDuckGo",isInternal:!1}:/(facebook|fb)\./i.test(r)?{source:"Facebook",isInternal:!1}:/instagram\./i.test(r)?{source:"Instagram",isInternal:!1}:/tiktok\./i.test(r)?{source:"TikTok",isInternal:!1}:/(t|x)\.co|twitter\./i.test(r)?{source:"X / Twitter",isInternal:!1}:/linkedin\./i.test(r)?{source:"LinkedIn",isInternal:!1}:/youtube\./i.test(r)?{source:"YouTube",isInternal:!1}:/pinterest\./i.test(r)?{source:"Pinterest",isInternal:!1}:/reddit\./i.test(r)?{source:"Reddit",isInternal:!1}:{source:r,isInternal:!1}}catch{return{source:"Okänd",isInternal:!1}}}function Lt(t,s){const r=t.product_id?s.get(t.product_id):null;switch(t.event_type){case"product_view":return{icon:e.jsx(X,{className:"h-3 w-3 text-blue-500"}),text:`Tittar på ${r||"produkt"}`};case"product_click":return{icon:e.jsx(be,{className:"h-3 w-3 text-purple-500"}),text:`Klickade på ${r||"produkt"}`};case"add_to_cart":return{icon:e.jsx(R,{className:"h-3 w-3 text-green-600"}),text:`Lade ${r||"produkt"} i kundvagn`};case"configurator_start":return{icon:e.jsx(V,{className:"h-3 w-3 text-blue-600"}),text:`Började bygga ${r||"säng"}`};case"bedtest_view":return{icon:e.jsx(V,{className:"h-3 w-3 text-amber-600"}),text:"Startade sängtestet"};case"bedtest_click":return{icon:e.jsx(V,{className:"h-3 w-3 text-amber-600"}),text:`Klickade på ${r||"test-resultat"}`};case"page_view":default:return{icon:e.jsx(je,{className:"h-3 w-3 text-muted-foreground"}),text:t.path||"/"}}}function he(t){return t?t==="/"?"Startsidan":t.startsWith("/produkt/")?`Produkt: ${t.replace("/produkt/","")}`:t.startsWith("/kategori/")?`Kategori: ${t.replace("/kategori/","")}`:t.startsWith("/blogg/")?`Blogg: ${t.replace("/blogg/","")}
31`:t.startsWith("/varumarke/")?`Varumärke: ${t.replace("/varumarke/","")}`:t.startsWith("/sangbutik/")?`Stadssida: ${t.replace("/sangbutik/","")}`:t==="/checkout"?"💳 KASSAN":t==="/sangtest"?"Sängtestet":t==="/sangar"?"Alla sängar":t:"Okänd sida"}function we(t){return!!t&&(t==="/checkout"||t.startsWith("/checkout"))}const At=()=>{const[t,s]=f.useState(new Map),[r,m]=f.useState(new Map),[i,g]=f.useState(new Map),[c,v]=f.useState(0);f.useEffect(()=>{let o=!1;const n=new Date(Date.now()-U).toISOString();return(async()=>{const{data:l}=await N.from("page_events").select("*").gte("created_at",n).neq("event_type","session_end").order("created_at",{ascending:!0}).limit(2e3);if(o)return;const h=new Map;for(const a of l||[])fe(h,a);s(h);const u=Array.from(new Set((l||[]).map(a=>a.product_id).filter(a=>!!a)));if(u.length){const{data:a}=await N.from("products").select("id, name").in("id",u);if(!o&&a){const x=new Map;for(const y of a)x.set(y.id,y.name);m(x)}}})(),()=>{o=!0}},[]),f.useEffect(()=>{let o=!1;(async()=>{const l=new Date(Date.now()-U).toISOString(),{data:h}=await N.from("live_carts").select("*").gte("updated_at",l);if(o||!h)return;const u=new Map;for(const a of h)u.set(a.session_id,a);g(u)})();const n=N.channel("admin-live-carts").on("postgres_changes",{event:"*",schema:"public",table:"live_carts"},l=>{g(h=>{const u=new Map(h);if(l.eventType==="DELETE"){const a=l.old;a?.session_id&&u.delete(a.session_id)}else{const a=l.new;a?.session_id&&u.set(a.session_id,a)}return u})}).subscribe();return()=>{o=!0,N.removeChannel(n)}},[]),f.useEffect(()=>{const o=N.channel("admin-live-events").on("postgres_changes",{event:"INSERT",schema:"public",table:"page_events"},async n=>{const l=n.new;if(l.event_type!=="session_end"&&(s(h=>{const u=new Map(h);return fe(u,l),u}),l.product_id&&!r.has(l.product_id))){const{data:h}=await N.from("products").select("id, name").eq("id",l.product_id).maybeSingle();h&&m(u=>new Map(u).set(h.id,h.name))}}).subscribe();return()=>{N.removeChannel(o)}},[]),f.useEffect(()=>{const o=setInterval(()=>{v(n=>n+1),s(n=>{const l=Date.now()-U;let h=!1;const u=new Map(n);for(const[a,x]of u)new Date(x.last_seen).getTime()<l&&(u.delete(a),h=!0);return h?u:n})},15e3);return()=>clearInterval(o)},[]);const p=f.useMemo(()=>{const o=Array.from(t.values());return o.sort((n,l)=>new Date(l.last_seen).getTime()-new Date(n.last_seen).getTime()),o},[t,c]),k=f.useMemo(()=>{const o=p.filter(u=>we(u.current_path)).length,n=p.filter(u=>u.current_path?.startsWith("/produkt/")).length,l=p.filter(u=>u.page_count<=1).length,h=p.filter(u=>{const a=i.get(u.session_id);return a&&a.item_count>0}).length;return{inCheckout:o,onProduct:n,newVisitors:l,withCart:h}},[p,c,i]);return e.jsxs(Q,{className:"overflow-hidden",children:[e.jsxs("div",{className:"flex items-center justify-between gap-3 flex-wrap p-5 border-b border-border bg-gradient-to-r from-primary/5 to-transparent",children:[e.jsxs("div",{className:"flex items-center gap-3",children:[e.jsxs("div",{className:"relative",children:[e.jsx("span",{className:"absolute inline-flex h-2.5 w-2.5 rounded-full bg-green-500 opacity-75 animate-ping"}),e.jsx(yt,{className:"h-5 w-5 text-green-500 relative"})]}),e.jsxs("div",{children:[e.jsx("p",{className:"font-mono-label text-xs text-accent",children:"Live"}),e.jsxs("h2",{className:"font-display text-xl tracking-tight",children:[p.length," ",(p.length===1,"besökare")," just nu"]})]})]}),e.jsxs("div",{className:"flex items-center gap-2 flex-wrap",children:[k.inCheckout>0&&e.jsxs(O,{className:"bg-green-600 text-white hover:bg-green-600 gap-1",children:[e.jsx(R,{className:"h-3 w-3"})," ",k.inCheckout," i kassan"]}),k.withCart>0&&e.jsxs(O,{className:"bg-amber-500 text-white hover:bg-amber-500 gap-1",children:[e.jsx(R,{className:"h-3 w-3"})," ",k.withCart," med varukorg"]}),k.onProduct>0&&e.jsxs(O,{variant:"secondary",className:"gap-1",children:[e.jsx(X,{className:"h-3 w-3"})," ",k.onProduct," på produktsida"]}),e.jsxs(O,{variant:"outline",className:"gap-1",children:[e.jsx(bt,{className:"h-3 w-3"})," ",k.newVisitors," nya"]})]})]}),p.length===0?e.jsx("div",{className:"p-8 text-center text-sm text-muted-foreground",children:"Inga aktiva besökare just nu. Nya besökare dyker upp här direkt."}):e.jsx("ul",{className:"divide-y divide-border max-h-[420px] overflow-y-auto",children:p.map(o=>e.jsx(Tt,{session:o,productMap:r,cart:i.get(o.session_id)||null},o.session_id))})]})};function fe(t,s){const r=t.get(s.session_id);
31r?(r.last_seen=s.created_at,s.event_type==="page_view"?(r.current_path=s.path,r.page_count+=1):!r.current_path&&s.path&&(r.current_path=s.path),!r.referrer&&s.referrer&&(r.referrer=s.referrer),!r.device_type&&s.device_type&&(r.device_type=s.device_type),!r.city&&s.city&&(r.city=s.city),!r.country&&s.country&&(r.country=s.country),!r.search_query&&s.search_query&&(r.search_query=s.search_query),r.events=[...r.events.slice(-9),s]):t.set(s.session_id,{session_id:s.session_id,first_seen:s.created_at,last_seen:s.created_at,current_path:s.path,referrer:s.referrer,page_count:s.event_type==="page_view"?1:0,events:[s],device_type:s.device_type??null,city:s.city??null,country:s.country??null,search_query:s.search_query??null})}const Tt=({session:t,productMap:s,cart:r})=>{const m=Ot(t.referrer),i=we(t.current_path),g=Date.now()-new Date(t.last_seen).getTime(),c=g<6e4,v=!!r&&r.item_count>0,p=t.device_type==="mobile"?Nt:t.device_type==="tablet"?St:wt,k=t.device_type==="mobile"?"Mobil":t.device_type==="tablet"?"Surfplatta":"Dator",o=t.events.find(n=>n.event_type==="page_view")?.path||t.current_path;return e.jsxs("li",{className:`p-4 transition-colors ${i?"bg-green-50/50":""}`,children:[e.jsxs("div",{className:"flex items-start justify-between gap-3 flex-wrap",children:[e.jsxs("div",{className:"min-w-0 flex-1",children:[e.jsxs("div",{className:"flex items-center gap-2 flex-wrap",children:[e.jsx("span",{className:`inline-block h-2 w-2 rounded-full ${c?"bg-green-500 animate-pulse":"bg-muted-foreground/40"}`}),e.jsx("span",{className:"font-medium text-sm",children:t.current_path?.startsWith("/produkt/")?e.jsxs(L,{to:t.current_path,target:"_blank",className:"hover:text-accent inline-flex items-center gap-1",children:[he(t.current_path)," ",e.jsx(lt,{className:"h-3 w-3"})]}):he(t.current_path)}),i&&e.jsx(O,{className:"bg-green-600 text-white text-[10px]",children:"Hot lead!"}),t.page_count<=1&&e.jsx(O,{variant:"outline",className:"text-[10px]",children:"Ny besökare"}),v&&e.jsxs(O,{className:"bg-amber-500 text-white text-[10px] gap-1",children:[e.jsx(R,{className:"h-3 w-3"})," ",r.item_count," i varukorg"]})]}),e.jsxs("div",{className:"mt-1.5 flex items-center gap-3 text-xs text-muted-foreground flex-wrap",children:[e.jsxs("span",{className:"inline-flex items-center gap-1",children:[e.jsx(p,{className:"h-3 w-3"}),e.jsx("strong",{className:"text-foreground",children:k})]}),e.jsx("span",{children:"•"}),e.jsxs("span",{children:[e.jsx("strong",{className:"text-foreground",children:m.source}),!m.isInternal&&t.referrer&&e.jsxs("span",{className:"opacity-60",children:[" (",Ft(t.referrer),")"]})]}),(t.city||t.country)&&e.jsxs(e.Fragment,{children:[e.jsx("span",{children:"•"}),e.jsxs("span",{className:"inline-flex items-center gap-1",children:[e.jsx(Y,{className:"h-3 w-3"}),e.jsx("strong",{className:"text-foreground",children:t.city||t.country}),t.city&&t.country&&e.jsxs("span",{className:"opacity-60",children:[", ",t.country]})]})]}),e.jsx("span",{children:"•"}),e.jsxs("span",{children:["Landade på ",e.jsx("code",{className:"text-[10px] bg-muted px-1 py-0.5 rounded",children:o})]}),e.jsx("span",{children:"•"}),e.jsxs("span",{children:[t.page_count," sidor"]})]}),t.search_query&&e.jsxs("div",{className:"mt-1.5 inline-flex items-center gap-1.5 text-xs bg-blue-50 text-blue-900 border border-blue-200 rounded px-2 py-1",children:[e.jsx(ve,{className:"h-3 w-3"}),e.jsx("span",{className:"opacity-70",children:"Sökte på Google:"}),e.jsxs("strong",{children:['"',t.search_query,'"']})]})]}),e.jsxs("div",{className:"text-right shrink-0",children:[e.jsx("p",{className:"text-[10px] text-muted-foreground",children:"Senaste aktivitet"}),e.jsx("p",{className:"text-xs font-medium",children:g<5e3?"just nu":`för ${Mt(new Date(t.last_seen),{locale:ye})} sedan`}),e.jsxs("p",{className:"text-[10px] text-muted-foreground mt-0.5",children:["På sajten: ",Math.round((Date.now()-new Date(t.first_seen).getTime())/1e3)," s"]})]})]}),t.events.length>1&&e.jsx("ul",{className:"mt-2 ml-4 space-y-0.5 text-xs",children:t.events.slice(-5).reverse().map(n=>{const l=Lt(n,s);return e.jsxs("li",{className:"flex items-center gap-1.5 text-muted-foreground",children:[l.icon,e.jsx("span",{className:"truncate",children:l.text})]},n.id)})}),v&&e.jsxs("div",{className:"mt-3 ml-4 rounded-md border border-amber-200 bg-amber-50/60 p-2.5",children:[e.jsxs("div",{className:"flex items-center justify-between gap-2 mb-1.5",children:[e.jsxs("p",{className:"text-[11px] font-semibold text-amber-900 flex items-center gap-1",children:[e.jsx(R,{className:"h-3 w-3"})," Varukorg (",r.item_count," artiklar)"]}),e.jsx("p",{className:"text-[11px] font-semibold text-amber-900",children:new Intl.NumberFormat("sv-SE",{style:"currency",currency:"SEK",maximumFractionDigits:0}).format(r.subtotal)})]}),e.jsx("ul",{className:"space-y-1",children:r.items.map((n,l)=>e.jsxs("li",{className:"flex items-center gap-2 text-xs",children:[n.image?e.jsx("img",{src:n.image,alt:"",className:"h-7 w-7 rounded object-cover bg-white"}):e.jsx("div",{className:"h-7 w-7 rounded bg-muted"}),e.jsxs("div",{className:"min-w-0 flex-1",children:[e.jsx("p",{className:"truncate font-medium",children:n.name}),n.summary&&e.jsx("p",{className:"truncate text-[10px] text-muted-foreground",children:n.summary})]}),e.jsxs("span",{className:"text-[11px] text-muted-foreground shrink-0",children:["×",n.qt
31y]}),e.jsx("span",{className:"text-[11px] font-medium shrink-0 tabular-nums",children:new Intl.NumberFormat("sv-SE",{style:"currency",currency:"SEK",maximumFractionDigits:0}).format(n.price*n.qty)})]},`${n.id}-${l}`))})]})]})};function Ft(t){try{return new URL(t).hostname.replace(/^www\./,"")}catch{return t}}const hs=()=>{const{user:t,signOut:s}=Me(),{counts:r}=Ie(),m=r.newOrders+r.openClaims+r.unreadMessages;return e.jsxs("div",{className:"min-h-screen bg-background text-foreground",children:[e.jsx(Ce,{}),e.jsxs("main",{className:"container py-12 md:py-16",children:[e.jsxs("div",{className:"flex items-start justify-between gap-6 flex-wrap",children:[e.jsxs("div",{children:[e.jsx("p",{className:"font-mono-label text-accent",children:"Administratör"}),e.jsx("h1",{className:"mt-2 font-display text-4xl md:text-5xl tracking-tight",children:"Backend"}),e.jsxs("p",{className:"mt-3 text-muted-foreground",children:["Inloggad som ",e.jsx("span",{className:"text-foreground",children:t?.email})]})]}),e.jsxs("div",{className:"flex flex-wrap items-center gap-2 sm:gap-3 w-full md:w-auto",children:[e.jsx(C,{asChild:!0,size:"sm",className:"gap-2 sm:h-10 sm:px-4",children:e.jsxs(L,{to:"/admin/seo-dashboard",children:[e.jsx(G,{className:"h-4 w-4"})," SEO-Dashboard"]})}),e.jsx(C,{asChild:!0,size:"sm",className:"gap-2 sm:h-10 sm:px-4",children:e.jsxs(L,{to:"/admin/all-seo",children:[e.jsx(z,{className:"h-4 w-4"})," ALL SEO"]})}),e.jsx(C,{asChild:!0,size:"sm",className:"gap-2 sm:h-10 sm:px-4",children:e.jsxs(L,{to:"/admin/bast-i-test",children:[e.jsx(H,{className:"h-4 w-4"})," Bäst i test"]})}),e.jsx(C,{asChild:!0,size:"sm",className:"gap-2 sm:h-10 sm:px-4",children:e.jsxs(L,{to:"/admin/lokal-seo",children:[e.jsx(Y,{className:"h-4 w-4"})," Lokal SEO"]})}),m>0&&e.jsxs("div",{className:"inline-flex items-center gap-2 rounded-full border border-destructive/30 bg-destructive/10 px-3 py-1.5 text-sm text-destructive",children:[e.jsxs("span",{className:"relative inline-flex h-2 w-2",children:[e.jsx("span",{className:"absolute inline-flex h-full w-full animate-ping rounded-full bg-destructive opacity-75"}),e.jsx("span",{className:"relative inline-flex h-2 w-2 rounded-full bg-destructive"})]}),e.jsx(xt,{className:"h-4 w-4"}),e.jsxs("span",{className:"font-medium",children:[m," kräver åtgärd"]})]}),e.jsxs(C,{variant:"outline",size:"sm",onClick:s,className:"gap-2 sm:h-10 sm:px-4",children:[e.jsx(De,{className:"h-4 w-4"})," Logga ut"]})]})]}),e.jsx("div",{className:"mt-10",children:e.jsx(At,{})}),e.jsx("div",{className:"mt-8",children:e.jsx(Kt,{})}),e.jsx("div",{className:"mt-8",children:e.jsx(Et,{})}),e.jsxs("div",{className:"mt-12 space-y-12",children:[e.jsxs(E,{title:"Orderhantering",description:"Beställningar, kundärenden och kundkommunikation.",children:[e.jsx(d,{to:"/admin/ordrar",icon:e.jsx(ee,{className:"h-5 w-5"}),title:"Beställningar",description:"Se ordrar, uppdatera status och leveransdatum.",cta:"Hantera beställningar",badgeCount:r.newOrders,badgeLabel:"nya ordrar"}),e.jsx(d,{to:"/admin/meddelanden",icon:e.jsx(ht,{className:"h-5 w-5"}),title:"Meddelanden",description:"Konversationer med kunder.",cta:"Öppna inkorg",badgeCount:r.unreadMessages,badgeLabel:"olästa meddelanden"}),e.jsx(d,{to:"/admin/reklamationer",icon:e.jsx(te,{className:"h-5 w-5"}),title:"Reklamationer",description:"Hantera kundärenden och bilder.",cta:"Se reklamationer",badgeCount:r.openClaims,badgeLabel:"öppna ärenden"}),e.jsx(d,{to:"/admin/oversikt",icon:e.jsx(pe,{className:"h-5 w-5"}),title:"Översikt",description:"Alla ordrar i en lista — flagga ordrar som inte rört sig.",cta:"Öppna översikt"}),e.jsx(d,{to:"/admin/aterbetalningar",icon:e.jsx(ee,{className:"h-5 w-5"}),title:"Återbetalningar",description:"Alla återbetalningar via Stripe — order, belopp, datum och anledning.",cta:"Se återbetalningar"}),e.jsx(d,{to:"/admin/presentkort",icon:e.jsx(Ee,{className:"h-5 w-5"}),title:"Deposition & presentkort",description:"Registrera presentkort eller depositioner som kunden betalat i butiken. Ladda upp PDF, håll koll på saldo och koppla mot ordrar.",cta:"Hantera presentkort"}),e.jsx(d,{to:"/admin/faktafel",icon:e.jsx(te,{className:"h-5 w-5"}),title:"Faktafel-rapporter",description:"Inrapporterade fel om sängmodeller, märken och butiker. Åtgärda automatiskt med AI.",cta:"Hantera rapporter"})]}),e.jsxs(E,{title:"Katalog & produkter",description:"Sortiment, varumärken och produktegenskaper.",children:[e.jsx(d,{to:"/admin/produkter",icon:e.jsx(V,{className:"h-5 w-5"}),title:"Produkter",description:"Sängar, gavlar, ben och bäddmadrasser.",cta:"Hantera produkter"}),e.jsx(d,{to:"/admin/varumarken",icon:e.jsx(H,{className:"h-5 w-5"}),title:"Varumärken",description:"Skapa och redigera varumärken med logotyp och bio.",cta:"Hantera varumärken"}),e.jsx(d,{to:"/admin/leverantorer",icon:e.jsx(q,{className:"h-5 w-5"}),title:"Leverantörer",description:"Fabriker som du beställer från. Används vid utskick av leverantörsorder.",cta:"Hantera leverantörer"}),e.jsx(d,{to:"/admin/boom-artiklar",icon:e.jsx(q,{className:"h-5 w-5"}),title:"BOOM-artiklar",description:"Importerat artikelregister från Kinnabädden (Masterfil). Sök, filtrera och granska.",cta:"Visa artiklar"}),e.jsx(d,{to:"/admin/bildbank",icon:e.jsx(pe,{className:"h-5 w-5"}),title:"Bildbanken",description:"Hantera produktbilder per varumärke. Varje varumärke får en egen flik där du k
31an bulk-uppladda och tagga bilder för konfiguratorn.",cta:"Öppna bildbanken"}),e.jsx(d,{to:"/admin/butiker",icon:e.jsx(ft,{className:"h-5 w-5"}),title:"Butiker & leveransadresser",description:"Hantera dina butiker och webshopar. Markera huvudbutik – välj sedan per order om beställningen ska skickas till kund eller en butik.",cta:"Hantera butiker"}),e.jsx(d,{to:"/admin/hot-products",icon:e.jsx(Oe,{className:"h-5 w-5"}),title:"Hot products",description:"Markera produkter som Hot — visningar, klick, köp och konverteringsgrad per produkt.",cta:"Hantera Hot products"}),e.jsx(d,{to:"/admin/test-winners",icon:e.jsx(H,{className:"h-5 w-5"}),title:"Bäst i test-ram",description:"Svartguld ram för testvinnare. Auto på för 1:a-platserna — stäng av per produkt och se konvertering.",cta:"Hantera Bäst i test-ram"}),e.jsx(d,{to:"/admin/bast-i-test",icon:e.jsx(H,{className:"h-5 w-5"}),title:"Bäst i test",description:"Översikt över sängtestet med snabb redigering av segment och betyg + statistik på klick, konvertering och intäkt.",cta:"Hantera sängtestet"})]}),e.jsxs(E,{title:"Marknadsföring & kampanjer",description:"Erbjudanden, recensioner och retention.",children:[e.jsx(d,{to:"/admin/kampanjer",icon:e.jsx(Le,{className:"h-5 w-5"}),title:"Kampanjer",description:"Aktivera, planera och avsluta kampanjer.",cta:"Hantera kampanjer"}),e.jsx(d,{to:"/admin/recensioner",icon:e.jsx(se,{className:"h-5 w-5"}),title:"Recensioner",description:"Granska och moderera kundrecensioner.",cta:"Se recensioner"}),e.jsx(d,{to:"/admin/totalbetyg",icon:e.jsx(se,{className:"h-5 w-5"}),title:"Totalbetyg",description:"Håll snittet på 4,9 — auto-fix och bulk-postning av recensioner via dummy-konton.",cta:"Hantera totalbetyg"}),e.jsx(d,{to:"/admin/nyhetsbrev",icon:e.jsx(re,{className:"h-5 w-5"}),title:"Nyhetsbrev",description:"Lista och exportera prenumeranter från kassa och konto.",cta:"Se prenumeranter"}),e.jsx(d,{to:"/admin/referrals",icon:e.jsx(Ae,{className:"h-5 w-5"}),title:"Referrals",description:"Värva-en-vän — alla kunders länkar, klick, konverteringar och utbetalningar.",cta:"Öppna referrals"}),e.jsx(d,{to:"/admin/konverteringsfunktioner",icon:e.jsx(z,{className:"h-5 w-5"}),title:"Konverteringsfunktioner",description:"Slå på/av enskilda CRO-knep (sticky CTA, urgency, social proof m.m.) och se statistik på effekten — med vs utan.",cta:"Hantera CRO-funktioner"})]}),e.jsxs(E,{title:"Innehåll & SEO",description:"Sidor, taggar och sökmotoroptimering.",children:[e.jsx(d,{to:"/admin/innehall",icon:e.jsx(Te,{className:"h-5 w-5"}),title:"Innehåll & sidor",description:"Visuell page builder, kategorier, CMS-sidor och SEO.",cta:"Hantera innehåll"}),e.jsx(d,{to:"/admin/taggar",icon:e.jsx(Fe,{className:"h-5 w-5"}),title:"Taggar",description:"Skapa fria SEO-taggar med egna sidor och meta. Filtrerar produkter.",cta:"Hantera taggar"}),e.jsx(d,{to:"/admin/seo-dashboard",icon:e.jsx(G,{className:"h-5 w-5"}),title:"SEO-Dashboard",description:"Alla sidor, kategorier, taggar och produkter med SEO-poäng och konkreta förbättringsförslag.",cta:"Öppna SEO-dashboard"}),e.jsx(d,{to:"/admin/lokal-seo",icon:e.jsx(Y,{className:"h-5 w-5"}),title:"Lokal SEO",description:"Alla 316 stadssidor (Sängbutik {Stad}) med trafik, klick, ordrar och attribuerad intäkt per ort. Sök, filtrera och borra ner per stad.",cta:"Öppna lokal SEO"}),e.jsx(d,{to:"/admin/sitemap-loggar",icon:e.jsx(G,{className:"h-5 w-5"}),title:"Sitemap-uppdateringar",description:"Senaste dagliga refresh, statuskoder, antal URL:er per delsitemap och eventuella fel. Kör manuellt vid behov.",cta:"Visa sitemap-loggar"})]}),e.jsx(E,{title:"Användare",description:"Kundkonton och roller.",children:e.jsx(d,{to:"/admin/anvandare",icon:e.jsx(ke,{className:"h-5 w-5"}),title:"Användare",description:"Se registrerade kunder och hantera roller.",cta:"Se användare"})}),e.jsxs(E,{title:"Analys & statistik",description:"Försäljnings- och beteendedata.",children:[e.jsx(d,{to:"/admin/statistik",icon:e.jsx(ae,{className:"h-5 w-5"}),title:"Statistik",description:"Försäljning, marginal, klick, sidvisningar och tid på sida.",cta:"Öppna dashboard"}),e.jsx(d,{to:"/admin/raporter",icon:e.jsx(ae,{className:"h-5 w-5"}),title:"Rapporter",description:"Dagliga slutrapporter (genereras 23:59) — sök i historik, exportera PDF/CSV och hitta exakt vad som hänt en specifik dag.",cta:"Öppna rapporter"}),e.jsx(d,{to:"/admin/stripe-handelser",icon:e.jsx(kt,{className:"h-5 w-5"}
31),title:"Stripe-händelser",description:"Webhookloggar, session_id och fel för felsökning av betalningar.",cta:"Öppna logg"}),e.jsx(d,{to:"/admin/orderbekraftelser",icon:e.jsx(re,{className:"h-5 w-5"}),title:"Orderbekräftelser",description:"Status per order: skickat, i kö, misslyckat. Skicka om vid behov.",cta:"Öppna vy"}),e.jsx(d,{to:"/admin/leverantorsmail",icon:e.jsx(q,{className:"h-5 w-5"}),title:"Leverantörsmail",description:"Logg över alla leverantörsorder som mailats — order, mottagare, status och PDF-länk.",cta:"Öppna utskickslogg"}),e.jsx(d,{to:"/admin/leverantorsinkorg",icon:e.jsx(vt,{className:"h-5 w-5"}),title:"Leverantörsinkorg",description:"Inkommande svar och bekräftelser från leverantörer — automatiskt kopplade till rätt order via referens.",cta:"Öppna inkorg"})]}),e.jsxs(E,{title:"Inställningar & system",description:"Tema, bolagsinformation och regelefterlevnad.",children:[e.jsx(d,{to:"/admin/meny",icon:e.jsx(Re,{className:"h-5 w-5"}),title:"Meny & Tema",description:"Bygg menyn, undermenyer och globala typsnitt/färger.",cta:"Anpassa meny"}),e.jsx(d,{to:"/admin/installningar",icon:e.jsx(gt,{className:"h-5 w-5"}),title:"Inställningar",description:"Bolag, organisationsnummer, moms, kontakt, adress, logotyp.",cta:"Öppna inställningar"}),e.jsx(d,{to:"/admin/gdpr-cookie",icon:e.jsx(jt,{className:"h-5 w-5"}),title:"GDPR & Cookie",description:"Redigera cookie-banner (texter, länkar, knappar), justera frekvens (var 30:e dag) och se statistik på godkännanden, exits och lästid.",cta:"Hantera cookie-banner"})]})]}),e.jsxs("div",{className:"mt-12 rounded-lg border border-dashed border-border bg-secondary/30 p-6",children:[e.jsx("p",{className:"font-mono-label text-muted-foreground",children:"Nästa steg"}),e.jsx("p",{className:"mt-2 text-sm text-foreground",children:'Säg vilken funktion du vill börja med — t.ex. "låt mig lägga upp sängar i backend" — så bygger jag det.'})]})]}),e.jsx(Ke,{})]})},E=({title:t,description:s,children:r})=>e.jsxs("section",{children:[e.jsx("div",{className:"flex items-end justify-between gap-4 flex-wrap border-b border-border pb-3",children:e.jsxs("div",{children:[e.jsx("h2",{className:"font-display text-2xl tracking-tight",children:t}),s&&e.jsx("p",{className:"mt-1 text-sm text-muted-foreground",children:s})]})}),e.jsx("div",{className:"mt-5 grid gap-4 sm:grid-cols-2 lg:grid-cols-3",children:r})]}),Rt=[{to:"/admin/seo-dashboard",title:"SEO-Dashboard",description:"Alla sidor med SEO-poäng och förbättringsförslag",section:"Innehåll & SEO"},{to:"/admin/all-seo",title:"ALL SEO",description:"Alla domäner och SEO-statistik",section:"Innehåll & SEO"},{to:"/admin/sovrum-export",title:"Flytta till Sovrum.se",description:"Skapa exportfil med produkter och kategorier samt prompt för Sovrum.se-projektet",section:"Inställningar"},{to:"/admin/externa-lankar",title:"Externa länkar",description:"100+ starka domäner med handlingsplan för att få länk",section:"Innehåll & SEO"},{to:"/admin/web-2-0",title:"Web 2.0-strategi",description:"Egenägd länkpyramid: Medium, Reddit, Quora, YouTube m.fl.",section:"Innehåll & SEO"},{to:"/admin/lokal-seo",title:"Lokal SEO",description:"Stadssidor, trafik och intäkt per ort",section:"Innehåll & SEO"},{to:"/admin/sitemap-loggar",title:"Sitemap-uppdateringar",description:"Sitemap-loggar och refresh",section:"Innehåll & SEO"},{to:"/admin/innehall",title:"Innehåll & sidor",description:"Page builder, kategorier, CMS, SEO",section:"Innehåll & SEO"},{to:"/admin/taggar",title:"Taggar",description:"SEO-taggar och egna sidor",section:"Innehåll & SEO"},{to:"/admin/bast-i-test",title:"Bäst i test",description:"Sängtest, segment och betyg",section:"Katalog"},{to:"/admin/produkter",title:"Produkter",description:"Sängar, gavlar, ben, bäddmadrasser",section:"Katalog"},{to:"/admin/underprodukter",title:"Underprodukter",description:"Färdiga sängpaket – ärver pris & info från huvudsängen",section:"Katalog"},{to:"/admin/varumarken",title:"Varumärken",description:"Logotyp och bio",section:"Katalog"},{to:"/admin/leverantorer",title:"Leverantörer",description:"Fabriker och beställningar",section:"Katalog"},{to:"/admin/boom-artiklar",title:"BOOM-artiklar",description:"Artikelregister Kinnabädden",section:"Katalog"},{to:"/admin/butiker",title:"Butiker & leveransadresser",description:"Hantera butiker och webshopar",section:"Katalog"},{to:"/admin/hot-products",title:"Hot products",description:"Markera produkter som Hot",section:"Katalog"},{to:"/admin/test-winners",title:"Bäst i test-ram",description:"Svartguld ram för testvinnare",section:"Katalog"},{to:"/admin/ordrar",title:"Beställningar",description:"Ordrar, status, leveransdatum",section:"Order"},{to:"/admin/meddelanden",title:"Meddelanden",description:"Konversationer med kunder",section:"Order"},{to:"/admin/reklamationer",title:"Reklamationer",description:"Kundärenden och bilder",section:"Order"},{to:"/admin/oversikt",title:"Översikt",description:"Alla ordrar i en lista",section:"Order"},{to:"/admin/aterbetalningar",title:"Återbetalningar",description:"Stripe-återbetalningar",section:"Order"},{to:"/admin/presentkort",title:"Deposition & presentkort",description:"Presentkort, saldon och PDF kopplade till kunder och ordrar",section:"Order"},{to:"/admin/faktafel",title:"Faktafel-rapporter",description:"Inrapporterade fel",section:"Order"},{to:"/admin/kampanjer",title:"Kampanjer",description:"Aktivera och planera kampanjer",section:"Marknadsföring"},{to:"/admin/recensioner",title:"Recensioner",description:"Granska och moderera",section:"Marknadsföring"},{to:"/admin/totalbetyg",title:"Totalbetyg",description:"Håll snittet på 4,9",section:"Marknadsföring"},{to:"/admin/nyhetsbrev",title:"Nyhetsbrev",description:"Prenumeranter",section:"Marknadsföring"}
31,{to:"/admin/referrals",title:"Referrals",description:"Värva-en-vän, klick och utbetalningar",section:"Marknadsföring"},{to:"/admin/konverteringsfunktioner",title:"Konverteringsfunktioner",description:"CRO-knep och statistik",section:"Marknadsföring"},{to:"/admin/anvandare",title:"Användare",description:"Kunder och roller",section:"Användare"},{to:"/admin/statistik",title:"Statistik",description:"Försäljning, marginal, klick",section:"Analys"},{to:"/admin/raporter",title:"Rapporter",description:"Dagliga slutrapporter",section:"Analys"},{to:"/admin/stripe-handelser",title:"Stripe-händelser",description:"Webhookloggar och fel",section:"Analys"},{to:"/admin/orderbekraftelser",title:"Orderbekräftelser",description:"Mailstatus per order",section:"Analys"},{to:"/admin/leverantorsmail",title:"Leverantörsmail",description:"Utskickslogg leverantörsorder",section:"Analys"},{to:"/admin/leverantorsinkorg",title:"Leverantörsinkorg",description:"Svar från leverantörer",section:"Analys"},{to:"/admin/meny",title:"Meny & Tema",description:"Meny, typsnitt, färger",section:"Inställningar"},{to:"/admin/installningar",title:"Inställningar",description:"Bolag, moms, kontakt, logotyp",section:"Inställningar"},{to:"/admin/gdpr-cookie",title:"GDPR & Cookie",description:"Cookie-banner och statistik",section:"Inställningar"}],Kt=()=>{const[t,s]=f.useState(""),[r,m]=f.useState(!1),[i,g]=f.useState(0),c=Pe(),v=f.useRef(null),p=f.useMemo(()=>{const o=t.trim().toLowerCase();return o?Rt.filter(n=>n.title.toLowerCase().includes(o)||n.description.toLowerCase().includes(o)||n.section.toLowerCase().includes(o)).slice(0,8):[]},[t]);f.useEffect(()=>{const o=l=>{v.current&&!v.current.contains(l.target)&&m(!1)},n=l=>{(l.metaKey||l.ctrlKey)&&l.key.toLowerCase()==="k"&&(l.preventDefault(),document.getElementById("admin-panel-search")?.focus())};return document.addEventListener("mousedown",o),document.addEventListener("keydown",n),()=>{document.removeEventListener("mousedown",o),document.removeEventListener("keydown",n)}},[]),f.useEffect(()=>g(0),[t]);const k=o=>{if(!(!r||p.length===0))if(o.key==="ArrowDown")o.preventDefault(),g(n=>(n+1)%p.length);else if(o.key==="ArrowUp")o.preventDefault(),g(n=>(n-1+p.length)%p.length);else if(o.key==="Enter"){o.preventDefault();const n=p[i];n&&(c(n.to),m(!1),s(""))}else o.key==="Escape"&&m(!1)};return e.jsxs("div",{ref:v,className:"relative",children:[e.jsxs("div",{className:"relative",children:[e.jsx(ve,{className:"absolute left-3 top-1/2 -translate-y-1/2 h-4 w-4 text-muted-foreground pointer-events-none"}),e.jsx(Be,{id:"admin-panel-search",value:t,onChange:o=>{s(o.target.value),m(!0)},onFocus:()=>m(!0),onKeyDown:k,placeholder:"Panelsök — sök bland alla backend-paneler (⌘K)",className:"pl-9 h-11"}),e.jsx("span",{className:"hidden sm:inline absolute right-3 top-1/2 -translate-y-1/2 text-[10px] font-mono text-muted-foreground border border-border rounded px-1.5 py-0.5",children:"⌘K"})]}),r&&t.trim()&&e.jsx("div",{className:"absolute z-50 mt-2 w-full rounded-lg border border-border bg-popover shadow-lg overflow-hidden",children:p.length===0?e.jsxs("div",{className:"px-4 py-6 text-sm text-muted-foreground text-center",children:['Inga paneler matchar "',t,'"']}):e.jsx("ul",{className:"max-h-80 overflow-y-auto",children:p.map((o,n)=>e.jsx("li",{children:e.jsxs(L,{to:o.to,onClick:()=>{m(!1),s("")},onMouseEnter:()=>g(n),className:`flex items-start justify-between gap-3 px-4 py-3 border-b border-border last:border-b-0 transition-colors ${n===i?"bg-accent/10":"hover:bg-muted/50"}`,children:[e.jsxs("div",{className:"min-w-0",children:[e.jsx("div",{className:"font-medium text-sm",children:o.title}),e.jsx("div",{className:"text-xs text-muted-foreground truncate",children:o.description})]}),e.jsx("span",{className:"shrink-0 text-[10px] font-mono uppercase tracking-wide text-muted-foreground mt-1",children:o.section})]})},o.to))})})]})},d=({to:t,icon:s,title:r,description:m,cta:i,badgeCount:g=0,badgeLabel:c})=>e.jsxs("div",{className:`relative rounded-lg border bg-card p-6 flex flex-col transition-colors ${g>0?"border-destructive/40":"border-border"}`,children:[g>0&&e.jsx(He,{count:g,className:"absolute -top-2 -right-2"}),e.jsx("div",{className:"inline-flex h-10 w-10 items-center justify-center rounded-full bg-secondary text-foreground",children:s}),e.jsx("h3",{className:"mt-4 font-display text-xl",children:r}),e.jsx("p",{className:"mt-1 text-sm text-muted-foreground flex-1",children:m}),g>0&&c&&e.jsxs("p",{className:"mt-2 text-xs font-medium text-destructive",children:[g," ",c]}),e.jsxs(L,{to:t,className:"mt-5 inline-flex items-center gap-1 text-sm font-medium text-foreground hover:text-accent transition-colors",children:[i," ",e.jsx(je,{className:"h-3.5 w-3.5"})]})]});
31export{hs as default};

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.