@infuro/cms-core 1.0.15 → 1.0.16

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/admin.js CHANGED
@@ -1,13 +1,14 @@
1
1
  "use client";
2
2
 
3
3
  // src/admin/pages/AdminLayout.tsx
4
- import React5, { useEffect as useEffect2, useState as useState2 } from "react";
4
+ import React5, { useEffect as useEffect2, useState as useState3 } from "react";
5
5
  import { useSession as useSession2 } from "next-auth/react";
6
6
  import { useRouter, usePathname as usePathname3 } from "next/navigation";
7
7
  import { Toaster } from "sonner";
8
8
 
9
9
  // src/components/Admin/Header.tsx
10
10
  import { signOut, useSession } from "next-auth/react";
11
+ import { useMemo, useState as useState2 } from "react";
11
12
 
12
13
  // src/components/ui/button.tsx
13
14
  import * as React from "react";
@@ -229,25 +230,44 @@ function useIsMobile() {
229
230
  return !!isMobile;
230
231
  }
231
232
 
233
+ // src/lib/infuro-favicon.ts
234
+ var INFURO_FAVICON_BASE64 = "data:image/x-icon;base64,AAABAAMAEBAAAAEAIABoBAAANgAAACAgAAABACAAKBEAAJ4EAAAwMAAAAQAgAGgmAADGFQAAKAAAABAAAAAgAAAAAQAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8V////bv///7D////R////0f///7D///9u////FQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wL///9s0qun7q9qYv/DkYv/6tfV///+/v///////////////+7///9r////AgAAAAAAAAAAAAAAAP///wL///+Q/////sqcl/+WOzH/ljsx/5c9M//AiYP/+/j4/////////////////v///5D///8CAAAAAAAAAAD///9s/////v/////Oo5//lz00/5Y7Mf+WOzH/ljsx/7Z3cP/9+/v////////////////+////bAAAAAD///8V////7v///////////v39//Tq6f/QqKP/m0U8/5Y7Mf+WOzH/z6ah/////////////////////+7///8V////bv///////////////////////////////+XOy/+ZQTf/ljsx/59MQ//69fX/////////////////////bv///7D/////////////////////////////////////wYyG/5Y7Mf+WOzH/4MTC/////////////////////7D////R//////////////////7+//79/f/+/f3//v39/+DGw/+WOzH/ljsx/82inf/////////////////////R////0f///////////////9Svq/+mWVH/pllR/6ZZUf+iUUj/ljsx/5Y7Mf/KnJf/////////////////////0f///7D////////////////KnJf/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/062p/////////////////////7D///9u////////////////0amk/6FQSP+hUEj/oVBI/6JRSP+mWVH/plpS/+7g3v////////////////////9u////Ff///+7///////////7+/v/9/Pz/9u7t/8SSjP/Dj4r/9ezr//79/f/////////////////////u////FQAAAAD///9s/////v///////////////8OPif+WOzH/ljsx/7+Jgv/////////////////////+////bAAAAAAAAAAA////Av///5D////+//////////+9hH7/ljsx/5Y7Mf+8g3z////////////////+////kP///wIAAAAAAAAAAAAAAAD///8C////bP///+7/////8OTi/7R0bP+zcmr/8OLh///////////u////bP///wIAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8V////bv///7D////R////0f///7D///9u////FQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKAAAACAAAABAAAAAAQAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8C////Hf///0n///95////mf///67///+u////mf///3n///9J////Hf///wIAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8I////Tf///7D////p/////v////////////////////////////////////7////p////sP///03///8IAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8C////Pfjz8r7HlpH7wY2H/86lof/iysf/9e3s///+/v//////////////////////////////////////////+////77///89////AgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////Cf///37////z9Ovq/6BORf+WOzH/ljsx/5Y8Mv+hUEf/v4iC/+rY1v/+/f3///////////////////////////////////////////H///99////CQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wr///+d/////P/////06+r/oE5F/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/m0Q7/8WTjf/38PD///////////////////////////////////////////z///+d////CgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8J////nf////3///////////Tr6v+gTkX/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/61mX//w4+L///////////////////////////////////////////3///+d////CQAAAAAAAAAAAAAAAAAAAAAAAAAA////Av///37////8////////////////9Ovq/6BORf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6daUv/v4uD///////////////////////////////////////////z///9+////AgAAAAAAAAAAAAAAAAAAAAD///89////8//////////////////////48fD/rGRc/5pCOf+YPjT/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6xkXf/37+////////////////////////////////////////////P///89AAAAAAAAAAAAAAAA////CP///77////////////////////////////////7+Pf/8eXj/+DGw/++hn//m0U8/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/8GLhf/9/Pz//////////////////////////////////////////77///8IAAAAAAAAAAD///9N////+/////////////////////////////////////////////////7+/v/p1tP/rGRd/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/mkI4/+XPzf//////////////////////////////////////////+////00AAAAA////Av///7D////////////////////////////////////////////////////////////////06+r/r2pi/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/tndw//38+///////////////////////////////////////////sP///wL///8d////6f/////////////////////////////////////////////////////////////////////x5eP/olJJ/5Y7Mf+WOzH/ljsx/5Y7Mf+aQjn/7dza///////////////////////////////////////////p////Hf///0n////+///////////////////////////////////////////////////////////////////////////Ur6v/ljwy/5Y7Mf+WOzH/ljsx/5Y7Mf/Oo5////////////////////////////////////////////7///9J////ef////////////////////////////////////////////////////////////////////////////////fw7/+jVEv/ljsx/5Y7Mf+WOzH/ljsx/7Nxav///////////////////////////////////////////////3n///+Z/////////////////////////////////////////////////////////////////////////////////////7yCfP+WOzH/ljsx/5Y7Mf+WOzH/pllQ//r29f//////////////////////////////////////////mf///67///////////////////////////////////////////79/f/9/Pz//fz8//38/P/9/Pz//fz8//38/P/9/Pz/yZuW/5Y7Mf+WOzH/ljsx/5Y7Mf+gT0b/9evr//////////////////////////////////////////+u////rv/////////////////////////////////////69vb/wo2I/7Z3cf+2d3H/tndx/7Z3cf+2d3H/tndx/7Z3cf+lV0//ljsx/5Y7Mf+WOzH/ljsx/6BORf/06+r//////////////////////////////////////////67///+Z//////////////////////////////////////Tr6v+gTkX/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/oE5F//Tr6v//////////////////////////////////////////mf///3n/////////////////////////////////////9Ovq/6BORf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+lVk7/+fPz//////////////////////////////////////////95////Sf////7////////////////////////////////06+r/oE5F/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/7FuZ////v7//////////////////////////////////////v///0n///8d////6f////////////////////////////////Tr6v+gTkX/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/zKCb///////////////////////////////////////////p////Hf///wL///+w////////////////////////////////+PLx/7d4cf+tZl//rWZf/61mX/+tZl//rWZf/61mX/+tZl//rmdg/7Z3cP+2d3H/tndx/7h7df/w4uH//////////////////////////////////////////7D///8CAAAAAP///03////7/////////////////////////////////Pv6//z6+f/8+vn//Pr5//z6+f/z6un/48zJ/+LKx//y5+b//fz8//38/P/9/Pz//fz8///////////////////////////////////////////7////TQAAAAAAAAAA////CP///77/////////////////////////////////////////////////////4MXC/6VXTv+WPDL/ljwy/6JRSP/aubb///7+/////////////////////////////////////////////////////77///8IAAAAAAAAAAAAAAAA////Pf////P///////////////////////////////////////////Xs6/+jU0r/ljsx/5Y7Mf+WOzH/ljsx/59MQv/w5OL////////////////////////////////////////////////z////PQAAAAAAAAAAAAAAAAAAAAD///8C////fv////z/////////////////////////////////////3sK//5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/9m5tf///////////////////////////////////////////P///37///8CAAAAAAAAAAAAAAAAAAAAAAAAAAD///8J////nf////3////////////////////////////////ZuLX/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/17Sw//////////////////////////////////////3///+d////CQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8K////nf////z//////////////////////////+zc2v+aQzn/ljsx/5Y7Mf+WOzH/ljsx/5pDOf/r2tj////////////////////////////////8////nf///woAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8J////fv////P//////////////////////v39/8eYkv+YPjT/ljsx/5Y7Mf+YPjT/xpSP//79/f//////////////////////////8////37///8JAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8C////Pf///77////7/////////////////fv6/+DEwf/Ekoz/wY2H/97Bvv/8+vr/////////////////////+////77///89////AgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////CP///03///+w////6f////7////////////////////////////////////+////6f///7D///9N////CAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wL///8d////Sf///3n///+Z////rv///67///+Z////ef///0n///8d////AgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKAAAADAAAABgAAAAAQAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8E////DP///xr///80////Rv///1n///9q////gP///4D///9q////Wf///0b///80////Gv///wz///8EAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////CP///y7///9g////lP///7v////V////6P////r////8/////P////z////8////+v///+j////V////u////5T///9g////Lv///wgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wf///81////k////8/////v////+v////////////////////////////////////////////////////////////////////r////v////z////5P///81////BwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8G////Kv37+3zt3Nrd27y5/Nm6t//fxMH/59LQ//Dk4v/48vH//fv6//////////////////////////////////////////////////////////////////////z////d////fP///yr///8GAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///xH///9g////wvz5+ffNop3+m0U8/5c+NP+cRz7/pFVN/65oYP+8gnv/0qun/+jU0v/59fT//v7+///////////////////////////////////////////////////////////+////9////8L///9f////EQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////GP///4n////m/////fv4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+XPTT/m0Q6/6ZaUf/BjIX/6NXT//z5+f////////////////////////////////////////////////////////////////3////k////if///xgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wH///8i////pP////f///////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+XPjT/oVFI/8yhnP/x5OP//vz8////////////////////////////////////////////////////////////////9////6T///8i////AQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///yL///+d////8/////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5tEOv+3eHL/48rH//37+/////////////////////////////////////////////////////////////////P///+d////IgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////GP///6T////z//////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+YPjT/qFxT/9y+uv/9+vr////////////////////////////////////////////////////////////////z////pP///xgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8R////if////f///////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsy/6NUS//Yt7P//Pn4////////////////////////////////////////////////////////////////9////4n///8RAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wb///9g////5v////////////////////////////////v4+P/KnZj/mUI4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5c8Mv+pXlb/38PA//38/P///////////////////////////////////////////////////////////////+b///9g////BgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///yr////C/////f////////////////////////////////38+//dwLz/qF1V/51JP/+bRDv/mD40/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+XPTP/qWBY/+vZ2P///v7///////////////////////////////////////////////////////////3////C////KgAAAAAAAAAAAAAAAAAAAAAAAAAA////B////3z////3///////////////////////////////////////////9+/r/9/Dv/+zc2f/dwLz/x5iT/7BrY/+eS0H/lz0z/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/lzwy/7d6c//06un////////////////////////////////////////////////////////////////3////fP///wcAAAAAAAAAAAAAAAAAAAAA////Nf///93////+//////////////////////////////////////////////////////7+/v/+/v7//fz8//Hm5f/XtLH/s3Fq/5lCOP+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/51JP//Sq6b//Pn5///////////////////////////////////////////////////////////+////3f///zUAAAAAAAAAAAAAAAD///8I////k/////z////////////////////////////////////////////////////////////////////////////////9+/v/8eTj/8aVkP+dRz7/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5c8Mv+vamL/7uDf/////////////////////////////////////////////////////////////////P///5P///8IAAAAAAAAAAD///8u////z/////////////////////////////////////////////////////////////////////////////////////////////////fx8P/ImZP/nUg//5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+ZQTj/0qyo//38/P///////////////////////////////////////////////////////////////8////8uAAAAAP///wT///9g////7//////////////////////////////////////////////////////////////////////////////////////////////////////07Or/xJGL/5hAN/+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/rGRd//Tq6P///////////////////////////////////////////////////////////////+////9g////BP///wz///+U////+v////////////////////////////////////////////////////////////////////////////////////////////////////////7/8+jm/7Nya/+WPDP/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/mkQ7/9m3s////v7///////////////////////////////////////////////////////////r///+U////DP///xr///+7/////////////////////////////////////////////////////////////////////////////////////////////////////////////////v7+/+HHxP+hUEf/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljwy/7yBe//69/f///////////////////////////////////////////////////////////////+7////Gv///zT////V//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////bu7f+7gHr/mD40/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6xkXP/u4N/////////////////////////////////////////////////////////////////V////NP///0b////o//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////38/P/XtK//nEY9/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6BNRP/iycb////////////////////////////////////////////////////////////////o////Rv///1n////6///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////o1NL/pVhQ/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5xGPP/Yt7L//v39///////////////////////////////////////////////////////////6////Wf///2r////8///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////06un/sW1m/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5pDOf/PpKD//Pr5///////////////////////////////////////////////////////////8////av///4D////8/////////////////////////////////////////////////////////////v7//fv7//37+v/9+/r//fv6//37+v/9+/r//fv6//37+v/9+/r//fv6//37+v/06un/snBp/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5lBOP/KnJj/+/j4///////////////////////////////////////////////////////////8////gP///4D////8//////////////////////////////////////////////////////79/f/s3Nr/z6ej/8uemv/Lnpr/y56a/8uemv/Lnpr/y56a/8uemv/Lnpr/y56a/8uemv/GlI//o1VM/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5lBOP/KnJf/+/j4///////////////////////////////////////////////////////////8////gP///2r////8//////////////////////////////////////////////////////z5+f/Nop3/m0Q7/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5lBOP/KnJf/+/j4///////////////////////////////////////////////////////////8////av///1n////6//////////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5lCOP/KnZj/+/j4///////////////////////////////////////////////////////////6////Wf///0b////o//////////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5pDOv/Qp6P//Pr6///////////////////////////////////////////////////////////o////Rv///zT////V//////////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/51IP//bvbr//v7+///////////////////////////////////////////////////////////V////NP///xr///+7//////////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6RVTf/n0c////////////////////////////////////////////////////////////////+7////Gv///wz///+U////+v////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/7FuZ//z6ej///////////////////////////////////////////////////////////r///+U////DP///wT///9g////7/////////////////////////////////////////////////z4+P/LnZj/mkI5/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/mUE3/8mblf/9+/r//////////////////////////////////////////////////////////+////9g////BAAAAAD///8u////z/////////////////////////////////////////////////38/P/iycb/v4iC/7yCfP+8gnz/vIJ8/7yCfP+8gnz/vIJ8/7yCfP+8gnz/vIJ8/7yCfP+8gnz/voR+/8qcl//Lnpr/y56a/8uemv/Lnpr/zqOf//Hl5P///v7//////////////////////////////////////////////////////////8////8uAAAAAAAAAAD///8I////k/////z////////////////////////////////////////////////9/Pz/+vf2//r39v/69/b/+vf2//r39v/69/b/+vf2//j08//07Ov/7+Df/+7f3v/z6+n/+PPy//z6+v/9+/r//fv6//37+v/9+/r//fv7///+/v///////////////////////////////////////////////////////////P///5P///8IAAAAAAAAAAAAAAAA////Nf///93////+/////////////////////////////////////////////////////////////////////////////v7/9u7t/9i3s/++hn//sW1m/7BsZf+7gnv/066q//Ln5v/+/v7////////////////////////////////////////////////////////////////////////////////+////3f///zUAAAAAAAAAAAAAAAAAAAAA////B////3z////3///////////////////////////////////////////////////////////////////////////17Ov/wo6I/55KQf+XPjT/ljsx/5Y7Mf+XPTP/nEY9/7uBe//x5eP////////////////////////////////////////////////////////////////////////////////3////fP///wcAAAAAAAAAAAAAAAAAAAAAAAAAAP///yr////C/////f////////////////////////////////////////////////////////////////37+//UsKz/nUg//5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5tEO//No57/+/j4//////////////////////////////////////////////////////////////////////3////C////KgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wb///9g////5v////////////////////////////////////////////////////////////////bv7/+5fHb/lz0z/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y8Mv+ycGj/8ujm/////////////////////////////////////////////////////////////////////+b///9g////BgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8R////if////f//////////////////////////////////////////////////////////+3e3P+qYlr/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+oXVT/6tnX////////////////////////////////////////////////////////////////9////4n///8RAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////GP///6T////z/////////////////////////////////////////////////////+vZ1/+oXVT/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+nWlL/6dbU///////////////////////////////////////////////////////////z////pP///xgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///yL///+d////8/////////////////////////////////////////////////Hm5f+wa2T/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+uaGD/8OPh//////////////////////////////////////////////////////P///+d////IgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wH///8i////pP////f///////////////////////////////////////////r19P/CjYf/mD81/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5g/Nf/BjIb/+fTz////////////////////////////////////////////////9////6T///8i////AQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////GP///4n////m/////f////////////////////////////////7+/v/m0M7/qmFZ/5c9M/+WOzH/ljsx/5Y7Mf+WOzH/lz0z/6leV//lz8z//v7+//////////////////////////////////////3////m////if///xgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///xH///9g////wv////f////+///////////////////////////8+vr/4snG/7d4cf+iUUj/mUA3/5c+NP+gTkT/tXVu/+DFw//8+fn////////////////////////////////+////9////8L///9g////EQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8G////Kv///3z////d/////P///////////////////////////v38//Tr6v/kzcv/2726/9m6t//jysf/8uno//78/P////////////////////////////////z////d////fP///yr///8GAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wf///81////k////8/////v////+v////////////////////////////////////////////////////////////////////r////v////z////5P///81////BwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////CP///y7///9g////lP///7v////V////6P////r////8/////P////z////8////+v///+j////V////u////5T///9g////Lv///wgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8E////DP///xr///80////Rv///1n///9q////gP///4D///9q////Wf///0b///80////Gv///wz///8EAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA==";
235
+
232
236
  // src/components/Admin/Header.tsx
233
237
  import { Fragment, jsx as jsx3, jsxs as jsxs2 } from "react/jsx-runtime";
238
+ var DEFAULT_ADMIN_LOGO = "/images/logo/logo.png";
234
239
  function AdminHeader() {
235
240
  const { data: session } = useSession();
236
241
  const isMobile = useIsMobile();
242
+ const configuredLogo = process.env.NEXT_PUBLIC_ADMIN_LOGO_URL || DEFAULT_ADMIN_LOGO;
243
+ const [logoSrc, setLogoSrc] = useState2(configuredLogo);
244
+ const [logoFailed, setLogoFailed] = useState2(false);
245
+ const isDataLogo = useMemo(() => logoSrc.startsWith("data:"), [logoSrc]);
237
246
  const handleLogout = () => {
238
247
  signOut({ callbackUrl: "/admin/signin" });
239
248
  };
240
249
  return /* @__PURE__ */ jsx3("header", { className: "bg-white border-b border-gray-200 px-4 py-2", children: /* @__PURE__ */ jsxs2("div", { className: "flex items-center justify-between", children: [
241
- /* @__PURE__ */ jsx3("div", { className: "flex items-center max-h-9 shrink-0", children: /* @__PURE__ */ jsx3(
250
+ /* @__PURE__ */ jsx3("div", { className: "flex items-center max-h-9 shrink-0", children: !logoFailed ? /* @__PURE__ */ jsx3(
242
251
  Image,
243
252
  {
244
- src: process.env.NEXT_PUBLIC_ADMIN_LOGO_URL || "/images/logo/logo.png",
253
+ src: logoSrc,
245
254
  alt: "Admin",
246
255
  width: 120,
247
256
  height: 34,
248
- className: "max-h-9 w-auto object-contain object-left"
257
+ className: "max-h-9 w-auto object-contain object-left",
258
+ unoptimized: isDataLogo,
259
+ onError: () => {
260
+ if (logoSrc !== DEFAULT_ADMIN_LOGO) {
261
+ setLogoSrc(DEFAULT_ADMIN_LOGO);
262
+ return;
263
+ }
264
+ setLogoFailed(true);
265
+ }
249
266
  }
250
- ) }),
267
+ ) : /* @__PURE__ */ jsxs2("div", { className: "flex items-center gap-2", children: [
268
+ /* @__PURE__ */ jsx3(Image, { src: INFURO_FAVICON_BASE64, alt: "Infuro", width: 18, height: 18, unoptimized: true }),
269
+ /* @__PURE__ */ jsx3("span", { className: "text-sm font-semibold text-gray-800", children: "Infuro" })
270
+ ] }) }),
251
271
  /* @__PURE__ */ jsx3("div", { className: "flex items-center space-x-3", children: /* @__PURE__ */ jsxs2(DropdownMenu, { children: [
252
272
  /* @__PURE__ */ jsx3(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxs2(
253
273
  Button,
@@ -330,11 +350,8 @@ var defaultValue = {
330
350
  };
331
351
  var AdminConfigContext = createContext(defaultValue);
332
352
 
333
- // src/lib/infuro-favicon.ts
334
- var INFURO_FAVICON_BASE64 = "data:image/x-icon;base64,AAABAAMAEBAAAAEAIABoBAAANgAAACAgAAABACAAKBEAAJ4EAAAwMAAAAQAgAGgmAADGFQAAKAAAABAAAAAgAAAAAQAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8V////bv///7D////R////0f///7D///9u////FQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wL///9s0qun7q9qYv/DkYv/6tfV///+/v///////////////+7///9r////AgAAAAAAAAAAAAAAAP///wL///+Q/////sqcl/+WOzH/ljsx/5c9M//AiYP/+/j4/////////////////v///5D///8CAAAAAAAAAAD///9s/////v/////Oo5//lz00/5Y7Mf+WOzH/ljsx/7Z3cP/9+/v////////////////+////bAAAAAD///8V////7v///////////v39//Tq6f/QqKP/m0U8/5Y7Mf+WOzH/z6ah/////////////////////+7///8V////bv///////////////////////////////+XOy/+ZQTf/ljsx/59MQ//69fX/////////////////////bv///7D/////////////////////////////////////wYyG/5Y7Mf+WOzH/4MTC/////////////////////7D////R//////////////////7+//79/f/+/f3//v39/+DGw/+WOzH/ljsx/82inf/////////////////////R////0f///////////////9Svq/+mWVH/pllR/6ZZUf+iUUj/ljsx/5Y7Mf/KnJf/////////////////////0f///7D////////////////KnJf/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/062p/////////////////////7D///9u////////////////0amk/6FQSP+hUEj/oVBI/6JRSP+mWVH/plpS/+7g3v////////////////////9u////Ff///+7///////////7+/v/9/Pz/9u7t/8SSjP/Dj4r/9ezr//79/f/////////////////////u////FQAAAAD///9s/////v///////////////8OPif+WOzH/ljsx/7+Jgv/////////////////////+////bAAAAAAAAAAA////Av///5D////+//////////+9hH7/ljsx/5Y7Mf+8g3z////////////////+////kP///wIAAAAAAAAAAAAAAAD///8C////bP///+7/////8OTi/7R0bP+zcmr/8OLh///////////u////bP///wIAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8V////bv///7D////R////0f///7D///9u////FQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKAAAACAAAABAAAAAAQAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8C////Hf///0n///95////mf///67///+u////mf///3n///9J////Hf///wIAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8I////Tf///7D////p/////v////////////////////////////////////7////p////sP///03///8IAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8C////Pfjz8r7HlpH7wY2H/86lof/iysf/9e3s///+/v//////////////////////////////////////////+////77///89////AgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////Cf///37////z9Ovq/6BORf+WOzH/ljsx/5Y8Mv+hUEf/v4iC/+rY1v/+/f3///////////////////////////////////////////H///99////CQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wr///+d/////P/////06+r/oE5F/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/m0Q7/8WTjf/38PD///////////////////////////////////////////z///+d////CgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8J////nf////3///////////Tr6v+gTkX/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/61mX//w4+L///////////////////////////////////////////3///+d////CQAAAAAAAAAAAAAAAAAAAAAAAAAA////Av///37////8////////////////9Ovq/6BORf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6daUv/v4uD///////////////////////////////////////////z///9+////AgAAAAAAAAAAAAAAAAAAAAD///89////8//////////////////////48fD/rGRc/5pCOf+YPjT/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6xkXf/37+////////////////////////////////////////////P///89AAAAAAAAAAAAAAAA////CP///77////////////////////////////////7+Pf/8eXj/+DGw/++hn//m0U8/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/8GLhf/9/Pz//////////////////////////////////////////77///8IAAAAAAAAAAD///9N////+/////////////////////////////////////////////////7+/v/p1tP/rGRd/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/mkI4/+XPzf//////////////////////////////////////////+////00AAAAA////Av///7D////////////////////////////////////////////////////////////////06+r/r2pi/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/tndw//38+///////////////////////////////////////////sP///wL///8d////6f/////////////////////////////////////////////////////////////////////x5eP/olJJ/5Y7Mf+WOzH/ljsx/5Y7Mf+aQjn/7dza///////////////////////////////////////////p////Hf///0n////+///////////////////////////////////////////////////////////////////////////Ur6v/ljwy/5Y7Mf+WOzH/ljsx/5Y7Mf/Oo5////////////////////////////////////////////7///9J////ef////////////////////////////////////////////////////////////////////////////////fw7/+jVEv/ljsx/5Y7Mf+WOzH/ljsx/7Nxav///////////////////////////////////////////////3n///+Z/////////////////////////////////////////////////////////////////////////////////////7yCfP+WOzH/ljsx/5Y7Mf+WOzH/pllQ//r29f//////////////////////////////////////////mf///67///////////////////////////////////////////79/f/9/Pz//fz8//38/P/9/Pz//fz8//38/P/9/Pz/yZuW/5Y7Mf+WOzH/ljsx/5Y7Mf+gT0b/9evr//////////////////////////////////////////+u////rv/////////////////////////////////////69vb/wo2I/7Z3cf+2d3H/tndx/7Z3cf+2d3H/tndx/7Z3cf+lV0//ljsx/5Y7Mf+WOzH/ljsx/6BORf/06+r//////////////////////////////////////////67///+Z//////////////////////////////////////Tr6v+gTkX/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/oE5F//Tr6v//////////////////////////////////////////mf///3n/////////////////////////////////////9Ovq/6BORf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+lVk7/+fPz//////////////////////////////////////////95////Sf////7////////////////////////////////06+r/oE5F/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/7FuZ////v7//////////////////////////////////////v///0n///8d////6f////////////////////////////////Tr6v+gTkX/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/zKCb///////////////////////////////////////////p////Hf///wL///+w////////////////////////////////+PLx/7d4cf+tZl//rWZf/61mX/+tZl//rWZf/61mX/+tZl//rmdg/7Z3cP+2d3H/tndx/7h7df/w4uH//////////////////////////////////////////7D///8CAAAAAP///03////7/////////////////////////////////Pv6//z6+f/8+vn//Pr5//z6+f/z6un/48zJ/+LKx//y5+b//fz8//38/P/9/Pz//fz8///////////////////////////////////////////7////TQAAAAAAAAAA////CP///77/////////////////////////////////////////////////////4MXC/6VXTv+WPDL/ljwy/6JRSP/aubb///7+/////////////////////////////////////////////////////77///8IAAAAAAAAAAAAAAAA////Pf////P///////////////////////////////////////////Xs6/+jU0r/ljsx/5Y7Mf+WOzH/ljsx/59MQv/w5OL////////////////////////////////////////////////z////PQAAAAAAAAAAAAAAAAAAAAD///8C////fv////z/////////////////////////////////////3sK//5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/9m5tf///////////////////////////////////////////P///37///8CAAAAAAAAAAAAAAAAAAAAAAAAAAD///8J////nf////3////////////////////////////////ZuLX/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/17Sw//////////////////////////////////////3///+d////CQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8K////nf////z//////////////////////////+zc2v+aQzn/ljsx/5Y7Mf+WOzH/ljsx/5pDOf/r2tj////////////////////////////////8////nf///woAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8J////fv////P//////////////////////v39/8eYkv+YPjT/ljsx/5Y7Mf+YPjT/xpSP//79/f//////////////////////////8////37///8JAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8C////Pf///77////7/////////////////fv6/+DEwf/Ekoz/wY2H/97Bvv/8+vr/////////////////////+////77///89////AgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////CP///03///+w////6f////7////////////////////////////////////+////6f///7D///9N////CAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wL///8d////Sf///3n///+Z////rv///67///+Z////ef///0n///8d////AgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKAAAADAAAABgAAAAAQAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8E////DP///xr///80////Rv///1n///9q////gP///4D///9q////Wf///0b///80////Gv///wz///8EAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////CP///y7///9g////lP///7v////V////6P////r////8/////P////z////8////+v///+j////V////u////5T///9g////Lv///wgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wf///81////k////8/////v////+v////////////////////////////////////////////////////////////////////r////v////z////5P///81////BwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8G////Kv37+3zt3Nrd27y5/Nm6t//fxMH/59LQ//Dk4v/48vH//fv6//////////////////////////////////////////////////////////////////////z////d////fP///yr///8GAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///xH///9g////wvz5+ffNop3+m0U8/5c+NP+cRz7/pFVN/65oYP+8gnv/0qun/+jU0v/59fT//v7+///////////////////////////////////////////////////////////+////9////8L///9f////EQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////GP///4n////m/////fv4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+XPTT/m0Q6/6ZaUf/BjIX/6NXT//z5+f////////////////////////////////////////////////////////////////3////k////if///xgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wH///8i////pP////f///////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+XPjT/oVFI/8yhnP/x5OP//vz8////////////////////////////////////////////////////////////////9////6T///8i////AQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///yL///+d////8/////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5tEOv+3eHL/48rH//37+/////////////////////////////////////////////////////////////////P///+d////IgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////GP///6T////z//////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+YPjT/qFxT/9y+uv/9+vr////////////////////////////////////////////////////////////////z////pP///xgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8R////if////f///////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsy/6NUS//Yt7P//Pn4////////////////////////////////////////////////////////////////9////4n///8RAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wb///9g////5v////////////////////////////////v4+P/KnZj/mUI4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5c8Mv+pXlb/38PA//38/P///////////////////////////////////////////////////////////////+b///9g////BgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///yr////C/////f////////////////////////////////38+//dwLz/qF1V/51JP/+bRDv/mD40/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+XPTP/qWBY/+vZ2P///v7///////////////////////////////////////////////////////////3////C////KgAAAAAAAAAAAAAAAAAAAAAAAAAA////B////3z////3///////////////////////////////////////////9+/r/9/Dv/+zc2f/dwLz/x5iT/7BrY/+eS0H/lz0z/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/lzwy/7d6c//06un////////////////////////////////////////////////////////////////3////fP///wcAAAAAAAAAAAAAAAAAAAAA////Nf///93////+//////////////////////////////////////////////////////7+/v/+/v7//fz8//Hm5f/XtLH/s3Fq/5lCOP+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/51JP//Sq6b//Pn5///////////////////////////////////////////////////////////+////3f///zUAAAAAAAAAAAAAAAD///8I////k/////z////////////////////////////////////////////////////////////////////////////////9+/v/8eTj/8aVkP+dRz7/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5c8Mv+vamL/7uDf/////////////////////////////////////////////////////////////////P///5P///8IAAAAAAAAAAD///8u////z/////////////////////////////////////////////////////////////////////////////////////////////////fx8P/ImZP/nUg//5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+ZQTj/0qyo//38/P///////////////////////////////////////////////////////////////8////8uAAAAAP///wT///9g////7//////////////////////////////////////////////////////////////////////////////////////////////////////07Or/xJGL/5hAN/+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/rGRd//Tq6P///////////////////////////////////////////////////////////////+////9g////BP///wz///+U////+v////////////////////////////////////////////////////////////////////////////////////////////////////////7/8+jm/7Nya/+WPDP/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/mkQ7/9m3s////v7///////////////////////////////////////////////////////////r///+U////DP///xr///+7/////////////////////////////////////////////////////////////////////////////////////////////////////////////////v7+/+HHxP+hUEf/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljwy/7yBe//69/f///////////////////////////////////////////////////////////////+7////Gv///zT////V//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////bu7f+7gHr/mD40/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6xkXP/u4N/////////////////////////////////////////////////////////////////V////NP///0b////o//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////38/P/XtK//nEY9/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6BNRP/iycb////////////////////////////////////////////////////////////////o////Rv///1n////6///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////o1NL/pVhQ/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5xGPP/Yt7L//v39///////////////////////////////////////////////////////////6////Wf///2r////8///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////06un/sW1m/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5pDOf/PpKD//Pr5///////////////////////////////////////////////////////////8////av///4D////8/////////////////////////////////////////////////////////////v7//fv7//37+v/9+/r//fv6//37+v/9+/r//fv6//37+v/9+/r//fv6//37+v/06un/snBp/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5lBOP/KnJj/+/j4///////////////////////////////////////////////////////////8////gP///4D////8//////////////////////////////////////////////////////79/f/s3Nr/z6ej/8uemv/Lnpr/y56a/8uemv/Lnpr/y56a/8uemv/Lnpr/y56a/8uemv/GlI//o1VM/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5lBOP/KnJf/+/j4///////////////////////////////////////////////////////////8////gP///2r////8//////////////////////////////////////////////////////z5+f/Nop3/m0Q7/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5lBOP/KnJf/+/j4///////////////////////////////////////////////////////////8////av///1n////6//////////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5lCOP/KnZj/+/j4///////////////////////////////////////////////////////////6////Wf///0b////o//////////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5pDOv/Qp6P//Pr6///////////////////////////////////////////////////////////o////Rv///zT////V//////////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/51IP//bvbr//v7+///////////////////////////////////////////////////////////V////NP///xr///+7//////////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/6RVTf/n0c////////////////////////////////////////////////////////////////+7////Gv///wz///+U////+v////////////////////////////////////////////////v4+P/KnJf/mUE4/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/7FuZ//z6ej///////////////////////////////////////////////////////////r///+U////DP///wT///9g////7/////////////////////////////////////////////////z4+P/LnZj/mkI5/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/ljwy/5Y8Mv+WPDL/mUE3/8mblf/9+/r//////////////////////////////////////////////////////////+////9g////BAAAAAD///8u////z/////////////////////////////////////////////////38/P/iycb/v4iC/7yCfP+8gnz/vIJ8/7yCfP+8gnz/vIJ8/7yCfP+8gnz/vIJ8/7yCfP+8gnz/voR+/8qcl//Lnpr/y56a/8uemv/Lnpr/zqOf//Hl5P///v7//////////////////////////////////////////////////////////8////8uAAAAAAAAAAD///8I////k/////z////////////////////////////////////////////////9/Pz/+vf2//r39v/69/b/+vf2//r39v/69/b/+vf2//j08//07Ov/7+Df/+7f3v/z6+n/+PPy//z6+v/9+/r//fv6//37+v/9+/r//fv7///+/v///////////////////////////////////////////////////////////P///5P///8IAAAAAAAAAAAAAAAA////Nf///93////+/////////////////////////////////////////////////////////////////////////////v7/9u7t/9i3s/++hn//sW1m/7BsZf+7gnv/066q//Ln5v/+/v7////////////////////////////////////////////////////////////////////////////////+////3f///zUAAAAAAAAAAAAAAAAAAAAA////B////3z////3///////////////////////////////////////////////////////////////////////////17Ov/wo6I/55KQf+XPjT/ljsx/5Y7Mf+XPTP/nEY9/7uBe//x5eP////////////////////////////////////////////////////////////////////////////////3////fP///wcAAAAAAAAAAAAAAAAAAAAAAAAAAP///yr////C/////f////////////////////////////////////////////////////////////////37+//UsKz/nUg//5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5tEO//No57/+/j4//////////////////////////////////////////////////////////////////////3////C////KgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wb///9g////5v////////////////////////////////////////////////////////////////bv7/+5fHb/lz0z/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y8Mv+ycGj/8ujm/////////////////////////////////////////////////////////////////////+b///9g////BgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8R////if////f//////////////////////////////////////////////////////////+3e3P+qYlr/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+oXVT/6tnX////////////////////////////////////////////////////////////////9////4n///8RAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////GP///6T////z/////////////////////////////////////////////////////+vZ1/+oXVT/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+nWlL/6dbU///////////////////////////////////////////////////////////z////pP///xgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///yL///+d////8/////////////////////////////////////////////////Hm5f+wa2T/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5Y7Mf+uaGD/8OPh//////////////////////////////////////////////////////P///+d////IgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wH///8i////pP////f///////////////////////////////////////////r19P/CjYf/mD81/5Y7Mf+WOzH/ljsx/5Y7Mf+WOzH/ljsx/5g/Nf/BjIb/+fTz////////////////////////////////////////////////9////6T///8i////AQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////GP///4n////m/////f////////////////////////////////7+/v/m0M7/qmFZ/5c9M/+WOzH/ljsx/5Y7Mf+WOzH/lz0z/6leV//lz8z//v7+//////////////////////////////////////3////m////if///xgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///xH///9g////wv////f////+///////////////////////////8+vr/4snG/7d4cf+iUUj/mUA3/5c+NP+gTkT/tXVu/+DFw//8+fn////////////////////////////////+////9////8L///9g////EQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8G////Kv///3z////d/////P///////////////////////////v38//Tr6v/kzcv/2726/9m6t//jysf/8uno//78/P////////////////////////////////z////d////fP///yr///8GAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP///wf///81////k////8/////v////+v////////////////////////////////////////////////////////////////////r////v////z////5P///81////BwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA////CP///y7///9g////lP///7v////V////6P////r////8/////P////z////8////+v///+j////V////u////5T///9g////Lv///wgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD///8E////DP///xr///80////Rv///1n///9q////gP///4D///9q////Wf///0b///80////Gv///wz///8EAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA==";
335
-
336
353
  // src/lib/cms-version.ts
337
- var CMS_VERSION = true ? "1.0.15" : "0.0.0";
354
+ var CMS_VERSION = true ? "1.0.16" : "0.0.0";
338
355
 
339
356
  // src/components/Admin/Sidebar.tsx
340
357
  import { jsx as jsx4, jsxs as jsxs3 } from "react/jsx-runtime";
@@ -743,8 +760,8 @@ function AdminLayoutInner({ children }) {
743
760
  const { data: session, status } = useSession2();
744
761
  const router = useRouter();
745
762
  const pathname = usePathname3();
746
- const [loadingTimeout, setLoadingTimeout] = useState2(false);
747
- const [moreSheetOpen, setMoreSheetOpen] = useState2(false);
763
+ const [loadingTimeout, setLoadingTimeout] = useState3(false);
764
+ const [moreSheetOpen, setMoreSheetOpen] = useState3(false);
748
765
  const isMobile = useIsMobile();
749
766
  useAdminViewSettings();
750
767
  const isPublicPath = PUBLIC_ADMIN_PATHS.includes(pathname);
@@ -806,7 +823,7 @@ function AdminLayoutInner({ children }) {
806
823
  ] });
807
824
  }
808
825
  function useResolvedTheme(theme, themeRegistry) {
809
- const [activeThemeId, setActiveThemeId] = useState2(null);
826
+ const [activeThemeId, setActiveThemeId] = useState3(null);
810
827
  useEffect2(() => {
811
828
  if (!themeRegistry || themeRegistry.length === 0) return;
812
829
  fetch("/api/settings/theme").then((r) => r.ok ? r.json() : {}).then((data) => {
@@ -821,7 +838,7 @@ function useResolvedTheme(theme, themeRegistry) {
821
838
  return found?.config ?? theme ?? themeRegistry[0]?.config;
822
839
  }
823
840
  function useStoreEnabled() {
824
- const [storeEnabled, setStoreEnabled] = useState2(false);
841
+ const [storeEnabled, setStoreEnabled] = useState3(false);
825
842
  useEffect2(() => {
826
843
  fetch("/api/settings/store").then((r) => r.ok ? r.json() : {}).then((data) => {
827
844
  setStoreEnabled(data?.enabled === "true");
@@ -863,10 +880,10 @@ function AdminShell({ children }) {
863
880
  }
864
881
 
865
882
  // src/components/Admin/CRUD.tsx
866
- import { useEffect as useEffect6, useState as useState7 } from "react";
883
+ import { useEffect as useEffect6, useRef as useRef3, useState as useState8 } from "react";
867
884
 
868
885
  // src/components/Admin/CreateEditForm.tsx
869
- import { useState as useState5, useEffect as useEffect4 } from "react";
886
+ import { useState as useState6, useEffect as useEffect4 } from "react";
870
887
  import { X as X2 } from "lucide-react";
871
888
 
872
889
  // src/components/ui/input.tsx
@@ -1064,7 +1081,7 @@ var Label3 = React10.forwardRef(({ className, ...props }, ref) => /* @__PURE__ *
1064
1081
  Label3.displayName = LabelPrimitive.Root.displayName;
1065
1082
 
1066
1083
  // src/components/ui/file-upload.tsx
1067
- import { useState as useState3 } from "react";
1084
+ import { useState as useState4 } from "react";
1068
1085
 
1069
1086
  // src/components/ui/progress.tsx
1070
1087
  import * as React11 from "react";
@@ -1093,10 +1110,10 @@ Progress.displayName = ProgressPrimitive.Root.displayName;
1093
1110
  // src/components/ui/file-upload.tsx
1094
1111
  import { jsx as jsx15, jsxs as jsxs9 } from "react/jsx-runtime";
1095
1112
  function FileUpload({ onUploadSuccess }) {
1096
- const [selectedFile, setSelectedFile] = useState3(null);
1097
- const [uploading, setUploading] = useState3(false);
1098
- const [progress, setProgress] = useState3(0);
1099
- const [fileUrl, setFileUrl] = useState3("");
1113
+ const [selectedFile, setSelectedFile] = useState4(null);
1114
+ const [uploading, setUploading] = useState4(false);
1115
+ const [progress, setProgress] = useState4(0);
1116
+ const [fileUrl, setFileUrl] = useState4("");
1100
1117
  const handleFileChange = (event) => {
1101
1118
  setSelectedFile(event.target.files[0]);
1102
1119
  };
@@ -1137,7 +1154,7 @@ function FileUpload({ onUploadSuccess }) {
1137
1154
  }
1138
1155
 
1139
1156
  // src/components/Admin/RelationAutocomplete.tsx
1140
- import { useState as useState4, useEffect as useEffect3, useRef, useCallback } from "react";
1157
+ import { useState as useState5, useEffect as useEffect3, useRef, useCallback } from "react";
1141
1158
  import { ChevronDown as ChevronDown3 } from "lucide-react";
1142
1159
  import { jsx as jsx16, jsxs as jsxs10 } from "react/jsx-runtime";
1143
1160
  var DEBOUNCE_MS = 300;
@@ -1151,16 +1168,16 @@ function RelationAutocomplete({
1151
1168
  placeholder = "Select\u2026",
1152
1169
  disabled = false
1153
1170
  }) {
1154
- const [open, setOpen] = useState4(false);
1155
- const [search, setSearch] = useState4("");
1156
- const [searchInput, setSearchInput] = useState4("");
1157
- const [items, setItems] = useState4([]);
1158
- const [total, setTotal] = useState4(0);
1159
- const [page, setPage] = useState4(1);
1160
- const [loading, setLoading] = useState4(false);
1161
- const [loadingMore, setLoadingMore] = useState4(false);
1162
- const [selectedLabel, setSelectedLabel] = useState4(null);
1163
- const [initialLabelLoaded, setInitialLabelLoaded] = useState4(false);
1171
+ const [open, setOpen] = useState5(false);
1172
+ const [search, setSearch] = useState5("");
1173
+ const [searchInput, setSearchInput] = useState5("");
1174
+ const [items, setItems] = useState5([]);
1175
+ const [total, setTotal] = useState5(0);
1176
+ const [page, setPage] = useState5(1);
1177
+ const [loading, setLoading] = useState5(false);
1178
+ const [loadingMore, setLoadingMore] = useState5(false);
1179
+ const [selectedLabel, setSelectedLabel] = useState5(null);
1180
+ const [initialLabelLoaded, setInitialLabelLoaded] = useState5(false);
1164
1181
  const containerRef = useRef(null);
1165
1182
  const listRef = useRef(null);
1166
1183
  const debounceRef = useRef(null);
@@ -1207,6 +1224,12 @@ function RelationAutocomplete({
1207
1224
  if (debounceRef.current) clearTimeout(debounceRef.current);
1208
1225
  };
1209
1226
  }, [searchInput, open]);
1227
+ useEffect3(() => {
1228
+ if (open) return;
1229
+ setSearchInput("");
1230
+ setSearch("");
1231
+ setPage(1);
1232
+ }, [open]);
1210
1233
  const loadInitialLabel = useCallback(() => {
1211
1234
  if (initialLabelLoaded || value == null || value === "") return;
1212
1235
  setInitialLabelLoaded(true);
@@ -1334,8 +1357,8 @@ import { toast } from "sonner";
1334
1357
  import { jsx as jsx17, jsxs as jsxs11 } from "react/jsx-runtime";
1335
1358
  function CreateEditForm({ isOpen, onClose, apiEndpoint, columns, existingData }) {
1336
1359
  const isMobile = useIsMobile();
1337
- const [formData, setFormData] = useState5({});
1338
- const [errors, setErrors] = useState5({});
1360
+ const [formData, setFormData] = useState6({});
1361
+ const [errors, setErrors] = useState6({});
1339
1362
  useEffect4(() => {
1340
1363
  if (existingData) {
1341
1364
  setFormData(existingData);
@@ -1623,7 +1646,7 @@ var DialogContent = React14.forwardRef(({ className, children, ...props }, ref)
1623
1646
  {
1624
1647
  ref,
1625
1648
  className: cn(
1626
- "fixed left-[50%] top-[50%] z-50 grid w-full max-w-lg translate-x-[-50%] translate-y-[-50%] gap-4 border bg-background p-6 shadow-lg duration-200 data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[state=closed]:slide-out-to-left-1/2 data-[state=closed]:slide-out-to-top-[48%] data-[state=open]:slide-in-from-left-1/2 data-[state=open]:slide-in-from-top-[48%] sm:rounded-lg",
1649
+ "fixed left-[50%] top-[50%] z-50 grid w-[calc(100vw-1rem)] max-w-lg max-h-[calc(100vh-1rem)] translate-x-[-50%] translate-y-[-50%] gap-4 overflow-y-auto rounded-lg border bg-background p-4 shadow-lg duration-200 data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[state=closed]:slide-out-to-left-1/2 data-[state=closed]:slide-out-to-top-[48%] data-[state=open]:slide-in-from-left-1/2 data-[state=open]:slide-in-from-top-[48%] sm:max-h-[calc(100vh-2rem)] sm:p-6",
1627
1650
  className
1628
1651
  ),
1629
1652
  ...props,
@@ -1659,7 +1682,7 @@ var DialogFooter = ({
1659
1682
  "div",
1660
1683
  {
1661
1684
  className: cn(
1662
- "flex flex-col-reverse sm:flex-row sm:justify-end sm:space-x-2",
1685
+ "flex flex-col-reverse gap-2 sm:flex-row sm:justify-end sm:space-x-2 sm:gap-0 [&>button]:w-full sm:[&>button]:w-auto",
1663
1686
  className
1664
1687
  ),
1665
1688
  ...props
@@ -1689,11 +1712,12 @@ var DialogDescription = React14.forwardRef(({ className, ...props }, ref) => /*
1689
1712
  DialogDescription.displayName = DialogPrimitive.Description.displayName;
1690
1713
 
1691
1714
  // src/components/Admin/CRUD.tsx
1692
- import { Edit, Trash2, Eye, Plus, Search, Check as Check3, X as X5, RefreshCw, Upload as Upload2, Download as Download2, MoreVertical, Filter } from "lucide-react";
1715
+ import { Edit, Trash2, Plus, Search, Check as Check3, X as X5, RefreshCw, Upload as Upload2, Download as Download2, MoreVertical, Filter } from "lucide-react";
1693
1716
  import Link4 from "next/link";
1717
+ import { useRouter as useRouter2 } from "next/navigation";
1694
1718
 
1695
1719
  // src/components/Admin/BulkUploadDialog.tsx
1696
- import { useState as useState6, useEffect as useEffect5, useRef as useRef2 } from "react";
1720
+ import { useState as useState7, useEffect as useEffect5, useRef as useRef2 } from "react";
1697
1721
  import { Download, Upload, AlertCircle, CheckCircle2, X as X4 } from "lucide-react";
1698
1722
  import Papa from "papaparse";
1699
1723
  import { jsx as jsx21, jsxs as jsxs14 } from "react/jsx-runtime";
@@ -1708,16 +1732,16 @@ var AUTO_GENERATED_COLS = /* @__PURE__ */ new Set([
1708
1732
  "deleted"
1709
1733
  ]);
1710
1734
  function BulkUploadDialog({ apiEndpoint, onClose }) {
1711
- const [columns, setColumns] = useState6([]);
1712
- const [uniqueColumns, setUniqueColumns] = useState6([]);
1713
- const [loading, setLoading] = useState6(true);
1714
- const [importing, setImporting] = useState6(false);
1715
- const [error, setError] = useState6(null);
1716
- const [success, setSuccess] = useState6(null);
1717
- const [parsedData, setParsedData] = useState6([]);
1718
- const [parseErrors, setParseErrors] = useState6([]);
1719
- const [upsertKey, setUpsertKey] = useState6("id");
1720
- const [fileName, setFileName] = useState6("");
1735
+ const [columns, setColumns] = useState7([]);
1736
+ const [uniqueColumns, setUniqueColumns] = useState7([]);
1737
+ const [loading, setLoading] = useState7(true);
1738
+ const [importing, setImporting] = useState7(false);
1739
+ const [error, setError] = useState7(null);
1740
+ const [success, setSuccess] = useState7(null);
1741
+ const [parsedData, setParsedData] = useState7([]);
1742
+ const [parseErrors, setParseErrors] = useState7([]);
1743
+ const [upsertKey, setUpsertKey] = useState7("id");
1744
+ const [fileName, setFileName] = useState7("");
1721
1745
  const fileInputRef = useRef2(null);
1722
1746
  useEffect5(() => {
1723
1747
  fetchMetadata();
@@ -1961,6 +1985,7 @@ function BulkUploadDialog({ apiEndpoint, onClose }) {
1961
1985
  }
1962
1986
 
1963
1987
  // src/components/Admin/CRUD.tsx
1988
+ import { toast as toast2 } from "sonner";
1964
1989
  import { Fragment as Fragment3, jsx as jsx22, jsxs as jsxs15 } from "react/jsx-runtime";
1965
1990
  function getNestedValue(obj, path) {
1966
1991
  return path.split(".").reduce((current, key) => {
@@ -1985,27 +2010,40 @@ function AdminCRUD({
1985
2010
  extraListParams,
1986
2011
  manageUserGroups
1987
2012
  }) {
1988
- const [data, setData] = useState7([]);
1989
- const [loading, setLoading] = useState7(true);
1990
- const [error, setError] = useState7(null);
1991
- const [page, setPage] = useState7(1);
1992
- const [totalPages, setTotalPages] = useState7(1);
1993
- const [sortField, setSortField] = useState7(defaultSortField);
1994
- const [sortOrder, setSortOrder] = useState7(defaultSortOrder);
1995
- const [searchQuery, setSearchQuery] = useState7("");
1996
- const [filterValues, setFilterValues] = useState7({});
1997
- const [filterApplyKey, setFilterApplyKey] = useState7(0);
1998
- const [isFormOpen, setIsFormOpen] = useState7(false);
1999
- const [editingItem, setEditingItem] = useState7(null);
2000
- const [deleteDialogOpen, setDeleteDialogOpen] = useState7(false);
2001
- const [itemToDelete, setItemToDelete] = useState7(null);
2002
- const [deleteLoading, setDeleteLoading] = useState7(false);
2003
- const [refreshKey, setRefreshKey] = useState7(0);
2004
- const [bulkDialogOpen, setBulkDialogOpen] = useState7(false);
2005
- const [showFilters, setShowFilters] = useState7(false);
2006
- const [roleOptions, setRoleOptions] = useState7([]);
2013
+ const router = useRouter2();
2014
+ const [data, setData] = useState8([]);
2015
+ const [loading, setLoading] = useState8(true);
2016
+ const [error, setError] = useState8(null);
2017
+ const [page, setPage] = useState8(1);
2018
+ const [totalPages, setTotalPages] = useState8(1);
2019
+ const [sortField, setSortField] = useState8(defaultSortField);
2020
+ const [sortOrder, setSortOrder] = useState8(defaultSortOrder);
2021
+ const [searchQuery, setSearchQuery] = useState8("");
2022
+ const [searchInput, setSearchInput] = useState8("");
2023
+ const [filterValues, setFilterValues] = useState8({});
2024
+ const [filterApplyKey, setFilterApplyKey] = useState8(0);
2025
+ const [isFormOpen, setIsFormOpen] = useState8(false);
2026
+ const [editingItem, setEditingItem] = useState8(null);
2027
+ const [deleteDialogOpen, setDeleteDialogOpen] = useState8(false);
2028
+ const [itemToDelete, setItemToDelete] = useState8(null);
2029
+ const [deleteLoading, setDeleteLoading] = useState8(false);
2030
+ const [refreshKey, setRefreshKey] = useState8(0);
2031
+ const [bulkDialogOpen, setBulkDialogOpen] = useState8(false);
2032
+ const [showFilters, setShowFilters] = useState8(false);
2033
+ const [isRefetching, setIsRefetching] = useState8(false);
2034
+ const [roleOptions, setRoleOptions] = useState8([]);
2035
+ const hasLoadedRef = useRef3(false);
2007
2036
  const isMobile = useIsMobile();
2008
2037
  const showGroupColumn = !!manageUserGroups && roleOptions.length > 0;
2038
+ useEffect6(() => {
2039
+ const timeoutId = setTimeout(() => {
2040
+ if (searchInput !== searchQuery) {
2041
+ setPage(1);
2042
+ setSearchQuery(searchInput);
2043
+ }
2044
+ }, 300);
2045
+ return () => clearTimeout(timeoutId);
2046
+ }, [searchInput, searchQuery]);
2009
2047
  useEffect6(() => {
2010
2048
  if (!manageUserGroups) return;
2011
2049
  fetch("/api/admin/roles").then((r) => r.ok ? r.json() : null).then((data2) => {
@@ -2016,7 +2054,11 @@ function AdminCRUD({
2016
2054
  useEffect6(() => {
2017
2055
  async function loadData() {
2018
2056
  try {
2019
- setLoading(true);
2057
+ if (!hasLoadedRef.current) {
2058
+ setLoading(true);
2059
+ } else {
2060
+ setIsRefetching(true);
2061
+ }
2020
2062
  setError(null);
2021
2063
  const params = new URLSearchParams({
2022
2064
  page: page.toString(),
@@ -2056,6 +2098,8 @@ function AdminCRUD({
2056
2098
  setTotalPages(1);
2057
2099
  } finally {
2058
2100
  setLoading(false);
2101
+ setIsRefetching(false);
2102
+ hasLoadedRef.current = true;
2059
2103
  }
2060
2104
  }
2061
2105
  loadData();
@@ -2066,30 +2110,67 @@ function AdminCRUD({
2066
2110
  };
2067
2111
  const handleSearch = () => {
2068
2112
  setPage(1);
2113
+ setSearchQuery(searchInput);
2069
2114
  };
2070
2115
  const handleApplyFilters = () => {
2071
2116
  setPage(1);
2072
2117
  setFilterApplyKey((k) => k + 1);
2073
2118
  };
2119
+ const closeDeleteDialog = () => {
2120
+ console.debug("[CRUD][delete] closeDeleteDialog", {
2121
+ open: deleteDialogOpen,
2122
+ itemId: itemToDelete?.id,
2123
+ loading: deleteLoading
2124
+ });
2125
+ setDeleteDialogOpen(false);
2126
+ setItemToDelete(null);
2127
+ setDeleteLoading(false);
2128
+ };
2074
2129
  const handleDeleteClick = (item) => {
2130
+ console.debug("[CRUD][delete] handleDeleteClick", {
2131
+ itemId: item?.id,
2132
+ resource: resourceName
2133
+ });
2134
+ const active = typeof document !== "undefined" ? document.activeElement : null;
2135
+ if (active instanceof HTMLElement) {
2136
+ active.blur();
2137
+ }
2138
+ setDeleteLoading(false);
2075
2139
  setItemToDelete(item);
2076
- setDeleteDialogOpen(true);
2140
+ window.setTimeout(() => {
2141
+ setDeleteDialogOpen(true);
2142
+ }, 0);
2077
2143
  };
2078
2144
  const handleDelete = async () => {
2079
- if (!itemToDelete) return;
2145
+ if (!itemToDelete) {
2146
+ console.debug("[CRUD][delete] handleDelete blocked: no itemToDelete");
2147
+ return;
2148
+ }
2149
+ console.debug("[CRUD][delete] handleDelete start", {
2150
+ itemId: itemToDelete.id,
2151
+ resource: resourceName
2152
+ });
2080
2153
  setDeleteLoading(true);
2081
2154
  try {
2082
2155
  const res = await fetch(`${apiEndpoint}/${itemToDelete.id}`, { method: "DELETE" });
2156
+ console.debug("[CRUD][delete] handleDelete response", {
2157
+ itemId: itemToDelete.id,
2158
+ ok: res.ok,
2159
+ status: res.status
2160
+ });
2083
2161
  if (res.ok) {
2162
+ setData((prev) => prev.filter((row) => String(row.id) !== String(itemToDelete.id)));
2084
2163
  setRefreshKey((k) => k + 1);
2085
- setDeleteDialogOpen(false);
2086
- setItemToDelete(null);
2164
+ closeDeleteDialog();
2087
2165
  } else {
2088
2166
  console.error("Failed to delete item");
2089
2167
  }
2090
2168
  } catch (err) {
2091
2169
  console.error("Error deleting item:", err);
2092
2170
  } finally {
2171
+ console.debug("[CRUD][delete] handleDelete finally", {
2172
+ itemId: itemToDelete?.id
2173
+ });
2093
2174
  setDeleteLoading(false);
2094
2175
  }
2095
2176
  };
@@ -2124,18 +2205,33 @@ function AdminCRUD({
2124
2205
  }
2125
2206
  const result = await res.json();
2126
2207
  if (result.inviteLink) {
2127
- alert(`New invite link generated: ${result.inviteLink}
2128
-
2129
- Note: ${result.note}`);
2208
+ const note = result.note ? ` ${result.note}` : "";
2209
+ toast2.success(`New invite link generated.${note}`);
2130
2210
  }
2131
2211
  } catch (error2) {
2132
2212
  console.error("Error regenerating invite:", error2);
2133
- alert(error2 instanceof Error ? error2.message : "Failed to regenerate invite");
2213
+ toast2.error(error2 instanceof Error ? error2.message : "Failed to regenerate invite");
2134
2214
  }
2135
2215
  };
2136
2216
  const addEditPage = addEditPageUrl && addEditPageUrl.length > 0;
2137
2217
  const hasCustomView = customViewPageUrl && customViewPageUrl.length > 0;
2138
2218
  const resourceName = apiEndpoint.replace("/api/", "");
2219
+ const hasDetailViewPage = (/* @__PURE__ */ new Set(["contacts", "form-submissions", "orders", "payments"])).has(resourceName);
2220
+ const getRowDestination = (item) => {
2221
+ if (item.id == null) return "modal";
2222
+ if (addEditPage) return `${addEditPageUrl}/${item.id}`;
2223
+ if (hasCustomView) return `${customViewPageUrl}/${item.id}`;
2224
+ if (hasDetailViewPage) return `/admin/${resourceName}/${item.id}/view`;
2225
+ return "modal";
2226
+ };
2227
+ const handleRowClick = (item) => {
2228
+ const destination = getRowDestination(item);
2229
+ if (destination === "modal") {
2230
+ handleEdit(item);
2231
+ return;
2232
+ }
2233
+ router.push(destination);
2234
+ };
2139
2235
  const handleExport = async () => {
2140
2236
  try {
2141
2237
  const res = await fetch(`${apiEndpoint}/export?format=csv`);
@@ -2149,7 +2245,7 @@ Note: ${result.note}`);
2149
2245
  URL.revokeObjectURL(url);
2150
2246
  } catch (err) {
2151
2247
  console.error("Export error:", err);
2152
- alert("Failed to export data");
2248
+ toast2.error("Failed to export data");
2153
2249
  }
2154
2250
  };
2155
2251
  if (loading) {
@@ -2289,8 +2385,8 @@ Note: ${result.note}`);
2289
2385
  {
2290
2386
  type: "text",
2291
2387
  placeholder: "Search...",
2292
- value: searchQuery,
2293
- onChange: (e) => setSearchQuery(e.target.value),
2388
+ value: searchInput,
2389
+ onChange: (e) => setSearchInput(e.target.value),
2294
2390
  onKeyDown: (e) => e.key === "Enter" && handleSearch(),
2295
2391
  className: "border-0 focus-visible:ring-0 focus-visible:ring-offset-0 rounded-l-md rounded-r-none flex-1 min-w-0"
2296
2392
  }
@@ -2384,6 +2480,10 @@ Note: ${result.note}`);
2384
2480
  }),
2385
2481
  /* @__PURE__ */ jsx22(Button, { variant: "outline", size: "sm", className: "h-8", onClick: handleApplyFilters, children: "Apply filters" })
2386
2482
  ] }),
2483
+ isRefetching && /* @__PURE__ */ jsxs15("div", { className: "mb-3 flex items-center text-xs text-gray-500", children: [
2484
+ /* @__PURE__ */ jsx22("div", { className: "animate-spin rounded-full h-3.5 w-3.5 border-2 border-gray-300 border-t-gray-600" }),
2485
+ /* @__PURE__ */ jsx22("span", { className: "ml-2", children: "Refreshing list..." })
2486
+ ] }),
2387
2487
  isMobile ? /* @__PURE__ */ jsx22("div", { className: "flex flex-col gap-2 min-w-0", children: data && data.length > 0 ? data.map((item, index) => {
2388
2488
  const displayCols = columns?.slice(0, 4) ?? [];
2389
2489
  const primary = displayCols[0];
@@ -2391,27 +2491,17 @@ Note: ${result.note}`);
2391
2491
  return /* @__PURE__ */ jsxs15(
2392
2492
  "div",
2393
2493
  {
2394
- className: "min-w-0 rounded-md border border-gray-200 bg-gray-50/50 p-2.5 flex flex-col gap-1",
2494
+ className: "min-w-0 rounded-md border border-gray-200 bg-gray-50/50 p-2.5 flex flex-col gap-1 cursor-pointer",
2495
+ onClick: () => handleRowClick(item),
2395
2496
  children: [
2396
2497
  /* @__PURE__ */ jsxs15("div", { className: "flex items-center justify-between gap-2", children: [
2397
2498
  /* @__PURE__ */ jsx22("div", { className: "min-w-0 break-words flex-1 leading-tight", children: /* @__PURE__ */ jsx22("span", { className: "font-medium", children: primaryVal != null ? String(primaryVal) : "\u2014" }) }),
2398
- /* @__PURE__ */ jsxs15(DropdownMenu, { children: [
2499
+ /* @__PURE__ */ jsx22("div", { onClick: (e) => e.stopPropagation(), children: /* @__PURE__ */ jsxs15(DropdownMenu, { children: [
2399
2500
  /* @__PURE__ */ jsx22(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxs15(Button, { variant: "ghost", size: "icon", className: "h-8 w-8 shrink-0", children: [
2400
2501
  /* @__PURE__ */ jsx22(MoreVertical, { className: "h-4 w-4" }),
2401
2502
  /* @__PURE__ */ jsx22("span", { className: "sr-only", children: "Actions" })
2402
2503
  ] }) }),
2403
2504
  /* @__PURE__ */ jsxs15(DropdownMenuContent, { align: "end", children: [
2404
- /* @__PURE__ */ jsx22(DropdownMenuItem, { asChild: true, children: /* @__PURE__ */ jsxs15(
2405
- Link4,
2406
- {
2407
- href: hasCustomView ? `${customViewPageUrl}/${item.id}` : `/admin/${resourceName}/${item.id}/view`,
2408
- className: "flex items-center gap-2",
2409
- children: [
2410
- /* @__PURE__ */ jsx22(Eye, { className: "h-4 w-4" }),
2411
- "View"
2412
- ]
2413
- }
2414
- ) }),
2415
2505
  !addEditPage && /* @__PURE__ */ jsxs15(DropdownMenuItem, { onClick: () => handleEdit(item), children: [
2416
2506
  /* @__PURE__ */ jsx22(Edit, { className: "h-4 w-4 mr-2" }),
2417
2507
  "Edit"
@@ -2436,7 +2526,7 @@ Note: ${result.note}`);
2436
2526
  }
2437
2527
  )
2438
2528
  ] })
2439
- ] })
2529
+ ] }, `mobile-actions-${String(item.id ?? index)}-${refreshKey}`) })
2440
2530
  ] }),
2441
2531
  displayCols.slice(1).map((col) => /* @__PURE__ */ jsxs15("div", { className: "text-sm text-gray-600 flex gap-1 min-w-0 leading-tight", children: [
2442
2532
  /* @__PURE__ */ jsxs15("span", { className: "shrink-0", children: [
@@ -2445,7 +2535,7 @@ Note: ${result.note}`);
2445
2535
  ] }),
2446
2536
  /* @__PURE__ */ jsx22("span", { className: "min-w-0 break-words", children: formatCellValue(getNestedValue(item, col.field || col.key), col) })
2447
2537
  ] }, col.field || col.key)),
2448
- showGroupColumn && /* @__PURE__ */ jsxs15("div", { className: "text-sm text-gray-600 flex gap-1 items-center min-w-0", children: [
2538
+ showGroupColumn && /* @__PURE__ */ jsxs15("div", { className: "text-sm text-gray-600 flex gap-1 items-center min-w-0", onClick: (e) => e.stopPropagation(), children: [
2449
2539
  /* @__PURE__ */ jsx22("span", { className: "shrink-0", children: "Group:" }),
2450
2540
  /* @__PURE__ */ jsxs15(
2451
2541
  "select",
@@ -2485,70 +2575,94 @@ Note: ${result.note}`);
2485
2575
  showGroupColumn && /* @__PURE__ */ jsx22(TableHead, { className: "min-w-[140px]", children: "Group" }),
2486
2576
  /* @__PURE__ */ jsx22(TableHead, { className: "w-12 text-center", children: "Actions" })
2487
2577
  ] }) }),
2488
- /* @__PURE__ */ jsx22(TableBody, { children: data && data.length > 0 ? data.map((item, index) => /* @__PURE__ */ jsxs15(TableRow, { children: [
2489
- columns && columns.map((col, colIndex) => {
2490
- const fieldKey = col.field || col.key;
2491
- const value = getNestedValue(item, fieldKey);
2492
- return /* @__PURE__ */ jsx22(TableCell, { children: formatCellValue(value, col) }, `${item.id}-${colIndex}-${fieldKey}`);
2493
- }),
2494
- showGroupColumn && /* @__PURE__ */ jsx22(TableCell, { children: /* @__PURE__ */ jsxs15(
2495
- "select",
2496
- {
2497
- className: "max-w-[180px] rounded border border-gray-300 px-2 py-1 text-sm dark:border-gray-600 dark:bg-gray-800",
2498
- value: item.groupId != null && roleOptions.some((g) => g.id === item.groupId) ? String(item.groupId) : "",
2499
- onChange: (e) => {
2500
- const v = e.target.value;
2501
- if (v) handleUserGroupChange(Number(item.id), Number(v));
2502
- },
2503
- children: [
2504
- /* @__PURE__ */ jsx22("option", { value: "", children: "\u2014" }),
2505
- roleOptions.map((g) => /* @__PURE__ */ jsx22("option", { value: g.id, children: g.name }, g.id))
2506
- ]
2507
- }
2508
- ) }),
2509
- /* @__PURE__ */ jsx22(TableCell, { className: "text-center", children: /* @__PURE__ */ jsxs15(DropdownMenu, { children: [
2510
- /* @__PURE__ */ jsx22(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxs15(Button, { variant: "ghost", size: "icon", className: "h-8 w-8", children: [
2511
- /* @__PURE__ */ jsx22(MoreVertical, { className: "h-4 w-4" }),
2512
- /* @__PURE__ */ jsx22("span", { className: "sr-only", children: "Actions" })
2513
- ] }) }),
2514
- /* @__PURE__ */ jsxs15(DropdownMenuContent, { align: "end", children: [
2515
- /* @__PURE__ */ jsx22(DropdownMenuItem, { asChild: true, children: /* @__PURE__ */ jsxs15(
2516
- Link4,
2578
+ /* @__PURE__ */ jsx22(TableBody, { children: data && data.length > 0 ? data.map((item, index) => /* @__PURE__ */ jsxs15(
2579
+ TableRow,
2580
+ {
2581
+ className: "cursor-pointer",
2582
+ onClick: () => handleRowClick(item),
2583
+ children: [
2584
+ columns && columns.map((col, colIndex) => {
2585
+ const fieldKey = col.field || col.key;
2586
+ const value = getNestedValue(item, fieldKey);
2587
+ return /* @__PURE__ */ jsx22(TableCell, { children: formatCellValue(value, col) }, `${item.id}-${colIndex}-${fieldKey}`);
2588
+ }),
2589
+ showGroupColumn && /* @__PURE__ */ jsx22(TableCell, { onClick: (e) => e.stopPropagation(), children: /* @__PURE__ */ jsxs15(
2590
+ "select",
2517
2591
  {
2518
- href: hasCustomView ? `${customViewPageUrl}/${item.id}` : `/admin/${resourceName}/${item.id}/view`,
2519
- className: "flex items-center gap-2",
2592
+ className: "max-w-[180px] rounded border border-gray-300 px-2 py-1 text-sm dark:border-gray-600 dark:bg-gray-800",
2593
+ value: item.groupId != null && roleOptions.some((g) => g.id === item.groupId) ? String(item.groupId) : "",
2594
+ onChange: (e) => {
2595
+ const v = e.target.value;
2596
+ if (v) handleUserGroupChange(Number(item.id), Number(v));
2597
+ },
2520
2598
  children: [
2521
- /* @__PURE__ */ jsx22(Eye, { className: "h-4 w-4" }),
2522
- "View"
2599
+ /* @__PURE__ */ jsx22("option", { value: "", children: "\u2014" }),
2600
+ roleOptions.map((g) => /* @__PURE__ */ jsx22("option", { value: g.id, children: g.name }, g.id))
2523
2601
  ]
2524
2602
  }
2525
2603
  ) }),
2526
- !addEditPage && /* @__PURE__ */ jsxs15(DropdownMenuItem, { onClick: () => handleEdit(item), children: [
2527
- /* @__PURE__ */ jsx22(Edit, { className: "h-4 w-4 mr-2" }),
2528
- "Edit"
2529
- ] }),
2530
- addEditPage && /* @__PURE__ */ jsx22(DropdownMenuItem, { asChild: true, children: /* @__PURE__ */ jsxs15(Link4, { href: addEditPageUrl + "/" + item.id, className: "flex items-center gap-2", children: [
2531
- /* @__PURE__ */ jsx22(Edit, { className: "h-4 w-4" }),
2532
- "Edit"
2533
- ] }) }),
2534
- resourceName === "users" && /* @__PURE__ */ jsxs15(DropdownMenuItem, { onClick: () => handleRegenerateInvite(Number(item.id)), children: [
2535
- /* @__PURE__ */ jsx22(RefreshCw, { className: "h-4 w-4 mr-2" }),
2536
- "Regenerate Invite"
2537
- ] }),
2538
- /* @__PURE__ */ jsxs15(
2539
- DropdownMenuItem,
2540
- {
2541
- onClick: () => handleDeleteClick(item),
2542
- className: "text-red-600 focus:text-red-600",
2543
- children: [
2544
- /* @__PURE__ */ jsx22(Trash2, { className: "h-4 w-4 mr-2" }),
2545
- "Delete"
2546
- ]
2547
- }
2548
- )
2549
- ] })
2550
- ] }) })
2551
- ] }, String(item.id ?? index))) : /* @__PURE__ */ jsx22(TableRow, { children: /* @__PURE__ */ jsx22(
2604
+ /* @__PURE__ */ jsx22(TableCell, { className: "text-center", onClick: (e) => e.stopPropagation(), children: /* @__PURE__ */ jsxs15("div", { className: "flex items-center justify-center gap-1", children: [
2605
+ !addEditPage && /* @__PURE__ */ jsxs15(
2606
+ Button,
2607
+ {
2608
+ variant: "outline",
2609
+ size: "icon",
2610
+ className: "h-7 w-7",
2611
+ onClick: () => handleEdit(item),
2612
+ title: "Edit",
2613
+ children: [
2614
+ /* @__PURE__ */ jsx22(Edit, { className: "h-3.5 w-3.5" }),
2615
+ /* @__PURE__ */ jsx22("span", { className: "sr-only", children: "Edit" })
2616
+ ]
2617
+ }
2618
+ ),
2619
+ addEditPage && /* @__PURE__ */ jsxs15(
2620
+ Button,
2621
+ {
2622
+ variant: "outline",
2623
+ size: "icon",
2624
+ className: "h-7 w-7",
2625
+ onClick: () => router.push(addEditPageUrl + "/" + item.id),
2626
+ title: "Edit",
2627
+ children: [
2628
+ /* @__PURE__ */ jsx22(Edit, { className: "h-3.5 w-3.5" }),
2629
+ /* @__PURE__ */ jsx22("span", { className: "sr-only", children: "Edit" })
2630
+ ]
2631
+ }
2632
+ ),
2633
+ resourceName === "users" && /* @__PURE__ */ jsxs15(
2634
+ Button,
2635
+ {
2636
+ variant: "outline",
2637
+ size: "icon",
2638
+ className: "h-7 w-7",
2639
+ onClick: () => handleRegenerateInvite(Number(item.id)),
2640
+ title: "Regenerate Invite",
2641
+ children: [
2642
+ /* @__PURE__ */ jsx22(RefreshCw, { className: "h-3.5 w-3.5" }),
2643
+ /* @__PURE__ */ jsx22("span", { className: "sr-only", children: "Regenerate Invite" })
2644
+ ]
2645
+ }
2646
+ ),
2647
+ /* @__PURE__ */ jsxs15(
2648
+ Button,
2649
+ {
2650
+ variant: "outline",
2651
+ size: "icon",
2652
+ className: "h-7 w-7 border-red-300 text-red-600 hover:text-red-700",
2653
+ onClick: () => handleDeleteClick(item),
2654
+ title: "Delete",
2655
+ children: [
2656
+ /* @__PURE__ */ jsx22(Trash2, { className: "h-3.5 w-3.5" }),
2657
+ /* @__PURE__ */ jsx22("span", { className: "sr-only", children: "Delete" })
2658
+ ]
2659
+ }
2660
+ )
2661
+ ] }) })
2662
+ ]
2663
+ },
2664
+ String(item.id ?? index)
2665
+ )) : /* @__PURE__ */ jsx22(TableRow, { children: /* @__PURE__ */ jsx22(
2552
2666
  TableCell,
2553
2667
  {
2554
2668
  colSpan: columns ? columns.length + 1 + (showGroupColumn ? 1 : 0) : 1,
@@ -2594,21 +2708,35 @@ Note: ${result.note}`);
2594
2708
  existingData: editingItem
2595
2709
  }
2596
2710
  ),
2597
- /* @__PURE__ */ jsx22(Dialog, { open: deleteDialogOpen, onOpenChange: setDeleteDialogOpen, children: /* @__PURE__ */ jsxs15(DialogContent, { children: [
2598
- /* @__PURE__ */ jsxs15(DialogHeader, { children: [
2599
- /* @__PURE__ */ jsx22(DialogTitle, { children: "Confirm Delete" }),
2600
- /* @__PURE__ */ jsx22(DialogDescription, { children: "Are you sure you want to delete this item? This action cannot be undone." }),
2601
- itemToDelete && /* @__PURE__ */ jsxs15("div", { className: "mt-2 p-2 bg-gray-50 rounded", children: [
2602
- /* @__PURE__ */ jsx22("strong", { children: "Item:" }),
2603
- " ",
2604
- String(itemToDelete.name ?? itemToDelete.title ?? itemToDelete.id ?? "")
2711
+ /* @__PURE__ */ jsx22(
2712
+ Dialog,
2713
+ {
2714
+ open: deleteDialogOpen,
2715
+ onOpenChange: (open) => {
2716
+ console.debug("[CRUD][delete] dialog onOpenChange", {
2717
+ nextOpen: open,
2718
+ itemId: itemToDelete?.id
2719
+ });
2720
+ if (!open) closeDeleteDialog();
2721
+ else setDeleteDialogOpen(true);
2722
+ },
2723
+ children: /* @__PURE__ */ jsxs15(DialogContent, { children: [
2724
+ /* @__PURE__ */ jsxs15(DialogHeader, { children: [
2725
+ /* @__PURE__ */ jsx22(DialogTitle, { children: "Confirm Delete" }),
2726
+ /* @__PURE__ */ jsx22(DialogDescription, { children: "Are you sure you want to delete this item? This action cannot be undone." }),
2727
+ itemToDelete && /* @__PURE__ */ jsxs15("div", { className: "mt-2 p-2 bg-gray-50 rounded", children: [
2728
+ /* @__PURE__ */ jsx22("strong", { children: "Item:" }),
2729
+ " ",
2730
+ String(itemToDelete.name ?? itemToDelete.title ?? itemToDelete.id ?? "")
2731
+ ] })
2732
+ ] }),
2733
+ /* @__PURE__ */ jsxs15(DialogFooter, { children: [
2734
+ /* @__PURE__ */ jsx22(Button, { variant: "outline", onClick: closeDeleteDialog, disabled: deleteLoading, children: "Cancel" }),
2735
+ /* @__PURE__ */ jsx22(Button, { variant: "destructive", onClick: handleDelete, disabled: deleteLoading, children: deleteLoading ? "Deleting..." : "Delete" })
2736
+ ] })
2605
2737
  ] })
2606
- ] }),
2607
- /* @__PURE__ */ jsxs15(DialogFooter, { children: [
2608
- /* @__PURE__ */ jsx22(Button, { variant: "outline", onClick: () => setDeleteDialogOpen(false), disabled: deleteLoading, children: "Cancel" }),
2609
- /* @__PURE__ */ jsx22(Button, { variant: "destructive", onClick: handleDelete, disabled: deleteLoading, children: deleteLoading ? "Deleting..." : "Delete" })
2610
- ] })
2611
- ] }) }),
2738
+ }
2739
+ ),
2612
2740
  bulkDialogOpen && /* @__PURE__ */ jsx22(
2613
2741
  BulkUploadDialog,
2614
2742
  {
@@ -2624,7 +2752,7 @@ Note: ${result.note}`);
2624
2752
  }
2625
2753
 
2626
2754
  // src/components/Admin/FormBuilder.tsx
2627
- import { useState as useState9, useEffect as useEffect7, useCallback as useCallback2 } from "react";
2755
+ import { useState as useState10, useEffect as useEffect7, useCallback as useCallback2 } from "react";
2628
2756
 
2629
2757
  // src/components/ui/badge.tsx
2630
2758
  import { cva as cva4 } from "class-variance-authority";
@@ -2650,11 +2778,11 @@ function Badge({ className, variant, ...props }) {
2650
2778
  }
2651
2779
 
2652
2780
  // src/components/Admin/FormBuilder.tsx
2653
- import { X as X7, Save, Plus as Plus3, Trash2 as Trash22 } from "lucide-react";
2654
- import { useRouter as useRouter2 } from "next/navigation";
2781
+ import { X as X7, Save, Plus as Plus3, Trash2 as Trash22, Check as Check4 } from "lucide-react";
2782
+ import { useRouter as useRouter3 } from "next/navigation";
2655
2783
 
2656
2784
  // src/components/Admin/FormBuilder/FieldConfiguration.tsx
2657
- import { useState as useState8 } from "react";
2785
+ import { useState as useState9 } from "react";
2658
2786
  import { Plus as Plus2, X as X6 } from "lucide-react";
2659
2787
  import { jsx as jsx24, jsxs as jsxs16 } from "react/jsx-runtime";
2660
2788
  var FIELD_TYPES = [
@@ -2675,7 +2803,7 @@ var COLUMN_WIDTHS = [
2675
2803
  { value: 12, label: "Full Width (12 cols)" }
2676
2804
  ];
2677
2805
  function FieldConfiguration({ field, onUpdate }) {
2678
- const [newOption, setNewOption] = useState8("");
2806
+ const [newOption, setNewOption] = useState9("");
2679
2807
  const addOption = () => {
2680
2808
  if (newOption.trim()) {
2681
2809
  const currentOptions = field.options || [];
@@ -2948,7 +3076,7 @@ function FieldConfiguration({ field, onUpdate }) {
2948
3076
  // src/components/Admin/FormBuilder.tsx
2949
3077
  import { jsx as jsx25, jsxs as jsxs17 } from "react/jsx-runtime";
2950
3078
  function FormBuilder({ formId }) {
2951
- const [formData, setFormData] = useState9({
3079
+ const [formData, setFormData] = useState10({
2952
3080
  name: "",
2953
3081
  description: "",
2954
3082
  campaign: "",
@@ -2956,11 +3084,11 @@ function FormBuilder({ formId }) {
2956
3084
  published: false,
2957
3085
  fields: []
2958
3086
  });
2959
- const [errors, setErrors] = useState9([]);
2960
- const [isLoading, setIsLoading] = useState9(false);
2961
- const [isSaving, setIsSaving] = useState9(false);
2962
- const [selectedField, setSelectedField] = useState9(null);
2963
- const router = useRouter2();
3087
+ const [errors, setErrors] = useState10([]);
3088
+ const [isLoading, setIsLoading] = useState10(false);
3089
+ const [isSaving, setIsSaving] = useState10(false);
3090
+ const [selectedField, setSelectedField] = useState10(null);
3091
+ const router = useRouter3();
2964
3092
  const loadFormData = useCallback2(async () => {
2965
3093
  try {
2966
3094
  setIsLoading(true);
@@ -3125,19 +3253,34 @@ function FormBuilder({ formId }) {
3125
3253
  /* @__PURE__ */ jsx25("h1", { className: "text-xl font-bold text-white", children: formId ? "Edit Form" : "Create New Form" }),
3126
3254
  /* @__PURE__ */ jsx25("p", { className: "text-xs text-gray-300 mt-0.5", children: "Design your form with drag-and-drop fields" })
3127
3255
  ] }),
3128
- /* @__PURE__ */ jsx25("div", { className: "flex items-center space-x-3", children: /* @__PURE__ */ jsxs17(
3129
- Button,
3130
- {
3131
- variant: "outline",
3132
- size: "sm",
3133
- className: "bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
3134
- onClick: () => router.push("/admin/forms"),
3135
- children: [
3136
- /* @__PURE__ */ jsx25(X7, { className: "h-4 w-4 mr-2" }),
3137
- "Close"
3138
- ]
3139
- }
3140
- ) })
3256
+ /* @__PURE__ */ jsxs17("div", { className: "flex items-center space-x-3", children: [
3257
+ /* @__PURE__ */ jsxs17(
3258
+ Button,
3259
+ {
3260
+ variant: "outline",
3261
+ size: "icon",
3262
+ className: "md:hidden h-8 w-8 bg-white text-gray-800 hover:bg-gray-100 border-0",
3263
+ onClick: () => router.push("/admin/forms"),
3264
+ children: [
3265
+ /* @__PURE__ */ jsx25(X7, { className: "h-4 w-4" }),
3266
+ /* @__PURE__ */ jsx25("span", { className: "sr-only", children: "Close" })
3267
+ ]
3268
+ }
3269
+ ),
3270
+ /* @__PURE__ */ jsxs17(
3271
+ Button,
3272
+ {
3273
+ variant: "outline",
3274
+ size: "sm",
3275
+ className: "hidden md:inline-flex bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
3276
+ onClick: () => router.push("/admin/forms"),
3277
+ children: [
3278
+ /* @__PURE__ */ jsx25(X7, { className: "h-4 w-4 mr-2" }),
3279
+ "Close"
3280
+ ]
3281
+ }
3282
+ )
3283
+ ] })
3141
3284
  ] }) }),
3142
3285
  errors.length > 0 && /* @__PURE__ */ jsx25("div", { className: "bg-red-50 border-l-4 border-red-400 p-4 mx-6 mt-4", children: /* @__PURE__ */ jsx25("div", { className: "flex", children: /* @__PURE__ */ jsxs17("div", { className: "ml-3", children: [
3143
3286
  /* @__PURE__ */ jsx25("h3", { className: "text-sm font-medium text-red-800", children: "Please fix the following errors:" }),
@@ -3315,11 +3458,24 @@ function FormBuilder({ formId }) {
3315
3458
  /* @__PURE__ */ jsx25("div", { className: "bg-gray-50 border-t border-gray-200 px-6 py-4", children: /* @__PURE__ */ jsxs17("div", { className: "flex items-center justify-between", children: [
3316
3459
  /* @__PURE__ */ jsx25("div", { className: "text-sm text-gray-600", children: formId ? "Editing existing form" : "Creating new form" }),
3317
3460
  /* @__PURE__ */ jsxs17("div", { className: "flex items-center space-x-3", children: [
3461
+ /* @__PURE__ */ jsxs17(
3462
+ Button,
3463
+ {
3464
+ variant: "outline",
3465
+ size: "icon",
3466
+ className: "md:hidden h-8 w-8 bg-white text-gray-800 hover:bg-gray-100 border-0",
3467
+ onClick: () => router.push("/admin/forms"),
3468
+ children: [
3469
+ /* @__PURE__ */ jsx25(X7, { className: "h-4 w-4" }),
3470
+ /* @__PURE__ */ jsx25("span", { className: "sr-only", children: "Close" })
3471
+ ]
3472
+ }
3473
+ ),
3318
3474
  /* @__PURE__ */ jsx25(
3319
3475
  Button,
3320
3476
  {
3321
3477
  variant: "outline",
3322
- className: "bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
3478
+ className: "hidden md:inline-flex bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
3323
3479
  onClick: () => router.push("/admin/forms"),
3324
3480
  children: "Close"
3325
3481
  }
@@ -3329,19 +3485,45 @@ function FormBuilder({ formId }) {
3329
3485
  {
3330
3486
  onClick: () => handleSave(false),
3331
3487
  disabled: isSaving,
3332
- className: "bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
3488
+ size: "icon",
3489
+ className: "md:hidden h-8 w-8 bg-white text-gray-800 hover:bg-gray-100 border-0",
3490
+ children: [
3491
+ /* @__PURE__ */ jsx25(Save, { className: "h-4 w-4" }),
3492
+ /* @__PURE__ */ jsx25("span", { className: "sr-only", children: isSaving ? "Saving..." : "Save" })
3493
+ ]
3494
+ }
3495
+ ),
3496
+ /* @__PURE__ */ jsxs17(
3497
+ Button,
3498
+ {
3499
+ onClick: () => handleSave(false),
3500
+ disabled: isSaving,
3501
+ className: "hidden md:inline-flex bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
3333
3502
  children: [
3334
3503
  /* @__PURE__ */ jsx25(Save, { className: "h-4 w-4 mr-2" }),
3335
3504
  isSaving ? "Saving..." : "Save"
3336
3505
  ]
3337
3506
  }
3338
3507
  ),
3508
+ /* @__PURE__ */ jsxs17(
3509
+ Button,
3510
+ {
3511
+ onClick: () => handleSave(true),
3512
+ disabled: isSaving,
3513
+ size: "icon",
3514
+ className: "md:hidden h-8 w-8 bg-gray-800 text-white hover:bg-gray-700",
3515
+ children: [
3516
+ /* @__PURE__ */ jsx25(Check4, { className: "h-4 w-4" }),
3517
+ /* @__PURE__ */ jsx25("span", { className: "sr-only", children: isSaving ? "Publishing..." : "Publish" })
3518
+ ]
3519
+ }
3520
+ ),
3339
3521
  /* @__PURE__ */ jsx25(
3340
3522
  Button,
3341
3523
  {
3342
3524
  onClick: () => handleSave(true),
3343
3525
  disabled: isSaving,
3344
- className: "bg-gray-800 text-white hover:bg-gray-700 text-xs",
3526
+ className: "hidden md:inline-flex bg-gray-800 text-white hover:bg-gray-700 text-xs",
3345
3527
  children: isSaving ? "Publishing..." : "Publish"
3346
3528
  }
3347
3529
  )
@@ -3351,10 +3533,10 @@ function FormBuilder({ formId }) {
3351
3533
  }
3352
3534
 
3353
3535
  // src/components/Admin/BlogEditorPage.tsx
3354
- import { useState as useState14, useEffect as useEffect11 } from "react";
3536
+ import { useState as useState15, useEffect as useEffect11 } from "react";
3355
3537
 
3356
3538
  // src/components/ui/image-upload.tsx
3357
- import { useState as useState10, useRef as useRef3, useCallback as useCallback3 } from "react";
3539
+ import { useState as useState11, useRef as useRef4, useCallback as useCallback3 } from "react";
3358
3540
  import { Upload as Upload3, X as X8, ImageIcon as ImageIcon2, AlertCircle as AlertCircle2 } from "lucide-react";
3359
3541
  import Image3 from "next/image";
3360
3542
  import { jsx as jsx26, jsxs as jsxs18 } from "react/jsx-runtime";
@@ -3369,11 +3551,11 @@ function ImageUpload({
3369
3551
  // 10MB default
3370
3552
  acceptedTypes = ["image/jpeg", "image/png", "image/gif", "image/webp"]
3371
3553
  }) {
3372
- const [isDragOver, setIsDragOver] = useState10(false);
3373
- const [isUploading, setIsUploading] = useState10(false);
3374
- const [uploadProgress, setUploadProgress] = useState10(0);
3375
- const [error, setError] = useState10(null);
3376
- const fileInputRef = useRef3(null);
3554
+ const [isDragOver, setIsDragOver] = useState11(false);
3555
+ const [isUploading, setIsUploading] = useState11(false);
3556
+ const [uploadProgress, setUploadProgress] = useState11(0);
3557
+ const [error, setError] = useState11(null);
3558
+ const fileInputRef = useRef4(null);
3377
3559
  const handleFileSelect = useCallback3(async (file) => {
3378
3560
  setError(null);
3379
3561
  setUploadProgress(0);
@@ -3555,10 +3737,10 @@ function ImageUpload({
3555
3737
 
3556
3738
  // src/components/Admin/BlogEditorPage.tsx
3557
3739
  import { X as X12, Save as Save2, AlertCircle as AlertCircle3 } from "lucide-react";
3558
- import { useRouter as useRouter3 } from "next/navigation";
3740
+ import { useRouter as useRouter4 } from "next/navigation";
3559
3741
 
3560
3742
  // src/components/Admin/TagAutocomplete.tsx
3561
- import { useState as useState11, useEffect as useEffect8, useRef as useRef4, useCallback as useCallback4 } from "react";
3743
+ import { useState as useState12, useEffect as useEffect8, useRef as useRef5, useCallback as useCallback4 } from "react";
3562
3744
  import { X as X9, Plus as Plus4, Search as Search2 } from "lucide-react";
3563
3745
  import { Fragment as Fragment4, jsx as jsx27, jsxs as jsxs19 } from "react/jsx-runtime";
3564
3746
  function TagAutocomplete({
@@ -3567,13 +3749,13 @@ function TagAutocomplete({
3567
3749
  placeholder = "Search or create tags...",
3568
3750
  className = ""
3569
3751
  }) {
3570
- const [inputValue, setInputValue] = useState11("");
3571
- const [suggestions, setSuggestions] = useState11([]);
3572
- const [isLoading, setIsLoading] = useState11(false);
3573
- const [showSuggestions, setShowSuggestions] = useState11(false);
3574
- const [isCreating, setIsCreating] = useState11(false);
3575
- const inputRef = useRef4(null);
3576
- const suggestionsRef = useRef4(null);
3752
+ const [inputValue, setInputValue] = useState12("");
3753
+ const [suggestions, setSuggestions] = useState12([]);
3754
+ const [isLoading, setIsLoading] = useState12(false);
3755
+ const [showSuggestions, setShowSuggestions] = useState12(false);
3756
+ const [isCreating, setIsCreating] = useState12(false);
3757
+ const inputRef = useRef5(null);
3758
+ const suggestionsRef = useRef5(null);
3577
3759
  const fetchSuggestions = useCallback4(async (query) => {
3578
3760
  if (!query.trim()) {
3579
3761
  setSuggestions([]);
@@ -3719,7 +3901,10 @@ function TagAutocomplete({
3719
3901
  "div",
3720
3902
  {
3721
3903
  className: "px-4 py-2 hover:bg-gray-100 cursor-pointer text-sm",
3722
- onClick: () => handleSuggestionSelect(tag),
3904
+ onMouseDown: (e) => {
3905
+ e.preventDefault();
3906
+ handleSuggestionSelect(tag);
3907
+ },
3723
3908
  children: tag.name
3724
3909
  },
3725
3910
  tag.id
@@ -3735,7 +3920,10 @@ function TagAutocomplete({
3735
3920
  "div",
3736
3921
  {
3737
3922
  className: "px-4 py-2 hover:bg-gray-100 cursor-pointer text-sm text-gray-700 flex items-center",
3738
- onClick: handleCreateTag,
3923
+ onMouseDown: (e) => {
3924
+ e.preventDefault();
3925
+ handleCreateTag();
3926
+ },
3739
3927
  children: [
3740
3928
  /* @__PURE__ */ jsx27(Plus4, { className: "h-3 w-3 mr-2" }),
3741
3929
  'Create "',
@@ -3751,7 +3939,7 @@ function TagAutocomplete({
3751
3939
 
3752
3940
  // src/components/Admin/JoditRichText.tsx
3753
3941
  import dynamic from "next/dynamic";
3754
- import { useMemo } from "react";
3942
+ import { useMemo as useMemo2 } from "react";
3755
3943
  import "jodit/es2021/jodit.min.css";
3756
3944
  import { jsx as jsx28 } from "react/jsx-runtime";
3757
3945
  var JoditEditor = dynamic(() => import("jodit-react").then((m) => m.default), {
@@ -3759,7 +3947,7 @@ var JoditEditor = dynamic(() => import("jodit-react").then((m) => m.default), {
3759
3947
  loading: () => /* @__PURE__ */ jsx28("div", { className: "min-h-[300px] rounded-md border border-gray-200 bg-gray-50 animate-pulse" })
3760
3948
  });
3761
3949
  function JoditRichText({ value, onChange, placeholder, minHeight = 400 }) {
3762
- const config = useMemo(
3950
+ const config = useMemo2(
3763
3951
  () => ({
3764
3952
  readonly: false,
3765
3953
  placeholder: placeholder ?? "",
@@ -3823,8 +4011,8 @@ function JoditRichText({ value, onChange, placeholder, minHeight = 400 }) {
3823
4011
  }
3824
4012
 
3825
4013
  // src/components/Admin/CategoryAutocomplete.tsx
3826
- import { useState as useState12, useEffect as useEffect9, useRef as useRef5 } from "react";
3827
- import { X as X10, Plus as Plus5, Search as Search3, Check as Check4 } from "lucide-react";
4014
+ import { useState as useState13, useEffect as useEffect9, useRef as useRef6 } from "react";
4015
+ import { X as X10, Plus as Plus5, Search as Search3, Check as Check5 } from "lucide-react";
3828
4016
  import { Fragment as Fragment5, jsx as jsx29, jsxs as jsxs20 } from "react/jsx-runtime";
3829
4017
  function CategoryAutocomplete({
3830
4018
  selectedCategory,
@@ -3832,13 +4020,13 @@ function CategoryAutocomplete({
3832
4020
  placeholder = "Search or create category...",
3833
4021
  className = ""
3834
4022
  }) {
3835
- const [inputValue, setInputValue] = useState12("");
3836
- const [suggestions, setSuggestions] = useState12([]);
3837
- const [isLoading, setIsLoading] = useState12(false);
3838
- const [showSuggestions, setShowSuggestions] = useState12(false);
3839
- const [isCreating, setIsCreating] = useState12(false);
3840
- const inputRef = useRef5(null);
3841
- const suggestionsRef = useRef5(null);
4023
+ const [inputValue, setInputValue] = useState13("");
4024
+ const [suggestions, setSuggestions] = useState13([]);
4025
+ const [isLoading, setIsLoading] = useState13(false);
4026
+ const [showSuggestions, setShowSuggestions] = useState13(false);
4027
+ const [isCreating, setIsCreating] = useState13(false);
4028
+ const inputRef = useRef6(null);
4029
+ const suggestionsRef = useRef6(null);
3842
4030
  const fetchSuggestions = async (query) => {
3843
4031
  if (!query.trim()) {
3844
4032
  setSuggestions([]);
@@ -3979,10 +4167,13 @@ function CategoryAutocomplete({
3979
4167
  "div",
3980
4168
  {
3981
4169
  className: "px-4 py-2 hover:bg-gray-100 cursor-pointer text-sm flex items-center justify-between",
3982
- onClick: () => handleSuggestionSelect(category),
4170
+ onMouseDown: (e) => {
4171
+ e.preventDefault();
4172
+ handleSuggestionSelect(category);
4173
+ },
3983
4174
  children: [
3984
4175
  category.name,
3985
- selectedCategory === category.name && /* @__PURE__ */ jsx29(Check4, { className: "h-4 w-4 text-green-500" })
4176
+ selectedCategory === category.name && /* @__PURE__ */ jsx29(Check5, { className: "h-4 w-4 text-green-500" })
3986
4177
  ]
3987
4178
  },
3988
4179
  category.id
@@ -3998,7 +4189,10 @@ function CategoryAutocomplete({
3998
4189
  "div",
3999
4190
  {
4000
4191
  className: "px-4 py-2 hover:bg-gray-100 cursor-pointer text-sm text-gray-700 flex items-center",
4001
- onClick: handleCreateCategory,
4192
+ onMouseDown: (e) => {
4193
+ e.preventDefault();
4194
+ handleCreateCategory();
4195
+ },
4002
4196
  children: [
4003
4197
  /* @__PURE__ */ jsx29(Plus5, { className: "h-3 w-3 mr-2" }),
4004
4198
  'Create "',
@@ -4013,8 +4207,8 @@ function CategoryAutocomplete({
4013
4207
  }
4014
4208
 
4015
4209
  // src/components/Admin/UserAutocomplete.tsx
4016
- import { useState as useState13, useEffect as useEffect10, useRef as useRef6 } from "react";
4017
- import { X as X11, Search as Search4, Check as Check5 } from "lucide-react";
4210
+ import { useState as useState14, useEffect as useEffect10, useRef as useRef7 } from "react";
4211
+ import { X as X11, Search as Search4, Check as Check6 } from "lucide-react";
4018
4212
  import { jsx as jsx30, jsxs as jsxs21 } from "react/jsx-runtime";
4019
4213
  function UserAutocomplete({
4020
4214
  selectedUserId,
@@ -4022,12 +4216,12 @@ function UserAutocomplete({
4022
4216
  placeholder = "Select author...",
4023
4217
  className = ""
4024
4218
  }) {
4025
- const [inputValue, setInputValue] = useState13("");
4026
- const [suggestions, setSuggestions] = useState13([]);
4027
- const [isLoading, setIsLoading] = useState13(false);
4028
- const [showSuggestions, setShowSuggestions] = useState13(false);
4029
- const inputRef = useRef6(null);
4030
- const suggestionsRef = useRef6(null);
4219
+ const [inputValue, setInputValue] = useState14("");
4220
+ const [suggestions, setSuggestions] = useState14([]);
4221
+ const [isLoading, setIsLoading] = useState14(false);
4222
+ const [showSuggestions, setShowSuggestions] = useState14(false);
4223
+ const inputRef = useRef7(null);
4224
+ const suggestionsRef = useRef7(null);
4031
4225
  const fetchSuggestions = async (query) => {
4032
4226
  setIsLoading(true);
4033
4227
  try {
@@ -4125,13 +4319,16 @@ function UserAutocomplete({
4125
4319
  "div",
4126
4320
  {
4127
4321
  className: "px-4 py-2 hover:bg-gray-100 cursor-pointer text-sm flex items-center justify-between",
4128
- onClick: () => handleSuggestionSelect(user),
4322
+ onMouseDown: (e) => {
4323
+ e.preventDefault();
4324
+ handleSuggestionSelect(user);
4325
+ },
4129
4326
  children: [
4130
4327
  /* @__PURE__ */ jsxs21("div", { className: "flex flex-col", children: [
4131
4328
  /* @__PURE__ */ jsx30("span", { className: "font-medium", children: user.name }),
4132
4329
  /* @__PURE__ */ jsx30("span", { className: "text-xs text-gray-500", children: user.email })
4133
4330
  ] }),
4134
- selectedUserId === user.id && /* @__PURE__ */ jsx30(Check5, { className: "h-4 w-4 text-green-500" })
4331
+ selectedUserId === user.id && /* @__PURE__ */ jsx30(Check6, { className: "h-4 w-4 text-green-500" })
4135
4332
  ]
4136
4333
  },
4137
4334
  user.id
@@ -4144,39 +4341,39 @@ function UserAutocomplete({
4144
4341
  // src/components/Admin/BlogEditorPage.tsx
4145
4342
  import { jsx as jsx31, jsxs as jsxs22 } from "react/jsx-runtime";
4146
4343
  function BlogEditor({ existingBlog }) {
4147
- const [title, setTitle] = useState14(existingBlog?.title || "");
4148
- const [slug, setSlug] = useState14(existingBlog?.slug || "");
4149
- const [coverImage, setCoverImage] = useState14(
4344
+ const [title, setTitle] = useState15(existingBlog?.title || "");
4345
+ const [slug, setSlug] = useState15(existingBlog?.slug || "");
4346
+ const [coverImage, setCoverImage] = useState15(
4150
4347
  existingBlog?.coverImage || null
4151
4348
  );
4152
- const [ogImage, setOgImage] = useState14(
4349
+ const [ogImage, setOgImage] = useState15(
4153
4350
  existingBlog?.seo?.ogImage || existingBlog?.ogImage || null
4154
4351
  );
4155
- const [metaTitle, setMetaTitle] = useState14(existingBlog?.seo?.title || "");
4156
- const [metaDescription, setMetaDescription] = useState14(
4352
+ const [metaTitle, setMetaTitle] = useState15(existingBlog?.seo?.title || "");
4353
+ const [metaDescription, setMetaDescription] = useState15(
4157
4354
  existingBlog?.seo?.description || ""
4158
4355
  );
4159
- const [metaKeywords, setMetaKeywords] = useState14(
4356
+ const [metaKeywords, setMetaKeywords] = useState15(
4160
4357
  existingBlog?.seo?.keywords || ""
4161
4358
  );
4162
- const [published, setPublished] = useState14(existingBlog?.published || false);
4163
- const [tags, setTags] = useState14(
4359
+ const [published, setPublished] = useState15(existingBlog?.published || false);
4360
+ const [tags, setTags] = useState15(
4164
4361
  existingBlog?.tags?.map((tag) => tag.name) || []
4165
4362
  );
4166
- const [category, setCategory] = useState14(
4363
+ const [category, setCategory] = useState15(
4167
4364
  existingBlog?.category?.name || null
4168
4365
  );
4169
- const [authorId, setAuthorId] = useState14(
4366
+ const [authorId, setAuthorId] = useState15(
4170
4367
  existingBlog?.authorId || null
4171
4368
  );
4172
- const [content, setContent] = useState14(existingBlog?.content || "");
4173
- const [createdAt, setCreatedAt] = useState14(
4369
+ const [content, setContent] = useState15(existingBlog?.content || "");
4370
+ const [createdAt, setCreatedAt] = useState15(
4174
4371
  existingBlog?.createdAt ? new Date(existingBlog.createdAt).toISOString().slice(0, 16) : (/* @__PURE__ */ new Date()).toISOString().slice(0, 16)
4175
4372
  );
4176
- const [errors, setErrors] = useState14([]);
4177
- const [isLoading, setIsLoading] = useState14(false);
4178
- const [isSaving, setIsSaving] = useState14(false);
4179
- const router = useRouter3();
4373
+ const [errors, setErrors] = useState15([]);
4374
+ const [isLoading, setIsLoading] = useState15(false);
4375
+ const [isSaving, setIsSaving] = useState15(false);
4376
+ const router = useRouter4();
4180
4377
  useEffect11(() => {
4181
4378
  if (title && !slug) {
4182
4379
  const generatedSlug = title.toLowerCase().replace(/[^a-z0-9]+/g, "-").replace(/(^-|-$)/g, "");
@@ -4302,11 +4499,25 @@ function BlogEditor({ existingBlog }) {
4302
4499
  ),
4303
4500
  /* @__PURE__ */ jsx31("span", { className: "text-xs text-gray-300", children: "Published" })
4304
4501
  ] }),
4502
+ /* @__PURE__ */ jsxs22(
4503
+ Button,
4504
+ {
4505
+ size: "icon",
4506
+ className: "md:hidden h-8 w-8 bg-white text-gray-800 hover:bg-gray-100 border-0",
4507
+ onClick: () => handleSave(published),
4508
+ disabled: isSaving,
4509
+ title: isSaving ? "Saving..." : "Save",
4510
+ children: [
4511
+ /* @__PURE__ */ jsx31(Save2, { className: "h-4 w-4" }),
4512
+ /* @__PURE__ */ jsx31("span", { className: "sr-only", children: isSaving ? "Saving..." : "Save" })
4513
+ ]
4514
+ }
4515
+ ),
4305
4516
  /* @__PURE__ */ jsxs22(
4306
4517
  Button,
4307
4518
  {
4308
4519
  size: "sm",
4309
- className: "flex items-center bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
4520
+ className: "hidden md:inline-flex items-center bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
4310
4521
  onClick: () => handleSave(published),
4311
4522
  disabled: isSaving,
4312
4523
  children: [
@@ -4315,12 +4526,26 @@ function BlogEditor({ existingBlog }) {
4315
4526
  ]
4316
4527
  }
4317
4528
  ),
4529
+ /* @__PURE__ */ jsxs22(
4530
+ Button,
4531
+ {
4532
+ variant: "outline",
4533
+ size: "icon",
4534
+ className: "md:hidden h-8 w-8 bg-white text-gray-800 hover:bg-gray-100 border-0",
4535
+ onClick: () => router.back(),
4536
+ title: "Close",
4537
+ children: [
4538
+ /* @__PURE__ */ jsx31(X12, { className: "h-4 w-4" }),
4539
+ /* @__PURE__ */ jsx31("span", { className: "sr-only", children: "Close" })
4540
+ ]
4541
+ }
4542
+ ),
4318
4543
  /* @__PURE__ */ jsxs22(
4319
4544
  Button,
4320
4545
  {
4321
4546
  variant: "outline",
4322
4547
  size: "sm",
4323
- className: "flex items-center bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
4548
+ className: "hidden md:inline-flex items-center bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
4324
4549
  onClick: () => router.back(),
4325
4550
  children: [
4326
4551
  /* @__PURE__ */ jsx31(X12, { className: "h-4 w-4 mr-1" }),
@@ -4502,10 +4727,10 @@ function BlogEditor({ existingBlog }) {
4502
4727
  }
4503
4728
 
4504
4729
  // src/components/Admin/AnalyticsChart.tsx
4505
- import { useEffect as useEffect12, useRef as useRef7 } from "react";
4730
+ import { useEffect as useEffect12, useRef as useRef8 } from "react";
4506
4731
  import { jsx as jsx32, jsxs as jsxs23 } from "react/jsx-runtime";
4507
4732
  function AnalyticsChart({ data, title, type }) {
4508
- const canvasRef = useRef7(null);
4733
+ const canvasRef = useRef8(null);
4509
4734
  useEffect12(() => {
4510
4735
  if (!canvasRef.current || !data.length) return;
4511
4736
  const ctx = canvasRef.current.getContext("2d");
@@ -4741,14 +4966,14 @@ function AnalyticsExclusion() {
4741
4966
  }
4742
4967
 
4743
4968
  // src/components/Admin/ComponentSettings.tsx
4744
- import { useState as useState15, useEffect as useEffect14 } from "react";
4969
+ import { useState as useState16, useEffect as useEffect14 } from "react";
4745
4970
  import { jsx as jsx37, jsxs as jsxs28 } from "react/jsx-runtime";
4746
4971
  function EntitySelect({
4747
4972
  prop,
4748
4973
  value,
4749
4974
  onChange
4750
4975
  }) {
4751
- const [options, setOptions] = useState15([]);
4976
+ const [options, setOptions] = useState16([]);
4752
4977
  useEffect14(() => {
4753
4978
  if (!prop.entity) return;
4754
4979
  fetch(`/api/${prop.entity}`).then((r) => r.ok ? r.json() : { data: [] }).then((res) => setOptions(res.data || res || [])).catch(() => {
@@ -4887,7 +5112,7 @@ function ComponentSettings({
4887
5112
  }
4888
5113
 
4889
5114
  // src/components/Admin/NavbarEditor.tsx
4890
- import { useState as useState16, useEffect as useEffect15 } from "react";
5115
+ import { useState as useState17, useEffect as useEffect15 } from "react";
4891
5116
  import { Plus as Plus6, Trash2 as Trash23, GripVertical, ChevronDown as ChevronDown4, ChevronRight as ChevronRight3, ArrowRight, ArrowLeft as ArrowLeft3 } from "lucide-react";
4892
5117
  import { jsx as jsx38, jsxs as jsxs29 } from "react/jsx-runtime";
4893
5118
  function generateId() {
@@ -4907,8 +5132,8 @@ function NavItemEditor({
4907
5132
  canMoveUp,
4908
5133
  canMoveDown
4909
5134
  }) {
4910
- const [expanded, setExpanded] = useState16(false);
4911
- const [pages, setPages] = useState16([]);
5135
+ const [expanded, setExpanded] = useState17(false);
5136
+ const [pages, setPages] = useState17([]);
4912
5137
  useEffect15(() => {
4913
5138
  if (!expanded) return;
4914
5139
  fetch("/api/pages").then((r) => r.ok ? r.json() : []).then((data) => {
@@ -5177,9 +5402,9 @@ function NavbarEditor({ config, onChange }) {
5177
5402
 
5178
5403
  // src/admin/pages/SignInPage.tsx
5179
5404
  import Link5 from "next/link";
5180
- import { useState as useState17, useEffect as useEffect16 } from "react";
5405
+ import { useState as useState18, useEffect as useEffect16 } from "react";
5181
5406
  import { signIn, useSession as useSession3 } from "next-auth/react";
5182
- import { useRouter as useRouter4 } from "next/navigation";
5407
+ import { useRouter as useRouter5 } from "next/navigation";
5183
5408
 
5184
5409
  // src/components/Admin/AuthPageLayout.tsx
5185
5410
  import Image5 from "next/image";
@@ -5237,11 +5462,11 @@ function AuthPageLayout({ children }) {
5237
5462
  // src/admin/pages/SignInPage.tsx
5238
5463
  import { jsx as jsx41, jsxs as jsxs32 } from "react/jsx-runtime";
5239
5464
  var SigninPage = () => {
5240
- const [email, setEmail] = useState17("");
5241
- const [password, setPassword] = useState17("");
5242
- const [error, setError] = useState17("");
5243
- const [loading, setLoading] = useState17(false);
5244
- const router = useRouter4();
5465
+ const [email, setEmail] = useState18("");
5466
+ const [password, setPassword] = useState18("");
5467
+ const [error, setError] = useState18("");
5468
+ const [loading, setLoading] = useState18(false);
5469
+ const router = useRouter5();
5245
5470
  const { status } = useSession3();
5246
5471
  useEffect16(() => {
5247
5472
  if (status === "authenticated") {
@@ -5326,13 +5551,13 @@ var SigninPage = () => {
5326
5551
  var SignInPage_default = SigninPage;
5327
5552
 
5328
5553
  // src/admin/pages/ForgotPasswordPage.tsx
5329
- import { useState as useState18 } from "react";
5554
+ import { useState as useState19 } from "react";
5330
5555
  import Link6 from "next/link";
5331
5556
  import { jsx as jsx42, jsxs as jsxs33 } from "react/jsx-runtime";
5332
5557
  function ForgotPasswordPage() {
5333
- const [email, setEmail] = useState18("");
5334
- const [loading, setLoading] = useState18(false);
5335
- const [message, setMessage] = useState18("");
5558
+ const [email, setEmail] = useState19("");
5559
+ const [loading, setLoading] = useState19(false);
5560
+ const [message, setMessage] = useState19("");
5336
5561
  const handleSubmit = async (e) => {
5337
5562
  e.preventDefault();
5338
5563
  if (!email.trim()) return;
@@ -5374,16 +5599,16 @@ function ForgotPasswordPage() {
5374
5599
  }
5375
5600
 
5376
5601
  // src/admin/pages/ResetPasswordPage.tsx
5377
- import { useState as useState19, useEffect as useEffect17, Suspense } from "react";
5602
+ import { useState as useState20, useEffect as useEffect17, Suspense } from "react";
5378
5603
  import { useSearchParams } from "next/navigation";
5379
5604
  import Link7 from "next/link";
5380
5605
  import { jsx as jsx43, jsxs as jsxs34 } from "react/jsx-runtime";
5381
5606
  function ResetPasswordPageContent() {
5382
5607
  const searchParams = useSearchParams();
5383
5608
  const token = searchParams.get("token");
5384
- const [formData, setFormData] = useState19({ password: "", confirmPassword: "" });
5385
- const [loading, setLoading] = useState19(false);
5386
- const [message, setMessage] = useState19("");
5609
+ const [formData, setFormData] = useState20({ password: "", confirmPassword: "" });
5610
+ const [loading, setLoading] = useState20(false);
5611
+ const [message, setMessage] = useState20("");
5387
5612
  useEffect17(() => {
5388
5613
  if (!token) setMessage("Invalid reset link. Token is missing.");
5389
5614
  }, [token]);
@@ -5453,18 +5678,18 @@ function ResetPasswordPage() {
5453
5678
  }
5454
5679
 
5455
5680
  // src/admin/pages/InvitePage.tsx
5456
- import { useState as useState20, useEffect as useEffect18, Suspense as Suspense2 } from "react";
5681
+ import { useState as useState21, useEffect as useEffect18, Suspense as Suspense2 } from "react";
5457
5682
  import { useSearchParams as useSearchParams2 } from "next/navigation";
5458
5683
  import { jsx as jsx44, jsxs as jsxs35 } from "react/jsx-runtime";
5459
5684
  function InvitePageContent() {
5460
5685
  const searchParams = useSearchParams2();
5461
5686
  const token = searchParams.get("token");
5462
- const [formData, setFormData] = useState20({
5687
+ const [formData, setFormData] = useState21({
5463
5688
  password: "",
5464
5689
  confirmPassword: ""
5465
5690
  });
5466
- const [loading, setLoading] = useState20(false);
5467
- const [message, setMessage] = useState20("");
5691
+ const [loading, setLoading] = useState21(false);
5692
+ const [message, setMessage] = useState21("");
5468
5693
  useEffect18(() => {
5469
5694
  if (!token) {
5470
5695
  setMessage("Invalid invite link. Token is missing.");
@@ -5538,21 +5763,62 @@ function InvitePage() {
5538
5763
 
5539
5764
  // src/admin/pages/DashboardPage.tsx
5540
5765
  import { useSession as useSession4 } from "next-auth/react";
5541
- import { useEffect as useEffect19, useState as useState21 } from "react";
5542
- import { Users as Users4, Eye as Eye3, MousePointer, Globe, FileText, ClipboardList as ClipboardList2, UserCheck, TrendingUp, BarChart3, Activity } from "lucide-react";
5766
+ import { useContext as useContext3, useEffect as useEffect19, useMemo as useMemo3, useState as useState22 } from "react";
5767
+ import { useRouter as useRouter6 } from "next/navigation";
5768
+ import { Chart as ChartJS2, ArcElement, Tooltip as Tooltip2, Legend as Legend2 } from "chart.js";
5769
+ import { Doughnut } from "react-chartjs-2";
5770
+ import { Users as Users4, Eye as Eye2, MousePointer, Globe, FileText, ClipboardList as ClipboardList2, UserCheck, TrendingUp, BarChart3, Activity } from "lucide-react";
5543
5771
  import { Fragment as Fragment6, jsx as jsx45, jsxs as jsxs36 } from "react/jsx-runtime";
5772
+ ChartJS2.register(ArcElement, Tooltip2, Legend2);
5544
5773
  function DashboardPage() {
5545
5774
  const { data: session } = useSession4();
5546
- const [analyticsData, setAnalyticsData] = useState21(null);
5547
- const [dashboardStats, setDashboardStats] = useState21(null);
5548
- const [loading, setLoading] = useState21({ analytics: true, stats: true });
5549
- const [analyticsEnabled, setAnalyticsEnabled] = useState21(false);
5775
+ const router = useRouter6();
5776
+ const { storeEnabled } = useContext3(AdminConfigContext);
5777
+ const [analyticsData, setAnalyticsData] = useState22(null);
5778
+ const [ecommerceData, setEcommerceData] = useState22(null);
5779
+ const [dashboardStats, setDashboardStats] = useState22(null);
5780
+ const [loading, setLoading] = useState22({ analytics: true, stats: true, ecommerce: true });
5781
+ const [analyticsEnabled, setAnalyticsEnabled] = useState22(false);
5782
+ const [days, setDays] = useState22(30);
5783
+ const [activeTab, setActiveTab] = useState22("overview");
5784
+ const formatMoney4 = useMemo3(
5785
+ () => (value) => new Intl.NumberFormat(void 0, {
5786
+ style: "currency",
5787
+ currency: "INR",
5788
+ maximumFractionDigits: 0
5789
+ }).format(value || 0),
5790
+ []
5791
+ );
5792
+ const safePct = (v, max) => max > 0 ? Math.max(6, Math.round(v / max * 100)) : 0;
5793
+ const productPalette = ["#2563eb", "#0ea5e9", "#14b8a6", "#22c55e", "#eab308", "#f97316"];
5794
+ const salesBreakdownPalette = {
5795
+ sales: "#22c55e",
5796
+ returns: "#ef4444",
5797
+ replacements: "#f59e0b"
5798
+ };
5799
+ const contactTypeColor = (type) => {
5800
+ const t = type.trim().toLowerCase();
5801
+ if (t === "customer") return "#2563eb";
5802
+ if (t === "lead") return "#a855f7";
5803
+ if (t === "vendor") return "#14b8a6";
5804
+ return "#6b7280";
5805
+ };
5806
+ const metricBarColor = (label) => {
5807
+ const key = label.toLowerCase();
5808
+ if (key.includes("contact")) return "bg-blue-500";
5809
+ if (key.includes("submission")) return "bg-purple-500";
5810
+ if (key.includes("net sales")) return "bg-green-500";
5811
+ if (key.includes("gross sales")) return "bg-emerald-500";
5812
+ if (key.includes("return")) return "bg-red-500";
5813
+ return "bg-gray-600";
5814
+ };
5550
5815
  useEffect19(() => {
5551
5816
  const fetchData = async () => {
5552
- const analyticsPromise = fetch("/api/analytics?days=30");
5817
+ const analyticsPromise = fetch(`/api/analytics?days=${days}`);
5553
5818
  const statsPromise = fetch("/api/dashboard/stats");
5819
+ const ecommercePromise = storeEnabled ? fetch(`/api/dashboard/ecommerce?days=${days}`) : Promise.resolve(null);
5554
5820
  try {
5555
- const [analyticsResponse, statsResponse] = await Promise.all([analyticsPromise, statsPromise]);
5821
+ const [analyticsResponse, statsResponse, ecommerceResponse] = await Promise.all([analyticsPromise, statsPromise, ecommercePromise]);
5556
5822
  if (analyticsResponse.ok) {
5557
5823
  const data = await analyticsResponse.json();
5558
5824
  setAnalyticsData(data);
@@ -5570,15 +5836,22 @@ function DashboardPage() {
5570
5836
  const stats = await statsResponse.json();
5571
5837
  setDashboardStats(stats);
5572
5838
  }
5839
+ if (ecommerceResponse && ecommerceResponse.ok) {
5840
+ const ecommerce = await ecommerceResponse.json();
5841
+ setEcommerceData(ecommerce);
5842
+ } else {
5843
+ setEcommerceData(null);
5844
+ }
5573
5845
  } catch (error) {
5574
5846
  setAnalyticsEnabled(false);
5847
+ setEcommerceData(null);
5575
5848
  } finally {
5576
- setLoading({ analytics: false, stats: false });
5849
+ setLoading({ analytics: false, stats: false, ecommerce: false });
5577
5850
  }
5578
5851
  };
5579
5852
  fetchData();
5580
- }, []);
5581
- const isLoading = loading.analytics || loading.stats;
5853
+ }, [days, storeEnabled]);
5854
+ const isLoading = loading.analytics || loading.stats || storeEnabled && loading.ecommerce;
5582
5855
  return /* @__PURE__ */ jsxs36("div", { className: "min-w-0 rounded-lg bg-white shadow-md", children: [
5583
5856
  /* @__PURE__ */ jsx45("div", { className: "bg-gray-800 border-b border-gray-700 px-4 py-2.5 rounded-t-lg", children: /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between", children: [
5584
5857
  /* @__PURE__ */ jsxs36("div", { children: [
@@ -5594,13 +5867,54 @@ function DashboardPage() {
5594
5867
  ] }) })
5595
5868
  ] }) }),
5596
5869
  /* @__PURE__ */ jsxs36("div", { className: "min-w-0 p-4 bg-gray-50", children: [
5597
- /* @__PURE__ */ jsxs36("div", { className: "mb-4", children: [
5598
- /* @__PURE__ */ jsxs36("div", { className: "flex items-center mb-2", children: [
5870
+ /* @__PURE__ */ jsxs36("div", { className: "flex flex-wrap items-center justify-between gap-2 mb-3", children: [
5871
+ /* @__PURE__ */ jsxs36("div", { className: "flex items-center gap-2", children: [
5872
+ /* @__PURE__ */ jsx45(
5873
+ "button",
5874
+ {
5875
+ onClick: () => setActiveTab("overview"),
5876
+ className: `text-xs px-2 py-1 rounded border ${activeTab === "overview" ? "bg-gray-800 text-white border-gray-800" : "bg-white text-gray-700 border-gray-300"}`,
5877
+ children: "Overview"
5878
+ }
5879
+ ),
5880
+ /* @__PURE__ */ jsx45(
5881
+ "button",
5882
+ {
5883
+ onClick: () => setActiveTab("crm"),
5884
+ className: `text-xs px-2 py-1 rounded border ${activeTab === "crm" ? "bg-gray-800 text-white border-gray-800" : "bg-white text-gray-700 border-gray-300"}`,
5885
+ children: "CRM / Engagement"
5886
+ }
5887
+ ),
5888
+ storeEnabled && /* @__PURE__ */ jsx45(
5889
+ "button",
5890
+ {
5891
+ onClick: () => setActiveTab("sales"),
5892
+ className: `text-xs px-2 py-1 rounded border ${activeTab === "sales" ? "bg-gray-800 text-white border-gray-800" : "bg-white text-gray-700 border-gray-300"}`,
5893
+ children: "Sales"
5894
+ }
5895
+ )
5896
+ ] }),
5897
+ /* @__PURE__ */ jsxs36(
5898
+ "select",
5899
+ {
5900
+ value: days,
5901
+ onChange: (e) => setDays(Number(e.target.value)),
5902
+ className: "border border-gray-300 text-xs rounded px-2 py-1 bg-white",
5903
+ children: [
5904
+ /* @__PURE__ */ jsx45("option", { value: 7, children: "Last 7 days" }),
5905
+ /* @__PURE__ */ jsx45("option", { value: 30, children: "Last 30 days" }),
5906
+ /* @__PURE__ */ jsx45("option", { value: 90, children: "Last 90 days" })
5907
+ ]
5908
+ }
5909
+ )
5910
+ ] }),
5911
+ activeTab === "overview" && /* @__PURE__ */ jsxs36("div", { className: "mb-5", children: [
5912
+ /* @__PURE__ */ jsxs36("div", { className: "flex items-center mb-3", children: [
5599
5913
  /* @__PURE__ */ jsx45(BarChart3, { className: "w-4 h-4 text-gray-600 mr-2" }),
5600
- /* @__PURE__ */ jsx45("h2", { className: "text-sm font-semibold text-gray-800", children: "Overview" })
5914
+ /* @__PURE__ */ jsx45("h2", { className: "text-sm font-semibold text-gray-800", children: "Contacts & Forms" })
5601
5915
  ] }),
5602
- /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-3", children: [
5603
- /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
5916
+ /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-4", children: [
5917
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded border border-gray-200 p-3 shadow-sm", children: [
5604
5918
  /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between mb-1.5", children: [
5605
5919
  /* @__PURE__ */ jsx45("p", { className: "text-xs font-medium text-gray-600", children: "Total Contacts" }),
5606
5920
  /* @__PURE__ */ jsx45("div", { className: "p-1 bg-gray-200 rounded", children: /* @__PURE__ */ jsx45(Users4, { className: "w-3.5 h-3.5 text-gray-600" }) })
@@ -5616,7 +5930,7 @@ function DashboardPage() {
5616
5930
  ] })
5617
5931
  ] })
5618
5932
  ] }),
5619
- /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
5933
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded border border-gray-200 p-3 shadow-sm", children: [
5620
5934
  /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between mb-1.5", children: [
5621
5935
  /* @__PURE__ */ jsx45("p", { className: "text-xs font-medium text-gray-600", children: "Form Submissions" }),
5622
5936
  /* @__PURE__ */ jsx45("div", { className: "p-1 bg-gray-200 rounded", children: /* @__PURE__ */ jsx45(FileText, { className: "w-3.5 h-3.5 text-gray-600" }) })
@@ -5632,7 +5946,7 @@ function DashboardPage() {
5632
5946
  ] })
5633
5947
  ] })
5634
5948
  ] }),
5635
- /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
5949
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded border border-gray-200 p-3 shadow-sm", children: [
5636
5950
  /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between mb-1.5", children: [
5637
5951
  /* @__PURE__ */ jsx45("p", { className: "text-xs font-medium text-gray-600", children: "Active Forms" }),
5638
5952
  /* @__PURE__ */ jsx45("div", { className: "p-1 bg-gray-200 rounded", children: /* @__PURE__ */ jsx45(ClipboardList2, { className: "w-3.5 h-3.5 text-gray-600" }) })
@@ -5642,7 +5956,7 @@ function DashboardPage() {
5642
5956
  /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-500", children: "Total" })
5643
5957
  ] })
5644
5958
  ] }),
5645
- /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
5959
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded border border-gray-200 p-3 shadow-sm", children: [
5646
5960
  /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between mb-1.5", children: [
5647
5961
  /* @__PURE__ */ jsx45("p", { className: "text-xs font-medium text-gray-600", children: "Registered Users" }),
5648
5962
  /* @__PURE__ */ jsx45("div", { className: "p-1 bg-gray-200 rounded", children: /* @__PURE__ */ jsx45(UserCheck, { className: "w-3.5 h-3.5 text-gray-600" }) })
@@ -5654,8 +5968,151 @@ function DashboardPage() {
5654
5968
  ] })
5655
5969
  ] })
5656
5970
  ] }),
5657
- /* @__PURE__ */ jsx45("div", { className: "border-t-2 border-dotted border-gray-200 my-6" }),
5658
- analyticsEnabled && !isLoading && analyticsData && /* @__PURE__ */ jsxs36(Fragment6, { children: [
5971
+ activeTab === "overview" && !isLoading && /* @__PURE__ */ jsxs36("div", { className: "mb-6 bg-white rounded-lg border border-gray-200 p-4 shadow-sm", children: [
5972
+ /* @__PURE__ */ jsxs36("div", { className: "flex items-center mb-3", children: [
5973
+ /* @__PURE__ */ jsx45(Activity, { className: "w-4 h-4 text-gray-600 mr-2" }),
5974
+ /* @__PURE__ */ jsx45("h3", { className: "text-sm font-semibold text-gray-800", children: "Overview Snapshot" })
5975
+ ] }),
5976
+ /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 lg:grid-cols-2 gap-6", children: [
5977
+ /* @__PURE__ */ jsxs36("div", { children: [
5978
+ /* @__PURE__ */ jsx45("h4", { className: "text-xs font-semibold text-gray-700 mb-2", children: "Contacts & Forms" }),
5979
+ (() => {
5980
+ const rows = [
5981
+ { label: "Contacts (total)", value: dashboardStats?.contacts.total || 0 },
5982
+ { label: "New contacts", value: dashboardStats?.contacts.recent || 0 },
5983
+ { label: "Submissions", value: dashboardStats?.forms.submissions || 0 },
5984
+ { label: "New submissions", value: dashboardStats?.forms.recentSubmissions || 0 }
5985
+ ];
5986
+ const max = Math.max(...rows.map((r) => r.value), 0);
5987
+ return /* @__PURE__ */ jsx45("div", { className: "space-y-2", children: rows.map((r) => /* @__PURE__ */ jsxs36("div", { children: [
5988
+ /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between text-xs mb-1", children: [
5989
+ /* @__PURE__ */ jsx45("span", { className: "text-gray-600", children: r.label }),
5990
+ /* @__PURE__ */ jsx45("span", { className: "font-semibold text-gray-900", children: r.value })
5991
+ ] }),
5992
+ /* @__PURE__ */ jsx45("div", { className: "h-2 rounded bg-gray-100 overflow-hidden", children: /* @__PURE__ */ jsx45("div", { className: `h-2 rounded ${metricBarColor(r.label)}`, style: { width: `${safePct(r.value, max)}%` } }) })
5993
+ ] }, r.label)) });
5994
+ })()
5995
+ ] }),
5996
+ storeEnabled && ecommerceData && /* @__PURE__ */ jsxs36("div", { children: [
5997
+ /* @__PURE__ */ jsx45("h4", { className: "text-xs font-semibold text-gray-700 mb-2", children: "Sales, Returns & Products" }),
5998
+ (() => {
5999
+ const salesBase = Math.max(ecommerceData.kpis.grossSales, 1);
6000
+ const rows = [
6001
+ { label: "Net sales", value: ecommerceData.kpis.netSales, display: formatMoney4(ecommerceData.kpis.netSales) },
6002
+ { label: "Gross sales", value: ecommerceData.kpis.grossSales, display: formatMoney4(ecommerceData.kpis.grossSales) },
6003
+ { label: "Return value", value: ecommerceData.kpis.returnValue, display: formatMoney4(ecommerceData.kpis.returnValue) },
6004
+ { label: "Return rate", value: ecommerceData.kpis.returnRate, display: `${ecommerceData.kpis.returnRate.toFixed(1)}%` }
6005
+ ];
6006
+ const topProduct = ecommerceData.topProducts[0];
6007
+ return /* @__PURE__ */ jsxs36("div", { className: "space-y-2", children: [
6008
+ rows.map((r) => /* @__PURE__ */ jsxs36("div", { children: [
6009
+ /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between text-xs mb-1", children: [
6010
+ /* @__PURE__ */ jsx45("span", { className: "text-gray-600", children: r.label }),
6011
+ /* @__PURE__ */ jsx45("span", { className: "font-semibold text-gray-900", children: r.display })
6012
+ ] }),
6013
+ /* @__PURE__ */ jsx45("div", { className: "h-2 rounded bg-gray-100 overflow-hidden", children: /* @__PURE__ */ jsx45(
6014
+ "div",
6015
+ {
6016
+ className: `h-2 rounded ${metricBarColor(r.label)}`,
6017
+ style: { width: `${r.label === "Return rate" ? Math.max(6, Math.round(r.value)) : safePct(r.value, salesBase)}%` }
6018
+ }
6019
+ ) })
6020
+ ] }, r.label)),
6021
+ topProduct && /* @__PURE__ */ jsxs36("div", { className: "pt-1 text-xs text-gray-600", children: [
6022
+ "Top product: ",
6023
+ /* @__PURE__ */ jsx45("span", { className: "font-medium text-gray-900", children: topProduct.name }),
6024
+ " (",
6025
+ topProduct.units,
6026
+ " units)"
6027
+ ] })
6028
+ ] });
6029
+ })()
6030
+ ] })
6031
+ ] })
6032
+ ] }),
6033
+ activeTab === "overview" && !isLoading && /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 lg:grid-cols-3 gap-6 mb-7", children: [
6034
+ storeEnabled && ecommerceData && /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-200 p-4 shadow-sm", children: [
6035
+ /* @__PURE__ */ jsx45("h3", { className: "text-sm font-semibold text-gray-800 mb-3", children: "Sales vs Returns vs Replacements" }),
6036
+ /* @__PURE__ */ jsx45("div", { className: "h-56", children: /* @__PURE__ */ jsx45(
6037
+ Doughnut,
6038
+ {
6039
+ data: {
6040
+ labels: ["Sales", "Returns", "Replacements"],
6041
+ datasets: [
6042
+ {
6043
+ data: [
6044
+ ecommerceData.salesBreakdown?.sales.value ?? ecommerceData.kpis.grossSales,
6045
+ ecommerceData.salesBreakdown?.returns.value ?? ecommerceData.kpis.returnValue,
6046
+ ecommerceData.salesBreakdown?.replacements.value ?? 0
6047
+ ],
6048
+ backgroundColor: [
6049
+ salesBreakdownPalette.sales,
6050
+ salesBreakdownPalette.returns,
6051
+ salesBreakdownPalette.replacements
6052
+ ],
6053
+ borderWidth: 0
6054
+ }
6055
+ ]
6056
+ },
6057
+ options: {
6058
+ maintainAspectRatio: false,
6059
+ plugins: {
6060
+ legend: { position: "bottom" }
6061
+ }
6062
+ }
6063
+ }
6064
+ ) })
6065
+ ] }),
6066
+ storeEnabled && ecommerceData && /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-200 p-4 shadow-sm", children: [
6067
+ /* @__PURE__ */ jsx45("h3", { className: "text-sm font-semibold text-gray-800 mb-3", children: "Product-wise Sales (Top)" }),
6068
+ /* @__PURE__ */ jsx45("div", { className: "h-56", children: /* @__PURE__ */ jsx45(
6069
+ Doughnut,
6070
+ {
6071
+ data: {
6072
+ labels: ecommerceData.topProducts.map((p) => p.name),
6073
+ datasets: [
6074
+ {
6075
+ data: ecommerceData.topProducts.map((p) => p.sales),
6076
+ backgroundColor: productPalette.slice(0, Math.max(3, ecommerceData.topProducts.length)),
6077
+ borderWidth: 0
6078
+ }
6079
+ ]
6080
+ },
6081
+ options: {
6082
+ maintainAspectRatio: false,
6083
+ plugins: {
6084
+ legend: { position: "bottom" }
6085
+ }
6086
+ }
6087
+ }
6088
+ ) })
6089
+ ] }),
6090
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-200 p-4 shadow-sm", children: [
6091
+ /* @__PURE__ */ jsx45("h3", { className: "text-sm font-semibold text-gray-800 mb-3", children: "Contact Distribution" }),
6092
+ /* @__PURE__ */ jsx45("div", { className: "h-56", children: /* @__PURE__ */ jsx45(
6093
+ Doughnut,
6094
+ {
6095
+ data: {
6096
+ labels: (dashboardStats?.contactTypes?.length ? dashboardStats.contactTypes : [{ type: "unknown", count: dashboardStats?.contacts.total || 0 }]).map((c) => c.type),
6097
+ datasets: [
6098
+ {
6099
+ data: (dashboardStats?.contactTypes?.length ? dashboardStats.contactTypes : [{ type: "unknown", count: dashboardStats?.contacts.total || 0 }]).map((c) => c.count),
6100
+ backgroundColor: (dashboardStats?.contactTypes?.length ? dashboardStats.contactTypes : [{ type: "unknown", count: dashboardStats?.contacts.total || 0 }]).map((c) => contactTypeColor(c.type)),
6101
+ borderWidth: 0
6102
+ }
6103
+ ]
6104
+ },
6105
+ options: {
6106
+ maintainAspectRatio: false,
6107
+ plugins: {
6108
+ legend: { position: "bottom" }
6109
+ }
6110
+ }
6111
+ }
6112
+ ) })
6113
+ ] })
6114
+ ] }),
6115
+ activeTab === "overview" && analyticsEnabled && !isLoading && analyticsData && /* @__PURE__ */ jsxs36(Fragment6, { children: [
5659
6116
  /* @__PURE__ */ jsxs36("div", { className: "mb-4", children: [
5660
6117
  /* @__PURE__ */ jsxs36("div", { className: "flex items-center mb-2", children: [
5661
6118
  /* @__PURE__ */ jsx45(Globe, { className: "w-4 h-4 text-gray-600 mr-2" }),
@@ -5678,7 +6135,7 @@ function DashboardPage() {
5678
6135
  title: "Page Views",
5679
6136
  value: analyticsData.pageViews.toLocaleString(),
5680
6137
  subtitle: "Last 30 days",
5681
- icon: /* @__PURE__ */ jsx45(Eye3, { className: "w-5 h-5" }),
6138
+ icon: /* @__PURE__ */ jsx45(Eye2, { className: "w-5 h-5" }),
5682
6139
  trend: { value: 8.2, isPositive: true }
5683
6140
  }
5684
6141
  ),
@@ -5741,33 +6198,281 @@ function DashboardPage() {
5741
6198
  /* @__PURE__ */ jsx45("div", { className: "border-t-2 border-dotted border-gray-200 my-6" }),
5742
6199
  /* @__PURE__ */ jsx45("div", { className: "mb-6", children: /* @__PURE__ */ jsx45(GeographicMap, { data: analyticsData.geographicData }) })
5743
6200
  ] }),
6201
+ activeTab === "crm" && !isLoading && /* @__PURE__ */ jsxs36(Fragment6, { children: [
6202
+ /* @__PURE__ */ jsxs36("div", { className: "mb-4", children: [
6203
+ /* @__PURE__ */ jsxs36("div", { className: "flex items-center mb-2", children: [
6204
+ /* @__PURE__ */ jsx45(Users4, { className: "w-4 h-4 text-gray-600 mr-2" }),
6205
+ /* @__PURE__ */ jsx45("h2", { className: "text-sm font-semibold text-gray-800", children: "CRM Activity" })
6206
+ ] }),
6207
+ /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-3", children: [
6208
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/contacts"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6209
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "Contacts" }),
6210
+ /* @__PURE__ */ jsx45("p", { className: "text-lg font-bold text-gray-900", children: dashboardStats?.contacts.total || 0 }),
6211
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-green-600", children: [
6212
+ "+",
6213
+ dashboardStats?.contacts.recent || 0,
6214
+ " recent"
6215
+ ] })
6216
+ ] }),
6217
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/forms"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6218
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "Active Forms" }),
6219
+ /* @__PURE__ */ jsx45("p", { className: "text-lg font-bold text-gray-900", children: dashboardStats?.forms.total || 0 })
6220
+ ] }),
6221
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/submissions"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6222
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "Form Submissions" }),
6223
+ /* @__PURE__ */ jsx45("p", { className: "text-lg font-bold text-gray-900", children: dashboardStats?.forms.submissions || 0 }),
6224
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-green-600", children: [
6225
+ "+",
6226
+ dashboardStats?.forms.recentSubmissions || 0,
6227
+ " recent"
6228
+ ] })
6229
+ ] }),
6230
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/blogs"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6231
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "Blogs" }),
6232
+ /* @__PURE__ */ jsx45("p", { className: "text-lg font-bold text-gray-900", children: dashboardStats?.blogs || 0 })
6233
+ ] })
6234
+ ] })
6235
+ ] }),
6236
+ /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 lg:grid-cols-2 gap-6 mb-6", children: [
6237
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-100 p-4 shadow-sm", children: [
6238
+ /* @__PURE__ */ jsx45("h3", { className: "text-base font-semibold text-gray-800 mb-3", children: "Engagement Funnel" }),
6239
+ (() => {
6240
+ const contacts = dashboardStats?.contacts.total || 0;
6241
+ const submissions = dashboardStats?.forms.submissions || 0;
6242
+ const visitors = analyticsData?.visitors || 0;
6243
+ const base = Math.max(visitors, contacts, submissions, 1);
6244
+ const rows = [
6245
+ { label: "Visitors", value: visitors },
6246
+ { label: "Contacts", value: contacts },
6247
+ { label: "Submissions", value: submissions }
6248
+ ];
6249
+ return /* @__PURE__ */ jsxs36("div", { className: "space-y-3", children: [
6250
+ rows.map((r) => /* @__PURE__ */ jsxs36("div", { children: [
6251
+ /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between text-xs mb-1", children: [
6252
+ /* @__PURE__ */ jsx45("span", { className: "text-gray-600", children: r.label }),
6253
+ /* @__PURE__ */ jsx45("span", { className: "font-semibold text-gray-900", children: r.value.toLocaleString() })
6254
+ ] }),
6255
+ /* @__PURE__ */ jsx45("div", { className: "h-2 rounded bg-gray-100 overflow-hidden", children: /* @__PURE__ */ jsx45("div", { className: "h-2 bg-gray-700 rounded", style: { width: `${safePct(r.value, base)}%` } }) })
6256
+ ] }, r.label)),
6257
+ /* @__PURE__ */ jsxs36("div", { className: "pt-1 text-xs text-gray-600", children: [
6258
+ "Contact rate:",
6259
+ " ",
6260
+ /* @__PURE__ */ jsxs36("span", { className: "font-semibold text-gray-900", children: [
6261
+ visitors > 0 ? (contacts / visitors * 100).toFixed(1) : "0.0",
6262
+ "%"
6263
+ ] }),
6264
+ " ",
6265
+ " | Submission rate:",
6266
+ " ",
6267
+ /* @__PURE__ */ jsxs36("span", { className: "font-semibold text-gray-900", children: [
6268
+ visitors > 0 ? (submissions / visitors * 100).toFixed(1) : "0.0",
6269
+ "%"
6270
+ ] })
6271
+ ] })
6272
+ ] });
6273
+ })()
6274
+ ] }),
6275
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-100 p-4 shadow-sm", children: [
6276
+ /* @__PURE__ */ jsx45("h3", { className: "text-base font-semibold text-gray-800 mb-3", children: "CRM Distribution" }),
6277
+ (() => {
6278
+ const contacts = dashboardStats?.contacts.total || 0;
6279
+ const forms = dashboardStats?.forms.total || 0;
6280
+ const blogs = dashboardStats?.blogs || 0;
6281
+ const users = dashboardStats?.users || 0;
6282
+ const base = Math.max(contacts, forms, blogs, users, 1);
6283
+ const rows = [
6284
+ { label: "Contacts", value: contacts },
6285
+ { label: "Forms", value: forms },
6286
+ { label: "Blogs", value: blogs },
6287
+ { label: "Users", value: users }
6288
+ ];
6289
+ return /* @__PURE__ */ jsx45("div", { className: "space-y-2", children: rows.map((r) => /* @__PURE__ */ jsxs36("div", { children: [
6290
+ /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between text-xs mb-1", children: [
6291
+ /* @__PURE__ */ jsx45("span", { className: "text-gray-600", children: r.label }),
6292
+ /* @__PURE__ */ jsx45("span", { className: "font-semibold text-gray-900", children: r.value })
6293
+ ] }),
6294
+ /* @__PURE__ */ jsx45("div", { className: "h-2 rounded bg-gray-100 overflow-hidden", children: /* @__PURE__ */ jsx45("div", { className: "h-2 bg-gray-700 rounded", style: { width: `${safePct(r.value, base)}%` } }) })
6295
+ ] }, r.label)) });
6296
+ })()
6297
+ ] })
6298
+ ] }),
6299
+ analyticsEnabled && analyticsData && /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-100 p-4 shadow-sm mb-2", children: [
6300
+ /* @__PURE__ */ jsx45("h3", { className: "text-base font-semibold text-gray-800 mb-3", children: "Top Content & Sources" }),
6301
+ /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 lg:grid-cols-2 gap-6", children: [
6302
+ /* @__PURE__ */ jsxs36("div", { children: [
6303
+ /* @__PURE__ */ jsx45("p", { className: "text-xs font-semibold text-gray-700 mb-2", children: "Top Pages" }),
6304
+ /* @__PURE__ */ jsx45("div", { className: "space-y-1", children: analyticsData.topPages.slice(0, 5).map((page, index) => /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between text-xs", children: [
6305
+ /* @__PURE__ */ jsx45("span", { className: "text-gray-600 truncate max-w-[75%]", children: page.page }),
6306
+ /* @__PURE__ */ jsx45("span", { className: "font-semibold text-gray-900", children: page.views.toLocaleString() })
6307
+ ] }, index)) })
6308
+ ] }),
6309
+ /* @__PURE__ */ jsxs36("div", { children: [
6310
+ /* @__PURE__ */ jsx45("p", { className: "text-xs font-semibold text-gray-700 mb-2", children: "Traffic Sources" }),
6311
+ /* @__PURE__ */ jsx45("div", { className: "space-y-1", children: analyticsData.trafficSources.slice(0, 5).map((source, index) => /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between text-xs", children: [
6312
+ /* @__PURE__ */ jsx45("span", { className: "text-gray-600", children: source.source }),
6313
+ /* @__PURE__ */ jsx45("span", { className: "font-semibold text-gray-900", children: source.sessions.toLocaleString() })
6314
+ ] }, index)) })
6315
+ ] })
6316
+ ] })
6317
+ ] })
6318
+ ] }),
6319
+ activeTab === "sales" && !isLoading && storeEnabled && ecommerceData && /* @__PURE__ */ jsxs36(Fragment6, { children: [
6320
+ /* @__PURE__ */ jsx45("div", { className: "border-t-2 border-dotted border-gray-200 my-6" }),
6321
+ /* @__PURE__ */ jsxs36("div", { className: "mb-4", children: [
6322
+ /* @__PURE__ */ jsxs36("div", { className: "flex items-center mb-2", children: [
6323
+ /* @__PURE__ */ jsx45(BarChart3, { className: "w-4 h-4 text-gray-600 mr-2" }),
6324
+ /* @__PURE__ */ jsx45("h2", { className: "text-sm font-semibold text-gray-800", children: "Store Analytics" })
6325
+ ] }),
6326
+ /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-3", children: [
6327
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/orders"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6328
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "Net Sales" }),
6329
+ /* @__PURE__ */ jsx45("p", { className: "text-lg font-bold text-gray-900", children: formatMoney4(ecommerceData.kpis.netSales) })
6330
+ ] }),
6331
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/orders"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6332
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "Orders" }),
6333
+ /* @__PURE__ */ jsx45("p", { className: "text-lg font-bold text-gray-900", children: ecommerceData.kpis.ordersPlaced })
6334
+ ] }),
6335
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/orders"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6336
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "AOV" }),
6337
+ /* @__PURE__ */ jsx45("p", { className: "text-lg font-bold text-gray-900", children: formatMoney4(ecommerceData.kpis.averageOrderValue) })
6338
+ ] }),
6339
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/contacts"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6340
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "Returning Customer Rate" }),
6341
+ /* @__PURE__ */ jsxs36("p", { className: "text-lg font-bold text-gray-900", children: [
6342
+ ecommerceData.kpis.returningCustomerRate.toFixed(1),
6343
+ "%"
6344
+ ] })
6345
+ ] }),
6346
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/orders"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6347
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "Return Rate" }),
6348
+ /* @__PURE__ */ jsxs36("p", { className: "text-lg font-bold text-gray-900", children: [
6349
+ ecommerceData.kpis.returnRate.toFixed(1),
6350
+ "%"
6351
+ ] })
6352
+ ] }),
6353
+ /* @__PURE__ */ jsxs36("button", { onClick: () => router.push("/admin/payments"), className: "text-left bg-white rounded border border-gray-200 p-2.5 shadow-sm", children: [
6354
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-600", children: "Payment Success" }),
6355
+ /* @__PURE__ */ jsxs36("p", { className: "text-lg font-bold text-gray-900", children: [
6356
+ ecommerceData.kpis.paymentSuccessRate.toFixed(1),
6357
+ "%"
6358
+ ] })
6359
+ ] })
6360
+ ] })
6361
+ ] }),
6362
+ /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 lg:grid-cols-2 gap-6 mb-6", children: [
6363
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-100 p-4 shadow-sm", children: [
6364
+ /* @__PURE__ */ jsx45("h3", { className: "text-base font-semibold text-gray-800 mb-3", children: "Sales Over Time" }),
6365
+ /* @__PURE__ */ jsx45("div", { className: "space-y-2 max-h-64 overflow-auto", children: ecommerceData.salesOverTime.slice(-10).map((point) => /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-between text-xs", children: [
6366
+ /* @__PURE__ */ jsx45("span", { className: "text-gray-600", children: point.date }),
6367
+ /* @__PURE__ */ jsxs36("span", { className: "font-semibold text-gray-900", children: [
6368
+ formatMoney4(point.value),
6369
+ " (",
6370
+ point.orders,
6371
+ ")"
6372
+ ] })
6373
+ ] }, point.date)) })
6374
+ ] }),
6375
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-100 p-4 shadow-sm", children: [
6376
+ /* @__PURE__ */ jsx45("h3", { className: "text-base font-semibold text-gray-800 mb-3", children: "Top Products" }),
6377
+ /* @__PURE__ */ jsx45("div", { className: "space-y-2", children: ecommerceData.topProducts.map((p, idx) => /* @__PURE__ */ jsxs36(
6378
+ "button",
6379
+ {
6380
+ onClick: () => router.push("/admin/products"),
6381
+ className: "w-full text-left flex items-center justify-between p-2 bg-gray-50 rounded-lg",
6382
+ children: [
6383
+ /* @__PURE__ */ jsx45("span", { className: "text-xs text-gray-700 truncate max-w-[70%]", children: p.name }),
6384
+ /* @__PURE__ */ jsxs36("span", { className: "text-xs font-semibold text-gray-900", children: [
6385
+ p.units,
6386
+ " / ",
6387
+ formatMoney4(p.sales)
6388
+ ] })
6389
+ ]
6390
+ },
6391
+ `${p.name}-${idx}`
6392
+ )) })
6393
+ ] })
6394
+ ] }),
6395
+ /* @__PURE__ */ jsxs36("div", { className: "grid grid-cols-1 lg:grid-cols-3 gap-6 mb-2", children: [
6396
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-100 p-4 shadow-sm", children: [
6397
+ /* @__PURE__ */ jsx45("h3", { className: "text-base font-semibold text-gray-800 mb-2", children: "Customer Mix" }),
6398
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-gray-700", children: [
6399
+ "New: ",
6400
+ ecommerceData.customerMix.newCustomers
6401
+ ] }),
6402
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-gray-700", children: [
6403
+ "Returning: ",
6404
+ ecommerceData.customerMix.returningCustomers
6405
+ ] }),
6406
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-gray-700", children: [
6407
+ "Repeat rate: ",
6408
+ ecommerceData.customerMix.repeatPurchaseRate.toFixed(1),
6409
+ "%"
6410
+ ] })
6411
+ ] }),
6412
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-100 p-4 shadow-sm", children: [
6413
+ /* @__PURE__ */ jsx45("h3", { className: "text-base font-semibold text-gray-800 mb-2", children: "Returns Trend" }),
6414
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-gray-700", children: [
6415
+ "Return value: ",
6416
+ formatMoney4(ecommerceData.kpis.returnValue)
6417
+ ] }),
6418
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-gray-700", children: [
6419
+ "Return orders: ",
6420
+ ecommerceData.returnsTrend.reduce((s, r) => s + r.count, 0)
6421
+ ] }),
6422
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-gray-700", children: [
6423
+ "Return rate: ",
6424
+ ecommerceData.kpis.returnRate.toFixed(1),
6425
+ "%"
6426
+ ] })
6427
+ ] }),
6428
+ /* @__PURE__ */ jsxs36("div", { className: "bg-white rounded-lg border border-gray-100 p-4 shadow-sm", children: [
6429
+ /* @__PURE__ */ jsx45("h3", { className: "text-base font-semibold text-gray-800 mb-2", children: "Inventory Risk" }),
6430
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-gray-700", children: [
6431
+ "Out of stock: ",
6432
+ ecommerceData.inventoryRisk.outOfStockCount
6433
+ ] }),
6434
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-gray-700", children: [
6435
+ "Low stock: ",
6436
+ ecommerceData.inventoryRisk.lowStockCount
6437
+ ] }),
6438
+ /* @__PURE__ */ jsxs36("p", { className: "text-xs text-gray-700", children: [
6439
+ "Total units: ",
6440
+ ecommerceData.inventoryRisk.totalInventory
6441
+ ] })
6442
+ ] })
6443
+ ] })
6444
+ ] }),
5744
6445
  isLoading && /* @__PURE__ */ jsxs36("div", { className: "flex items-center justify-center py-8", children: [
5745
6446
  /* @__PURE__ */ jsx45("div", { className: "animate-spin rounded-full h-5 w-5 border-2 border-gray-300 border-t-gray-600" }),
5746
6447
  /* @__PURE__ */ jsx45("span", { className: "ml-2 text-sm text-gray-600", children: "Loading dashboard data..." })
5747
6448
  ] }),
5748
- !isLoading && !analyticsEnabled && /* @__PURE__ */ jsxs36("div", { className: "text-center py-8", children: [
6449
+ !isLoading && activeTab === "overview" && !analyticsEnabled && /* @__PURE__ */ jsxs36("div", { className: "text-center py-8", children: [
5749
6450
  /* @__PURE__ */ jsx45(Globe, { className: "w-10 h-10 text-gray-400 mx-auto mb-3" }),
5750
6451
  /* @__PURE__ */ jsx45("h3", { className: "text-base font-medium text-gray-600 mb-1", children: "Analytics Not Configured" }),
5751
6452
  /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-500", children: "Google Analytics integration is required to view website analytics." })
6453
+ ] }),
6454
+ !isLoading && activeTab === "sales" && !storeEnabled && /* @__PURE__ */ jsxs36("div", { className: "text-center py-8", children: [
6455
+ /* @__PURE__ */ jsx45("h3", { className: "text-base font-medium text-gray-600 mb-1", children: "Store analytics unavailable" }),
6456
+ /* @__PURE__ */ jsx45("p", { className: "text-xs text-gray-500", children: "Enable store/ecomm to view sales reports." })
5752
6457
  ] })
5753
6458
  ] })
5754
6459
  ] });
5755
6460
  }
5756
6461
 
5757
6462
  // src/admin/pages/AdminPageResolver.tsx
5758
- import { useState as useState35, useEffect as useEffect33, useContext as useContext6, useMemo as useMemo2 } from "react";
5759
- import { useRouter as useRouter13 } from "next/navigation";
6463
+ import { useState as useState36, useEffect as useEffect33, useContext as useContext7, useMemo as useMemo4 } from "react";
6464
+ import { useRouter as useRouter15 } from "next/navigation";
5760
6465
 
5761
6466
  // src/admin/pages/SubmissionDetailPage.tsx
5762
- import { useEffect as useEffect20, useState as useState22 } from "react";
6467
+ import { useEffect as useEffect20, useState as useState23 } from "react";
5763
6468
  import Link9 from "next/link";
5764
6469
  import { ArrowLeft as ArrowLeft5 } from "lucide-react";
5765
6470
 
5766
6471
  // src/components/Admin/DetailPageHeader.tsx
5767
6472
  import Link8 from "next/link";
5768
- import { useRouter as useRouter5 } from "next/navigation";
5769
- import { ArrowLeft as ArrowLeft4, MoreVertical as MoreVertical2, X as X13 } from "lucide-react";
5770
- import { jsx as jsx46, jsxs as jsxs37 } from "react/jsx-runtime";
6473
+ import { useRouter as useRouter7 } from "next/navigation";
6474
+ import { ArrowLeft as ArrowLeft4, X as X13 } from "lucide-react";
6475
+ import { Fragment as Fragment7, jsx as jsx46, jsxs as jsxs37 } from "react/jsx-runtime";
5771
6476
  function DetailPageHeader({
5772
6477
  title,
5773
6478
  subtitle,
@@ -5777,7 +6482,7 @@ function DetailPageHeader({
5777
6482
  onClose,
5778
6483
  menuItems = []
5779
6484
  }) {
5780
- const router = useRouter5();
6485
+ const router = useRouter7();
5781
6486
  const handleClose = () => {
5782
6487
  if (onClose) onClose();
5783
6488
  else if (closeHref) router.push(closeHref);
@@ -5802,20 +6507,32 @@ function DetailPageHeader({
5802
6507
  ] })
5803
6508
  ] }),
5804
6509
  /* @__PURE__ */ jsxs37("div", { className: "flex items-center gap-2 shrink-0", children: [
5805
- menuItems.length > 0 && /* @__PURE__ */ jsxs37(DropdownMenu, { children: [
5806
- /* @__PURE__ */ jsx46(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxs37(
5807
- Button,
5808
- {
5809
- variant: "ghost",
5810
- size: "icon",
5811
- className: "h-8 w-8 text-gray-300 hover:text-white hover:bg-gray-700",
5812
- children: [
5813
- /* @__PURE__ */ jsx46(MoreVertical2, { className: "h-4 w-4" }),
5814
- /* @__PURE__ */ jsx46("span", { className: "sr-only", children: "More" })
5815
- ]
5816
- }
5817
- ) }),
5818
- /* @__PURE__ */ jsx46(DropdownMenuContent, { align: "end", className: "w-48", children: menuItems.map((item, i) => /* @__PURE__ */ jsx46(DropdownMenuItem, { onClick: item.onClick, children: item.label }, i)) })
6510
+ menuItems.length > 0 && /* @__PURE__ */ jsxs37(Fragment7, { children: [
6511
+ /* @__PURE__ */ jsx46("div", { className: "flex items-center gap-2 md:hidden", children: menuItems.map((item, i) => {
6512
+ const Icon2 = item.icon;
6513
+ return /* @__PURE__ */ jsxs37(
6514
+ Button,
6515
+ {
6516
+ variant: item.variant ?? "outline",
6517
+ size: "icon",
6518
+ className: "h-8 w-8 border border-gray-600 bg-transparent text-white hover:bg-gray-700",
6519
+ onClick: item.onClick,
6520
+ title: item.label,
6521
+ children: [
6522
+ /* @__PURE__ */ jsx46(Icon2, { className: "h-4 w-4" }),
6523
+ /* @__PURE__ */ jsx46("span", { className: "sr-only", children: item.label })
6524
+ ]
6525
+ },
6526
+ i
6527
+ );
6528
+ }) }),
6529
+ /* @__PURE__ */ jsx46("div", { className: "hidden md:flex items-center gap-2", children: menuItems.map((item, i) => {
6530
+ const Icon2 = item.icon;
6531
+ return /* @__PURE__ */ jsxs37(Button, { variant: item.variant ?? "outline", size: "sm", onClick: item.onClick, children: [
6532
+ /* @__PURE__ */ jsx46(Icon2, { className: "h-4 w-4 mr-1" }),
6533
+ item.label
6534
+ ] }, i);
6535
+ }) })
5819
6536
  ] }),
5820
6537
  /* @__PURE__ */ jsxs37(
5821
6538
  Button,
@@ -5837,9 +6554,9 @@ function DetailPageHeader({
5837
6554
  // src/admin/pages/SubmissionDetailPage.tsx
5838
6555
  import { jsx as jsx47, jsxs as jsxs38 } from "react/jsx-runtime";
5839
6556
  function SubmissionDetailPage({ submissionId }) {
5840
- const [submission, setSubmission] = useState22(null);
5841
- const [loading, setLoading] = useState22(true);
5842
- const [error, setError] = useState22(null);
6557
+ const [submission, setSubmission] = useState23(null);
6558
+ const [loading, setLoading] = useState23(true);
6559
+ const [error, setError] = useState23(null);
5843
6560
  useEffect20(() => {
5844
6561
  async function load() {
5845
6562
  try {
@@ -5948,10 +6665,10 @@ function SubmissionDetailPage({ submissionId }) {
5948
6665
  }
5949
6666
 
5950
6667
  // src/admin/pages/OrderDetailPage.tsx
5951
- import { useEffect as useEffect21, useState as useState23 } from "react";
6668
+ import { useEffect as useEffect21, useState as useState24 } from "react";
5952
6669
  import Link10 from "next/link";
5953
- import { useRouter as useRouter6 } from "next/navigation";
5954
- import { X as X14 } from "lucide-react";
6670
+ import { useRouter as useRouter8 } from "next/navigation";
6671
+ import { X as X14, RefreshCw as RefreshCw2 } from "lucide-react";
5955
6672
 
5956
6673
  // src/components/Admin/DetailPageLayout.tsx
5957
6674
  import { jsx as jsx48, jsxs as jsxs39 } from "react/jsx-runtime";
@@ -5969,7 +6686,7 @@ function DetailPageLayout({
5969
6686
  }
5970
6687
 
5971
6688
  // src/admin/pages/OrderDetailPage.tsx
5972
- import { Fragment as Fragment7, jsx as jsx49, jsxs as jsxs40 } from "react/jsx-runtime";
6689
+ import { Fragment as Fragment8, jsx as jsx49, jsxs as jsxs40 } from "react/jsx-runtime";
5973
6690
  function formatMoney(amount, currency = "INR") {
5974
6691
  return new Intl.NumberFormat("en-IN", {
5975
6692
  style: "currency",
@@ -5992,12 +6709,12 @@ function formatAddress(a) {
5992
6709
  return parts.join(", ") || "\u2014";
5993
6710
  }
5994
6711
  function OrderDetailPage({ orderId }) {
5995
- const router = useRouter6();
5996
- const [order, setOrder] = useState23(null);
5997
- const [loading, setLoading] = useState23(true);
5998
- const [error, setError] = useState23(null);
5999
- const [erpEnabled, setErpEnabled] = useState23(false);
6000
- const [reposting, setReposting] = useState23(false);
6712
+ const router = useRouter8();
6713
+ const [order, setOrder] = useState24(null);
6714
+ const [loading, setLoading] = useState24(true);
6715
+ const [error, setError] = useState24(null);
6716
+ const [erpEnabled, setErpEnabled] = useState24(false);
6717
+ const [reposting, setReposting] = useState24(false);
6001
6718
  useEffect21(() => {
6002
6719
  async function load() {
6003
6720
  try {
@@ -6077,13 +6794,13 @@ function OrderDetailPage({ orderId }) {
6077
6794
  title: `Order ${order.orderNumber}`,
6078
6795
  subtitle: /* @__PURE__ */ jsx49("span", { className: "text-sm text-gray-400", children: formatDateTime(order.createdAt) }),
6079
6796
  closeHref: "/admin/orders",
6080
- menuItems: erpEnabled ? [{ label: reposting ? "Reposting..." : "Repost to ERP", onClick: handleRepostToErp }] : void 0
6797
+ menuItems: erpEnabled ? [{ label: reposting ? "Reposting..." : "Repost to ERP", icon: RefreshCw2, onClick: handleRepostToErp }] : void 0
6081
6798
  }
6082
6799
  ),
6083
6800
  /* @__PURE__ */ jsx49(
6084
6801
  DetailPageLayout,
6085
6802
  {
6086
- main: /* @__PURE__ */ jsxs40(Fragment7, { children: [
6803
+ main: /* @__PURE__ */ jsxs40(Fragment8, { children: [
6087
6804
  /* @__PURE__ */ jsxs40("section", { children: [
6088
6805
  /* @__PURE__ */ jsx49("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Order details" }),
6089
6806
  /* @__PURE__ */ jsx49("div", { className: "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50", children: /* @__PURE__ */ jsxs40("dl", { className: "min-w-0 grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-4 gap-3 text-sm", children: [
@@ -6115,7 +6832,7 @@ function OrderDetailPage({ orderId }) {
6115
6832
  /* @__PURE__ */ jsx49("dt", { className: "text-gray-500", children: "Total" }),
6116
6833
  /* @__PURE__ */ jsx49("dd", { className: "font-medium text-gray-900", children: formatMoney(Number(order.total), currency) })
6117
6834
  ] }),
6118
- (order.orderKind || order.parentOrderId != null) && /* @__PURE__ */ jsxs40(Fragment7, { children: [
6835
+ (order.orderKind || order.parentOrderId != null) && /* @__PURE__ */ jsxs40(Fragment8, { children: [
6119
6836
  /* @__PURE__ */ jsxs40("div", { className: "min-w-0", children: [
6120
6837
  /* @__PURE__ */ jsx49("dt", { className: "text-gray-500", children: "Kind" }),
6121
6838
  /* @__PURE__ */ jsx49("dd", { className: "font-medium text-gray-900 capitalize", children: order.orderKind ?? "sale" })
@@ -6238,7 +6955,7 @@ function OrderDetailPage({ orderId }) {
6238
6955
  ] })
6239
6956
  ] }) })
6240
6957
  ] }),
6241
- sidebar: /* @__PURE__ */ jsxs40(Fragment7, { children: [
6958
+ sidebar: /* @__PURE__ */ jsxs40(Fragment8, { children: [
6242
6959
  contact && /* @__PURE__ */ jsxs40("section", { children: [
6243
6960
  /* @__PURE__ */ jsx49("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Customer" }),
6244
6961
  /* @__PURE__ */ jsx49("div", { className: "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50", children: /* @__PURE__ */ jsxs40("dl", { className: "min-w-0 grid grid-cols-1 sm:grid-cols-3 gap-3 text-sm", children: [
@@ -6317,11 +7034,11 @@ function OrderDetailPage({ orderId }) {
6317
7034
  }
6318
7035
 
6319
7036
  // src/admin/pages/PaymentDetailPage.tsx
6320
- import { useEffect as useEffect22, useState as useState24 } from "react";
7037
+ import { useEffect as useEffect22, useState as useState25 } from "react";
6321
7038
  import Link11 from "next/link";
6322
- import { useRouter as useRouter7 } from "next/navigation";
7039
+ import { useRouter as useRouter9 } from "next/navigation";
6323
7040
  import { X as X15 } from "lucide-react";
6324
- import { Fragment as Fragment8, jsx as jsx50, jsxs as jsxs41 } from "react/jsx-runtime";
7041
+ import { Fragment as Fragment9, jsx as jsx50, jsxs as jsxs41 } from "react/jsx-runtime";
6325
7042
  function formatMoney2(amount, currency = "INR") {
6326
7043
  return new Intl.NumberFormat("en-IN", {
6327
7044
  style: "currency",
@@ -6330,10 +7047,10 @@ function formatMoney2(amount, currency = "INR") {
6330
7047
  }).format(Number(amount));
6331
7048
  }
6332
7049
  function PaymentDetailPage({ paymentId }) {
6333
- const router = useRouter7();
6334
- const [payment, setPayment] = useState24(null);
6335
- const [loading, setLoading] = useState24(true);
6336
- const [error, setError] = useState24(null);
7050
+ const router = useRouter9();
7051
+ const [payment, setPayment] = useState25(null);
7052
+ const [loading, setLoading] = useState25(true);
7053
+ const [error, setError] = useState25(null);
6337
7054
  useEffect22(() => {
6338
7055
  async function load() {
6339
7056
  try {
@@ -6383,7 +7100,7 @@ function PaymentDetailPage({ paymentId }) {
6383
7100
  /* @__PURE__ */ jsx50(
6384
7101
  DetailPageLayout,
6385
7102
  {
6386
- main: /* @__PURE__ */ jsxs41(Fragment8, { children: [
7103
+ main: /* @__PURE__ */ jsxs41(Fragment9, { children: [
6387
7104
  /* @__PURE__ */ jsxs41("section", { children: [
6388
7105
  /* @__PURE__ */ jsx50("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Payment details" }),
6389
7106
  /* @__PURE__ */ jsx50("div", { className: "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50", children: /* @__PURE__ */ jsxs41("dl", { className: "min-w-0 grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-4 gap-3 text-sm", children: [
@@ -6446,7 +7163,7 @@ function PaymentDetailPage({ paymentId }) {
6446
7163
  ] })
6447
7164
  ] })
6448
7165
  ] }),
6449
- sidebar: /* @__PURE__ */ jsx50(Fragment8, { children: customer && /* @__PURE__ */ jsxs41("section", { children: [
7166
+ sidebar: /* @__PURE__ */ jsx50(Fragment9, { children: customer && /* @__PURE__ */ jsxs41("section", { children: [
6450
7167
  /* @__PURE__ */ jsx50("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Customer" }),
6451
7168
  /* @__PURE__ */ jsx50("div", { className: "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50", children: /* @__PURE__ */ jsxs41("dl", { className: "min-w-0 grid grid-cols-1 sm:grid-cols-3 gap-3 text-sm", children: [
6452
7169
  /* @__PURE__ */ jsxs41("div", { className: "min-w-0", children: [
@@ -6476,11 +7193,11 @@ function PaymentDetailPage({ paymentId }) {
6476
7193
  }
6477
7194
 
6478
7195
  // src/admin/pages/ContactDetailPage.tsx
6479
- import { useEffect as useEffect23, useState as useState25 } from "react";
7196
+ import { useEffect as useEffect23, useState as useState26 } from "react";
6480
7197
  import Link12 from "next/link";
6481
- import { useRouter as useRouter8 } from "next/navigation";
7198
+ import { useRouter as useRouter10 } from "next/navigation";
6482
7199
  import { Plus as Plus7, X as X16 } from "lucide-react";
6483
- import { Fragment as Fragment9, jsx as jsx51, jsxs as jsxs42 } from "react/jsx-runtime";
7200
+ import { Fragment as Fragment10, jsx as jsx51, jsxs as jsxs42 } from "react/jsx-runtime";
6484
7201
  function formatMoney3(amount, currency = "INR") {
6485
7202
  return new Intl.NumberFormat("en-IN", {
6486
7203
  style: "currency",
@@ -6494,13 +7211,13 @@ function formatAddress2(a) {
6494
7211
  }
6495
7212
  var ADDRESS_TAGS = [{ value: "", label: "\u2014" }, { value: "default", label: "Default" }, { value: "billing", label: "Billing" }, { value: "shipping", label: "Shipping" }];
6496
7213
  function ContactDetailPage({ contactId }) {
6497
- const router = useRouter8();
6498
- const [contact, setContact] = useState25(null);
6499
- const [loading, setLoading] = useState25(true);
6500
- const [error, setError] = useState25(null);
6501
- const [addAddressOpen, setAddAddressOpen] = useState25(false);
6502
- const [addAddressSaving, setAddAddressSaving] = useState25(false);
6503
- const [addAddressForm, setAddAddressForm] = useState25({
7214
+ const router = useRouter10();
7215
+ const [contact, setContact] = useState26(null);
7216
+ const [loading, setLoading] = useState26(true);
7217
+ const [error, setError] = useState26(null);
7218
+ const [addAddressOpen, setAddAddressOpen] = useState26(false);
7219
+ const [addAddressSaving, setAddAddressSaving] = useState26(false);
7220
+ const [addAddressForm, setAddAddressForm] = useState26({
6504
7221
  tag: "",
6505
7222
  line1: "",
6506
7223
  line2: "",
@@ -6592,7 +7309,7 @@ function ContactDetailPage({ contactId }) {
6592
7309
  /* @__PURE__ */ jsx51(
6593
7310
  DetailPageLayout,
6594
7311
  {
6595
- main: /* @__PURE__ */ jsxs42(Fragment9, { children: [
7312
+ main: /* @__PURE__ */ jsxs42(Fragment10, { children: [
6596
7313
  /* @__PURE__ */ jsxs42("section", { children: [
6597
7314
  /* @__PURE__ */ jsx51("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Contact details" }),
6598
7315
  /* @__PURE__ */ jsx51("div", { className: "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50", children: /* @__PURE__ */ jsxs42("dl", { className: "min-w-0 grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-4 gap-3 text-sm", children: [
@@ -6608,7 +7325,7 @@ function ContactDetailPage({ contactId }) {
6608
7325
  /* @__PURE__ */ jsx51("dt", { className: "text-gray-500", children: "Phone" }),
6609
7326
  /* @__PURE__ */ jsx51("dd", { className: "font-medium text-gray-900 break-words", children: contact.phone ?? "\u2014" })
6610
7327
  ] }),
6611
- (contact.type ?? contact.company ?? contact.taxId) && /* @__PURE__ */ jsxs42(Fragment9, { children: [
7328
+ (contact.type ?? contact.company ?? contact.taxId) && /* @__PURE__ */ jsxs42(Fragment10, { children: [
6612
7329
  contact.type && /* @__PURE__ */ jsxs42("div", { className: "min-w-0", children: [
6613
7330
  /* @__PURE__ */ jsx51("dt", { className: "text-gray-500", children: "Type" }),
6614
7331
  /* @__PURE__ */ jsx51("dd", { className: "font-medium text-gray-900 break-words", children: contact.type })
@@ -6662,7 +7379,7 @@ function ContactDetailPage({ contactId }) {
6662
7379
  ] }) })
6663
7380
  ] })
6664
7381
  ] }),
6665
- sidebar: /* @__PURE__ */ jsxs42(Fragment9, { children: [
7382
+ sidebar: /* @__PURE__ */ jsxs42(Fragment10, { children: [
6666
7383
  /* @__PURE__ */ jsxs42("section", { children: [
6667
7384
  /* @__PURE__ */ jsx51("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Summary" }),
6668
7385
  /* @__PURE__ */ jsx51("div", { className: "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50", children: /* @__PURE__ */ jsxs42("dl", { className: "min-w-0 grid grid-cols-1 sm:grid-cols-3 gap-3 text-sm", children: [
@@ -6848,11 +7565,11 @@ function ContactDetailPage({ contactId }) {
6848
7565
  }
6849
7566
 
6850
7567
  // src/admin/pages/SettingsPage.tsx
6851
- import { useState as useState26, useEffect as useEffect24, useContext as useContext3 } from "react";
7568
+ import { useState as useState27, useEffect as useEffect24, useContext as useContext4 } from "react";
6852
7569
  import { useSearchParams as useSearchParams3 } from "next/navigation";
6853
- import { toast as toast2 } from "sonner";
7570
+ import { toast as toast3 } from "sonner";
6854
7571
  import { Save as Save3, RotateCcw } from "lucide-react";
6855
- import { Fragment as Fragment10, jsx as jsx52, jsxs as jsxs43 } from "react/jsx-runtime";
7572
+ import { Fragment as Fragment11, jsx as jsx52, jsxs as jsxs43 } from "react/jsx-runtime";
6856
7573
  var DEFAULTS = {
6857
7574
  primaryColor: "#313996",
6858
7575
  secondaryColor: "#6366f1",
@@ -6876,22 +7593,22 @@ function hexToHsl(hex) {
6876
7593
  function SettingsPage() {
6877
7594
  const searchParams = useSearchParams3();
6878
7595
  const tabParam = searchParams.get("tab");
6879
- const { theme, themeRegistry } = useContext3(AdminConfigContext);
6880
- const [tab, setTab] = useState26(
7596
+ const { theme, themeRegistry } = useContext4(AdminConfigContext);
7597
+ const [tab, setTab] = useState27(
6881
7598
  tabParam === "navbar" ? "navbar" : tabParam === "store" ? "store" : "appearance"
6882
7599
  );
6883
7600
  useEffect24(() => {
6884
7601
  if (tabParam === "navbar") setTab("navbar");
6885
7602
  else if (tabParam === "store") setTab("store");
6886
7603
  }, [tabParam]);
6887
- const [settings, setSettings] = useState26(DEFAULTS);
6888
- const [loading, setLoading] = useState26(true);
6889
- const [saving, setSaving] = useState26(false);
6890
- const [activeThemeId, setActiveThemeId] = useState26("");
6891
- const [navbarConfig, setNavbarConfig] = useState26({ logo: "", items: [], ctaLabel: "", ctaUrl: "" });
6892
- const [themeSettingsLoading, setThemeSettingsLoading] = useState26(true);
6893
- const [storeEnabled, setStoreEnabled] = useState26(false);
6894
- const [storeSettingsLoading, setStoreSettingsLoading] = useState26(true);
7604
+ const [settings, setSettings] = useState27(DEFAULTS);
7605
+ const [loading, setLoading] = useState27(true);
7606
+ const [saving, setSaving] = useState27(false);
7607
+ const [activeThemeId, setActiveThemeId] = useState27("");
7608
+ const [navbarConfig, setNavbarConfig] = useState27({ logo: "", items: [], ctaLabel: "", ctaUrl: "" });
7609
+ const [themeSettingsLoading, setThemeSettingsLoading] = useState27(true);
7610
+ const [storeEnabled, setStoreEnabled] = useState27(false);
7611
+ const [storeSettingsLoading, setStoreSettingsLoading] = useState27(true);
6895
7612
  useEffect24(() => {
6896
7613
  fetch("/api/settings/admin_view").then((r) => r.ok ? r.json() : {}).then((data) => {
6897
7614
  setSettings({
@@ -6937,9 +7654,9 @@ function SettingsPage() {
6937
7654
  document.documentElement.style.setProperty("--secondary", hexToHsl(settings.secondaryColor));
6938
7655
  if (settings.compactView === "true") document.documentElement.classList.add("compact");
6939
7656
  else document.documentElement.classList.remove("compact");
6940
- toast2.success("Settings saved");
7657
+ toast3.success("Settings saved");
6941
7658
  } catch {
6942
- toast2.error("Failed to save settings");
7659
+ toast3.error("Failed to save settings");
6943
7660
  } finally {
6944
7661
  setSaving(false);
6945
7662
  }
@@ -6953,10 +7670,10 @@ function SettingsPage() {
6953
7670
  headers: { "Content-Type": "application/json" },
6954
7671
  body: JSON.stringify({ activeThemeId: { value: id, type: "public" } })
6955
7672
  });
6956
- toast2.success("Theme updated");
7673
+ toast3.success("Theme updated");
6957
7674
  window.location.reload();
6958
7675
  } catch {
6959
- toast2.error("Failed to save theme");
7676
+ toast3.error("Failed to save theme");
6960
7677
  } finally {
6961
7678
  setSaving(false);
6962
7679
  }
@@ -6969,9 +7686,9 @@ function SettingsPage() {
6969
7686
  headers: { "Content-Type": "application/json" },
6970
7687
  body: JSON.stringify({ navbar: { value: JSON.stringify(navbarConfig), type: "public" } })
6971
7688
  });
6972
- toast2.success("Navbar saved");
7689
+ toast3.success("Navbar saved");
6973
7690
  } catch {
6974
- toast2.error("Failed to save");
7691
+ toast3.error("Failed to save");
6975
7692
  } finally {
6976
7693
  setSaving(false);
6977
7694
  }
@@ -6984,10 +7701,10 @@ function SettingsPage() {
6984
7701
  headers: { "Content-Type": "application/json" },
6985
7702
  body: JSON.stringify({ enabled: { value: storeEnabled ? "true" : "false", type: "public" } })
6986
7703
  });
6987
- toast2.success("Store settings saved");
7704
+ toast3.success("Store settings saved");
6988
7705
  window.location.reload();
6989
7706
  } catch {
6990
- toast2.error("Failed to save store settings");
7707
+ toast3.error("Failed to save store settings");
6991
7708
  } finally {
6992
7709
  setSaving(false);
6993
7710
  }
@@ -7063,7 +7780,7 @@ function SettingsPage() {
7063
7780
  /* @__PURE__ */ jsx52("span", { className: "text-[11px] text-gray-400", children: "Smaller spacing in admin" })
7064
7781
  ] }) })
7065
7782
  ] }),
7066
- tab === "navbar" && /* @__PURE__ */ jsx52("div", { className: "space-y-6", children: themeSettingsLoading ? /* @__PURE__ */ jsx52("div", { className: "flex items-center gap-2 text-gray-500", children: "Loading..." }) : /* @__PURE__ */ jsxs43(Fragment10, { children: [
7783
+ tab === "navbar" && /* @__PURE__ */ jsx52("div", { className: "space-y-6", children: themeSettingsLoading ? /* @__PURE__ */ jsx52("div", { className: "flex items-center gap-2 text-gray-500", children: "Loading..." }) : /* @__PURE__ */ jsxs43(Fragment11, { children: [
7067
7784
  /* @__PURE__ */ jsxs43("div", { children: [
7068
7785
  /* @__PURE__ */ jsx52("h2", { className: "text-lg font-semibold text-gray-900 mb-2", children: "Navbar & pages" }),
7069
7786
  /* @__PURE__ */ jsx52("p", { className: "text-sm text-gray-500 mb-4", children: "Set logo and menu items. Use parent/child (indent/outdent) for hierarchy. Each item can link to a page or a custom URL." }),
@@ -7071,7 +7788,7 @@ function SettingsPage() {
7071
7788
  ] }),
7072
7789
  /* @__PURE__ */ jsx52(Button, { onClick: handleSaveNavbar, disabled: saving, children: saving ? "Saving..." : "Save navbar" })
7073
7790
  ] }) }),
7074
- tab === "store" && /* @__PURE__ */ jsx52("div", { className: "space-y-6", children: storeSettingsLoading ? /* @__PURE__ */ jsx52("div", { className: "flex items-center gap-2 text-gray-500", children: "Loading..." }) : /* @__PURE__ */ jsxs43(Fragment10, { children: [
7791
+ tab === "store" && /* @__PURE__ */ jsx52("div", { className: "space-y-6", children: storeSettingsLoading ? /* @__PURE__ */ jsx52("div", { className: "flex items-center gap-2 text-gray-500", children: "Loading..." }) : /* @__PURE__ */ jsxs43(Fragment11, { children: [
7075
7792
  /* @__PURE__ */ jsxs43("div", { children: [
7076
7793
  /* @__PURE__ */ jsx52("h2", { className: "text-lg font-semibold text-gray-900 mb-2", children: "Store / E-commerce" }),
7077
7794
  /* @__PURE__ */ jsx52("p", { className: "text-sm text-gray-500 mb-4", children: "Enable e-commerce functionality to manage products, orders, payments, and more." }),
@@ -7103,11 +7820,39 @@ function SettingsPage() {
7103
7820
  }
7104
7821
 
7105
7822
  // src/admin/pages/MediaLibraryPage.tsx
7106
- import { useState as useState27, useEffect as useEffect25, useCallback as useCallback5, useRef as useRef8 } from "react";
7107
- import { Upload as Upload4, Search as Search5, Image as ImageIcon3, FileText as FileText2, Film, File as File3, Copy, Trash2 as Trash24, Edit2 } from "lucide-react";
7108
- import { toast as toast3 } from "sonner";
7109
- import { jsx as jsx53, jsxs as jsxs44 } from "react/jsx-runtime";
7110
- function getTypeCategory(mime) {
7823
+ import React17, { useState as useState28, useEffect as useEffect25, useCallback as useCallback5, useRef as useRef9 } from "react";
7824
+
7825
+ // src/lib/media-zip-extract.ts
7826
+ import { IsNull } from "typeorm";
7827
+ var ZIP_MIME_TYPES = /* @__PURE__ */ new Set(["application/zip", "application/x-zip-compressed"]);
7828
+ var MAX_TOTAL_UNCOMPRESSED = 80 * 1024 * 1024;
7829
+ function isZipMedia(mime, filename) {
7830
+ if (mime && ZIP_MIME_TYPES.has(mime)) return true;
7831
+ return filename.toLowerCase().endsWith(".zip");
7832
+ }
7833
+
7834
+ // src/admin/pages/MediaLibraryPage.tsx
7835
+ import {
7836
+ Upload as Upload4,
7837
+ Search as Search5,
7838
+ Image as ImageIcon3,
7839
+ FileText as FileText2,
7840
+ Film,
7841
+ File as File3,
7842
+ Copy,
7843
+ Trash2 as Trash24,
7844
+ Edit2,
7845
+ Folder,
7846
+ FolderPlus,
7847
+ Archive,
7848
+ LayoutGrid,
7849
+ List
7850
+ } from "lucide-react";
7851
+ import { toast as toast4 } from "sonner";
7852
+ import { Fragment as Fragment12, jsx as jsx53, jsxs as jsxs44 } from "react/jsx-runtime";
7853
+ function getTypeCategory(mime, kind, filename) {
7854
+ if (kind === "folder" || mime === "inode/directory") return "folder";
7855
+ if (isZipMedia(mime, filename ?? "")) return "zip";
7111
7856
  if (!mime) return "other";
7112
7857
  if (mime.startsWith("image/")) return "image";
7113
7858
  if (mime.startsWith("video/")) return "video";
@@ -7115,56 +7860,66 @@ function getTypeCategory(mime) {
7115
7860
  if (mime === "application/pdf" || mime.startsWith("application/")) return "document";
7116
7861
  return "other";
7117
7862
  }
7118
- function getTypeLabel(mime) {
7119
- const c = getTypeCategory(mime);
7863
+ function getTypeLabel(mime, kind, filename) {
7864
+ if (kind === "folder" || mime === "inode/directory") return "Folder";
7865
+ if (isZipMedia(mime, filename ?? "")) return "Zip";
7866
+ const c = getTypeCategory(mime, kind, filename);
7120
7867
  const labels = {
7121
7868
  image: "Image",
7122
7869
  video: "Video",
7123
7870
  audio: "Audio",
7124
7871
  document: "Document",
7872
+ folder: "Folder",
7873
+ zip: "Zip",
7125
7874
  other: "Other"
7126
7875
  };
7127
7876
  return labels[c] || "Other";
7128
7877
  }
7129
- function TypeIcon({ mimeType }) {
7130
- const c = getTypeCategory(mimeType);
7878
+ function TypeIcon({ mimeType, kind, filename }) {
7879
+ if (kind === "folder" || mimeType === "inode/directory") {
7880
+ return /* @__PURE__ */ jsx53(Folder, { className: "h-10 w-10 text-amber-500" });
7881
+ }
7882
+ if (isZipMedia(mimeType, filename ?? "")) {
7883
+ return /* @__PURE__ */ jsx53(Archive, { className: "h-10 w-10 text-violet-600" });
7884
+ }
7885
+ const c = getTypeCategory(mimeType, kind, filename);
7131
7886
  if (c === "image") return /* @__PURE__ */ jsx53(ImageIcon3, { className: "h-8 w-8 text-gray-400" });
7132
7887
  if (c === "video") return /* @__PURE__ */ jsx53(Film, { className: "h-8 w-8 text-gray-400" });
7133
7888
  if (c === "document") return /* @__PURE__ */ jsx53(FileText2, { className: "h-8 w-8 text-gray-400" });
7134
7889
  return /* @__PURE__ */ jsx53(File3, { className: "h-8 w-8 text-gray-400" });
7135
7890
  }
7136
- function groupByMonth(items) {
7137
- const groups = {};
7138
- items.forEach((item) => {
7139
- const d = new Date(item.createdAt);
7140
- const key = `${d.getFullYear()}-${String(d.getMonth() + 1).padStart(2, "0")}`;
7141
- const label = d.toLocaleDateString("en-US", { year: "numeric", month: "long" });
7142
- if (!groups[label]) groups[label] = [];
7143
- groups[label].push(item);
7144
- });
7145
- return groups;
7146
- }
7147
7891
  function MediaLibraryPage() {
7148
- const [data, setData] = useState27([]);
7149
- const [loading, setLoading] = useState27(true);
7150
- const [page, setPage] = useState27(1);
7151
- const [totalPages, setTotalPages] = useState27(1);
7152
- const [search, setSearch] = useState27("");
7153
- const [searchInput, setSearchInput] = useState27("");
7154
- const [typeFilter, setTypeFilter] = useState27("");
7155
- const [uploading, setUploading] = useState27(false);
7156
- const [editModal, setEditModal] = useState27(null);
7157
- const [editAlt, setEditAlt] = useState27("");
7158
- const [editPublic, setEditPublic] = useState27(false);
7159
- const fileInputRef = useRef8(null);
7892
+ const [data, setData] = useState28([]);
7893
+ const [loading, setLoading] = useState28(true);
7894
+ const [page, setPage] = useState28(1);
7895
+ const [totalPages, setTotalPages] = useState28(1);
7896
+ const [search, setSearch] = useState28("");
7897
+ const [searchInput, setSearchInput] = useState28("");
7898
+ const [typeFilter, setTypeFilter] = useState28("");
7899
+ const [sortField, setSortField] = useState28("filename");
7900
+ const [sortOrder, setSortOrder] = useState28("asc");
7901
+ const [viewMode, setViewMode] = useState28("grid");
7902
+ const [uploading, setUploading] = useState28(false);
7903
+ const [currentParentId, setCurrentParentId] = useState28(null);
7904
+ const [crumb, setCrumb] = useState28([]);
7905
+ const [newFolderOpen, setNewFolderOpen] = useState28(false);
7906
+ const [newFolderName, setNewFolderName] = useState28("");
7907
+ const [editModal, setEditModal] = useState28(null);
7908
+ const [deleteTarget, setDeleteTarget] = useState28(null);
7909
+ const [editAlt, setEditAlt] = useState28("");
7910
+ const [editPublic, setEditPublic] = useState28(false);
7911
+ const [editFilename, setEditFilename] = useState28("");
7912
+ const [extractingId, setExtractingId] = useState28(null);
7913
+ const fileInputRef = useRef9(null);
7160
7914
  const load = useCallback5(async () => {
7161
7915
  setLoading(true);
7162
7916
  const params = new URLSearchParams({
7163
7917
  page: String(page),
7164
7918
  limit: "24",
7165
- sortField: "createdAt",
7166
- sortOrder: "desc"
7919
+ sortField,
7920
+ sortOrder
7167
7921
  });
7922
+ params.set("parentId", currentParentId === null ? "" : String(currentParentId));
7168
7923
  if (search) params.set("search", search);
7169
7924
  if (typeFilter) params.set("type", typeFilter);
7170
7925
  try {
@@ -7179,11 +7934,33 @@ function MediaLibraryPage() {
7179
7934
  } finally {
7180
7935
  setLoading(false);
7181
7936
  }
7182
- }, [page, search, typeFilter]);
7937
+ }, [page, search, typeFilter, currentParentId, sortField, sortOrder]);
7183
7938
  useEffect25(() => {
7184
7939
  load();
7185
7940
  }, [load]);
7186
7941
  const handleSearch = () => setSearch(searchInput.trim());
7942
+ const goRoot = useCallback5(() => {
7943
+ setPage(1);
7944
+ setCurrentParentId(null);
7945
+ setCrumb([]);
7946
+ }, []);
7947
+ const goCrumb = useCallback5((index) => {
7948
+ setPage(1);
7949
+ if (index < 0) {
7950
+ goRoot();
7951
+ return;
7952
+ }
7953
+ const slice = crumb.slice(0, index + 1);
7954
+ setCrumb(slice);
7955
+ const last = slice[slice.length - 1];
7956
+ setCurrentParentId(last.id);
7957
+ }, [crumb, goRoot]);
7958
+ const enterFolder = (item) => {
7959
+ if (item.kind !== "folder") return;
7960
+ setPage(1);
7961
+ setCurrentParentId(item.id);
7962
+ setCrumb((c) => [...c, { id: item.id, name: item.filename }]);
7963
+ };
7187
7964
  const handleUpload = async (e) => {
7188
7965
  const file = e.target.files?.[0];
7189
7966
  if (!file) return;
@@ -7191,6 +7968,7 @@ function MediaLibraryPage() {
7191
7968
  try {
7192
7969
  const formData = new FormData();
7193
7970
  formData.append("file", file);
7971
+ if (currentParentId != null) formData.append("parentId", String(currentParentId));
7194
7972
  const uploadRes = await fetch("/api/upload", { method: "POST", body: formData });
7195
7973
  const uploadJson = await uploadRes.json();
7196
7974
  if (!uploadRes.ok) throw new Error(uploadJson.error || "Upload failed");
@@ -7200,69 +7978,134 @@ function MediaLibraryPage() {
7200
7978
  method: "POST",
7201
7979
  headers: { "Content-Type": "application/json" },
7202
7980
  body: JSON.stringify({
7981
+ kind: "file",
7203
7982
  filename: file.name,
7204
7983
  url: filePath.startsWith("http") ? filePath : filePath,
7205
7984
  mimeType: file.type || "application/octet-stream",
7206
7985
  size: file.size,
7207
7986
  alt: null,
7208
- isPublic: false
7987
+ isPublic: false,
7988
+ parentId: currentParentId
7209
7989
  })
7210
7990
  });
7211
7991
  if (!createRes.ok) throw new Error("Failed to create media record");
7212
- toast3.success("File uploaded");
7992
+ toast4.success("File uploaded");
7213
7993
  load();
7214
7994
  } catch (err) {
7215
- toast3.error(err instanceof Error ? err.message : "Upload failed");
7995
+ toast4.error(err instanceof Error ? err.message : "Upload failed");
7216
7996
  } finally {
7217
7997
  setUploading(false);
7218
7998
  e.target.value = "";
7219
7999
  }
7220
8000
  };
7221
- const handleDelete = async (id) => {
7222
- if (!confirm("Delete this file?")) return;
8001
+ const createFolder = async () => {
8002
+ const name = newFolderName.trim();
8003
+ if (!name) {
8004
+ toast4.error("Enter a folder name");
8005
+ return;
8006
+ }
8007
+ try {
8008
+ const res = await fetch("/api/media", {
8009
+ method: "POST",
8010
+ headers: { "Content-Type": "application/json" },
8011
+ body: JSON.stringify({
8012
+ kind: "folder",
8013
+ filename: name,
8014
+ parentId: currentParentId
8015
+ })
8016
+ });
8017
+ const j = await res.json().catch(() => ({}));
8018
+ if (!res.ok) throw new Error(j.error || "Failed to create folder");
8019
+ toast4.success("Folder created");
8020
+ setNewFolderOpen(false);
8021
+ setNewFolderName("");
8022
+ load();
8023
+ } catch (err) {
8024
+ toast4.error(err instanceof Error ? err.message : "Failed");
8025
+ }
8026
+ };
8027
+ const handleExtractZip = async (id) => {
8028
+ setExtractingId(id);
8029
+ try {
8030
+ const res = await fetch(`/api/media/extract/${id}`, { method: "POST" });
8031
+ const j = await res.json().catch(() => ({}));
8032
+ if (!res.ok) throw new Error(j.error || "Extract failed");
8033
+ toast4.success(
8034
+ `Extracted ${j.files ?? 0} file(s)` + (j.folderEntries ? `, ${j.folderEntries} folder path(s)` : "")
8035
+ );
8036
+ load();
8037
+ } catch (e) {
8038
+ toast4.error(e instanceof Error ? e.message : "Extract failed");
8039
+ } finally {
8040
+ setExtractingId(null);
8041
+ }
8042
+ };
8043
+ const handleDelete = async (item) => {
7223
8044
  try {
7224
- const res = await fetch(`/api/media/${id}`, { method: "DELETE" });
8045
+ const res = await fetch(`/api/media/${item.id}`, { method: "DELETE" });
7225
8046
  if (!res.ok) throw new Error("Delete failed");
7226
- toast3.success("Deleted");
8047
+ toast4.success("Deleted");
8048
+ setDeleteTarget(null);
7227
8049
  load();
7228
8050
  } catch {
7229
- toast3.error("Delete failed");
8051
+ toast4.error("Delete failed");
7230
8052
  }
7231
8053
  };
7232
8054
  const handleSaveEdit = async () => {
7233
8055
  if (!editModal) return;
7234
8056
  try {
8057
+ const isFolder = editModal.kind === "folder";
8058
+ const body = isFolder ? { filename: editFilename.trim() || editModal.filename } : { alt: editAlt || null, isPublic: editPublic };
8059
+ if (isFolder && !body.filename) {
8060
+ toast4.error("Name required");
8061
+ return;
8062
+ }
7235
8063
  const res = await fetch(`/api/media/${editModal.id}`, {
7236
8064
  method: "PUT",
7237
8065
  headers: { "Content-Type": "application/json" },
7238
- body: JSON.stringify({ alt: editAlt || null, isPublic: editPublic })
8066
+ body: JSON.stringify(body)
7239
8067
  });
7240
8068
  if (!res.ok) throw new Error("Update failed");
7241
- toast3.success("Updated");
8069
+ toast4.success("Updated");
7242
8070
  setEditModal(null);
7243
8071
  load();
7244
8072
  } catch {
7245
- toast3.error("Update failed");
8073
+ toast4.error("Update failed");
7246
8074
  }
7247
8075
  };
7248
8076
  const copyUrl = (url) => {
7249
8077
  const full = url.startsWith("http") ? url : `${typeof window !== "undefined" ? window.location.origin : ""}${url}`;
7250
8078
  navigator.clipboard.writeText(full);
7251
- toast3.success("URL copied");
8079
+ toast4.success("URL copied");
7252
8080
  };
7253
8081
  const openEdit = (item) => {
7254
8082
  setEditModal(item);
7255
8083
  setEditAlt(item.alt || "");
7256
8084
  setEditPublic(item.isPublic);
8085
+ setEditFilename(item.filename);
7257
8086
  };
7258
- const grouped = groupByMonth(data);
7259
- const isImage = (mime) => getTypeCategory(mime) === "image";
8087
+ const isImage = (mime, kind, filename) => kind !== "folder" && getTypeCategory(mime, kind, filename) === "image";
8088
+ const listViewData = React17.useMemo(() => {
8089
+ const sorted = [...data];
8090
+ const byDateDesc = (a, b) => new Date(b.createdAt).getTime() - new Date(a.createdAt).getTime();
8091
+ const folders = sorted.filter((x) => x.kind === "folder").sort(byDateDesc);
8092
+ const files = sorted.filter((x) => x.kind !== "folder").sort(byDateDesc);
8093
+ return [...folders, ...files];
8094
+ }, [data]);
7260
8095
  return /* @__PURE__ */ jsxs44("div", { className: "min-w-0 rounded-lg bg-white shadow-md", children: [
7261
8096
  /* @__PURE__ */ jsxs44("div", { className: "bg-gray-800 border-b border-gray-700 px-4 py-2.5 rounded-t-lg", children: [
7262
8097
  /* @__PURE__ */ jsx53("h1", { className: "text-base font-semibold text-white", children: "Media Library" }),
7263
- /* @__PURE__ */ jsx53("p", { className: "text-xs text-gray-300 mt-0.5", children: "Upload and manage files. Group by type or date." })
8098
+ /* @__PURE__ */ jsx53("p", { className: "text-xs text-gray-300 mt-0.5", children: "Folders and files (Google Drive\u2013style). Storage mirrors the folder tree under uploads/." })
7264
8099
  ] }),
7265
8100
  /* @__PURE__ */ jsxs44("div", { className: "min-w-0 p-4 space-y-3", children: [
8101
+ /* @__PURE__ */ jsxs44("div", { className: "flex flex-wrap items-center gap-2 text-sm text-gray-700", children: [
8102
+ /* @__PURE__ */ jsx53("span", { className: "font-medium text-gray-600", children: "Location:" }),
8103
+ /* @__PURE__ */ jsx53("button", { type: "button", className: "text-blue-600 hover:underline", onClick: () => goCrumb(-1), children: "Media" }),
8104
+ crumb.map((c, i) => /* @__PURE__ */ jsxs44("span", { className: "flex items-center gap-1", children: [
8105
+ /* @__PURE__ */ jsx53("span", { className: "text-gray-400", children: "/" }),
8106
+ /* @__PURE__ */ jsx53("button", { type: "button", className: "text-blue-600 hover:underline", onClick: () => goCrumb(i), children: c.name })
8107
+ ] }, `${c.id}-${i}`))
8108
+ ] }),
7266
8109
  /* @__PURE__ */ jsxs44("div", { className: "flex flex-wrap items-center gap-3", children: [
7267
8110
  /* @__PURE__ */ jsx53(
7268
8111
  "input",
@@ -7272,7 +8115,7 @@ function MediaLibraryPage() {
7272
8115
  className: "hidden",
7273
8116
  onChange: handleUpload,
7274
8117
  disabled: uploading,
7275
- accept: "image/*,video/*,audio/*,.pdf,.doc,.docx"
8118
+ accept: "image/*,video/*,audio/*,.pdf,.doc,.docx,.zip"
7276
8119
  }
7277
8120
  ),
7278
8121
  /* @__PURE__ */ jsxs44(
@@ -7288,11 +8131,15 @@ function MediaLibraryPage() {
7288
8131
  ]
7289
8132
  }
7290
8133
  ),
8134
+ /* @__PURE__ */ jsxs44(Button, { type: "button", variant: "secondary", className: "flex items-center gap-2", onClick: () => setNewFolderOpen(true), children: [
8135
+ /* @__PURE__ */ jsx53(FolderPlus, { className: "h-4 w-4" }),
8136
+ "New folder"
8137
+ ] }),
7291
8138
  /* @__PURE__ */ jsxs44("div", { className: "flex items-center gap-2 flex-1 min-w-[200px]", children: [
7292
8139
  /* @__PURE__ */ jsx53(
7293
8140
  Input,
7294
8141
  {
7295
- placeholder: "Search by filename...",
8142
+ placeholder: "Search by name...",
7296
8143
  value: searchInput,
7297
8144
  onChange: (e) => setSearchInput(e.target.value),
7298
8145
  onKeyDown: (e) => e.key === "Enter" && handleSearch()
@@ -7314,61 +8161,192 @@ function MediaLibraryPage() {
7314
8161
  /* @__PURE__ */ jsx53("option", { value: "application", children: "Documents" })
7315
8162
  ]
7316
8163
  }
7317
- )
8164
+ ),
8165
+ /* @__PURE__ */ jsxs44(
8166
+ "select",
8167
+ {
8168
+ className: "border rounded-md px-3 py-2 text-sm bg-white max-w-[200px]",
8169
+ value: `${sortField}:${sortOrder}`,
8170
+ onChange: (e) => {
8171
+ const [f, o] = e.target.value.split(":");
8172
+ setSortField(f);
8173
+ setSortOrder(o);
8174
+ setPage(1);
8175
+ },
8176
+ children: [
8177
+ /* @__PURE__ */ jsx53("option", { value: "filename:asc", children: "Name A\u2013Z" }),
8178
+ /* @__PURE__ */ jsx53("option", { value: "filename:desc", children: "Name Z\u2013A" }),
8179
+ /* @__PURE__ */ jsx53("option", { value: "createdAt:desc", children: "Newest first" }),
8180
+ /* @__PURE__ */ jsx53("option", { value: "createdAt:asc", children: "Oldest first" })
8181
+ ]
8182
+ }
8183
+ ),
8184
+ /* @__PURE__ */ jsxs44("div", { className: "inline-flex rounded-md border border-gray-300 overflow-hidden bg-white", children: [
8185
+ /* @__PURE__ */ jsxs44(
8186
+ "button",
8187
+ {
8188
+ type: "button",
8189
+ className: `px-2.5 py-2 text-xs inline-flex items-center gap-1 ${viewMode === "grid" ? "bg-gray-100 text-gray-900" : "text-gray-600"}`,
8190
+ onClick: () => setViewMode("grid"),
8191
+ title: "Grid view",
8192
+ children: [
8193
+ /* @__PURE__ */ jsx53(LayoutGrid, { className: "h-4 w-4" }),
8194
+ "Grid"
8195
+ ]
8196
+ }
8197
+ ),
8198
+ /* @__PURE__ */ jsxs44(
8199
+ "button",
8200
+ {
8201
+ type: "button",
8202
+ className: `px-2.5 py-2 text-xs inline-flex items-center gap-1 border-l border-gray-300 ${viewMode === "list" ? "bg-gray-100 text-gray-900" : "text-gray-600"}`,
8203
+ onClick: () => setViewMode("list"),
8204
+ title: "List view",
8205
+ children: [
8206
+ /* @__PURE__ */ jsx53(List, { className: "h-4 w-4" }),
8207
+ "List"
8208
+ ]
8209
+ }
8210
+ )
8211
+ ] })
7318
8212
  ] }),
7319
- loading ? /* @__PURE__ */ jsx53("div", { className: "flex justify-center py-12", children: /* @__PURE__ */ jsx53("div", { className: "animate-spin rounded-full h-8 w-8 border-2 border-gray-300 border-t-gray-600" }) }) : data.length === 0 ? /* @__PURE__ */ jsx53("div", { className: "text-center py-12 text-gray-500", children: "No media yet. Upload a file to get started." }) : /* @__PURE__ */ jsx53("div", { className: "space-y-8", children: Object.entries(grouped).map(([monthLabel, items]) => /* @__PURE__ */ jsxs44("div", { children: [
7320
- /* @__PURE__ */ jsx53("h2", { className: "text-sm font-semibold text-gray-500 uppercase tracking-wider mb-3", children: monthLabel }),
7321
- /* @__PURE__ */ jsx53("div", { className: "grid grid-cols-2 sm:grid-cols-3 md:grid-cols-4 lg:grid-cols-6 gap-4", children: items.map((item) => /* @__PURE__ */ jsxs44(
8213
+ loading ? /* @__PURE__ */ jsx53("div", { className: "flex justify-center py-12", children: /* @__PURE__ */ jsx53("div", { className: "animate-spin rounded-full h-8 w-8 border-2 border-gray-300 border-t-gray-600" }) }) : data.length === 0 ? /* @__PURE__ */ jsx53("div", { className: "text-center py-12 text-gray-500", children: "This folder is empty. Create a folder or upload a file." }) : viewMode === "grid" ? /* @__PURE__ */ jsx53("div", { className: "grid grid-cols-2 sm:grid-cols-3 md:grid-cols-4 lg:grid-cols-6 gap-4", children: data.map((item) => {
8214
+ const isF = item.kind === "folder";
8215
+ return /* @__PURE__ */ jsxs44(
7322
8216
  "div",
7323
8217
  {
7324
8218
  className: "border rounded-lg overflow-hidden bg-gray-50 hover:bg-gray-100 transition-colors group",
7325
8219
  children: [
7326
- /* @__PURE__ */ jsxs44("div", { className: "aspect-square flex items-center justify-center bg-gray-200 relative", children: [
7327
- isImage(item.mimeType) ? /* @__PURE__ */ jsx53(
7328
- "img",
7329
- {
7330
- src: item.url,
7331
- alt: item.alt || item.filename,
7332
- className: "w-full h-full object-cover"
7333
- }
7334
- ) : /* @__PURE__ */ jsx53(TypeIcon, { mimeType: item.mimeType }),
7335
- /* @__PURE__ */ jsxs44("div", { className: "absolute inset-0 bg-black/0 group-hover:bg-black/40 transition-colors flex items-center justify-center gap-1 opacity-0 group-hover:opacity-100", children: [
7336
- /* @__PURE__ */ jsx53(
7337
- Button,
7338
- {
7339
- size: "icon",
7340
- variant: "secondary",
7341
- className: "h-8 w-8",
7342
- onClick: () => copyUrl(item.url),
7343
- children: /* @__PURE__ */ jsx53(Copy, { className: "h-3 w-3" })
7344
- }
7345
- ),
7346
- /* @__PURE__ */ jsx53(Button, { size: "icon", variant: "secondary", className: "h-8 w-8", onClick: () => openEdit(item), children: /* @__PURE__ */ jsx53(Edit2, { className: "h-3 w-3" }) }),
7347
- /* @__PURE__ */ jsx53(
7348
- Button,
7349
- {
7350
- size: "icon",
7351
- variant: "destructive",
7352
- className: "h-8 w-8",
7353
- onClick: () => handleDelete(item.id),
7354
- children: /* @__PURE__ */ jsx53(Trash24, { className: "h-3 w-3" })
7355
- }
7356
- )
7357
- ] })
7358
- ] }),
8220
+ /* @__PURE__ */ jsxs44(
8221
+ "button",
8222
+ {
8223
+ type: "button",
8224
+ className: "w-full aspect-square flex items-center justify-center bg-gray-200 relative cursor-pointer",
8225
+ onClick: () => isF && enterFolder(item),
8226
+ children: [
8227
+ isImage(item.mimeType, item.kind, item.filename) ? /* @__PURE__ */ jsx53(
8228
+ "img",
8229
+ {
8230
+ src: item.url,
8231
+ alt: item.alt || item.filename,
8232
+ className: "w-full h-full object-cover"
8233
+ }
8234
+ ) : /* @__PURE__ */ jsx53(TypeIcon, { mimeType: item.mimeType, kind: item.kind, filename: item.filename }),
8235
+ /* @__PURE__ */ jsxs44("div", { className: "absolute inset-0 bg-black/0 group-hover:bg-black/40 transition-colors flex items-center justify-center gap-1 opacity-0 group-hover:opacity-100 flex-wrap", children: [
8236
+ !isF && isZipMedia(item.mimeType, item.filename) ? /* @__PURE__ */ jsx53(
8237
+ Button,
8238
+ {
8239
+ size: "icon",
8240
+ variant: "outline",
8241
+ className: "h-8 w-8",
8242
+ title: "Extract zip into this folder",
8243
+ disabled: extractingId === item.id,
8244
+ onClick: (e) => {
8245
+ e.stopPropagation();
8246
+ handleExtractZip(item.id);
8247
+ },
8248
+ children: /* @__PURE__ */ jsx53(Archive, { className: "h-3 w-3" })
8249
+ }
8250
+ ) : null,
8251
+ !isF && item.url ? /* @__PURE__ */ jsx53(
8252
+ Button,
8253
+ {
8254
+ size: "icon",
8255
+ variant: "outline",
8256
+ className: "h-8 w-8",
8257
+ onClick: (e) => {
8258
+ e.stopPropagation();
8259
+ copyUrl(item.url);
8260
+ },
8261
+ children: /* @__PURE__ */ jsx53(Copy, { className: "h-3 w-3" })
8262
+ }
8263
+ ) : null,
8264
+ /* @__PURE__ */ jsx53(
8265
+ Button,
8266
+ {
8267
+ size: "icon",
8268
+ variant: "outline",
8269
+ className: "h-8 w-8",
8270
+ onClick: (e) => {
8271
+ e.stopPropagation();
8272
+ openEdit(item);
8273
+ },
8274
+ children: /* @__PURE__ */ jsx53(Edit2, { className: "h-3 w-3" })
8275
+ }
8276
+ ),
8277
+ /* @__PURE__ */ jsx53(
8278
+ Button,
8279
+ {
8280
+ size: "icon",
8281
+ variant: "outline",
8282
+ className: "h-8 w-8 border-red-300 text-red-600 hover:text-red-700",
8283
+ onClick: (e) => {
8284
+ e.stopPropagation();
8285
+ setDeleteTarget(item);
8286
+ },
8287
+ children: /* @__PURE__ */ jsx53(Trash24, { className: "h-3 w-3" })
8288
+ }
8289
+ )
8290
+ ] })
8291
+ ]
8292
+ }
8293
+ ),
7359
8294
  /* @__PURE__ */ jsxs44("div", { className: "p-2", children: [
7360
- /* @__PURE__ */ jsx53("p", { className: "text-xs font-medium text-gray-900 truncate", title: item.filename, children: item.filename }),
8295
+ /* @__PURE__ */ jsx53("p", { className: "text-xs font-medium text-gray-900 truncate text-left", title: item.filename, children: item.filename }),
7361
8296
  /* @__PURE__ */ jsxs44("div", { className: "flex items-center justify-between mt-1", children: [
7362
8297
  /* @__PURE__ */ jsx53("span", { className: "text-xs text-gray-500", children: formatDate(item.createdAt) }),
7363
- /* @__PURE__ */ jsx53("span", { className: "text-xs px-1.5 py-0.5 rounded bg-gray-200 text-gray-600", children: getTypeLabel(item.mimeType) })
8298
+ /* @__PURE__ */ jsx53("span", { className: "text-xs px-1.5 py-0.5 rounded bg-gray-200 text-gray-600", children: getTypeLabel(item.mimeType, item.kind, item.filename) })
7364
8299
  ] }),
7365
- item.isPublic && /* @__PURE__ */ jsx53("span", { className: "text-xs text-green-600 mt-0.5 block", children: "Public" })
8300
+ item.isPublic && !isF && /* @__PURE__ */ jsx53("span", { className: "text-xs text-green-600 mt-0.5 block", children: "Public" }),
8301
+ isF && /* @__PURE__ */ jsx53(
8302
+ "button",
8303
+ {
8304
+ type: "button",
8305
+ className: "text-xs text-blue-600 mt-1 hover:underline",
8306
+ onClick: () => enterFolder(item),
8307
+ children: "Open"
8308
+ }
8309
+ )
7366
8310
  ] })
7367
8311
  ]
7368
8312
  },
7369
8313
  item.id
7370
- )) })
7371
- ] }, monthLabel)) }),
8314
+ );
8315
+ }) }) : /* @__PURE__ */ jsx53("div", { className: "overflow-x-auto rounded-md border border-gray-200 bg-white", children: /* @__PURE__ */ jsxs44("table", { className: "w-full text-sm", children: [
8316
+ /* @__PURE__ */ jsx53("thead", { children: /* @__PURE__ */ jsxs44("tr", { className: "border-b bg-gray-50", children: [
8317
+ /* @__PURE__ */ jsx53("th", { className: "p-3 text-left font-medium", children: "Name" }),
8318
+ /* @__PURE__ */ jsx53("th", { className: "p-3 text-left font-medium", children: "Type" }),
8319
+ /* @__PURE__ */ jsx53("th", { className: "p-3 text-left font-medium", children: "Created" }),
8320
+ /* @__PURE__ */ jsx53("th", { className: "p-3 text-left font-medium", children: "Size" }),
8321
+ /* @__PURE__ */ jsx53("th", { className: "p-3 text-right font-medium", children: "Actions" })
8322
+ ] }) }),
8323
+ /* @__PURE__ */ jsx53("tbody", { children: listViewData.map((item) => {
8324
+ const isF = item.kind === "folder";
8325
+ return /* @__PURE__ */ jsxs44("tr", { className: "border-b border-gray-100 hover:bg-gray-50", children: [
8326
+ /* @__PURE__ */ jsx53("td", { className: "p-3", children: /* @__PURE__ */ jsxs44(
8327
+ "button",
8328
+ {
8329
+ type: "button",
8330
+ className: `inline-flex items-center gap-2 ${isF ? "text-blue-600 hover:underline" : "text-gray-900"}`,
8331
+ onClick: () => isF && enterFolder(item),
8332
+ children: [
8333
+ /* @__PURE__ */ jsx53(TypeIcon, { mimeType: item.mimeType, kind: item.kind, filename: item.filename }),
8334
+ /* @__PURE__ */ jsx53("span", { className: "truncate max-w-[260px]", title: item.filename, children: item.filename })
8335
+ ]
8336
+ }
8337
+ ) }),
8338
+ /* @__PURE__ */ jsx53("td", { className: "p-3 text-gray-600", children: getTypeLabel(item.mimeType, item.kind, item.filename) }),
8339
+ /* @__PURE__ */ jsx53("td", { className: "p-3 text-gray-600", children: formatDate(item.createdAt) }),
8340
+ /* @__PURE__ */ jsx53("td", { className: "p-3 text-gray-600", children: isF ? "\u2014" : `${Math.round((item.size || 0) / 1024)} KB` }),
8341
+ /* @__PURE__ */ jsx53("td", { className: "p-3", children: /* @__PURE__ */ jsxs44("div", { className: "flex items-center justify-end gap-1", children: [
8342
+ !isF && isZipMedia(item.mimeType, item.filename) && /* @__PURE__ */ jsx53(Button, { size: "icon", variant: "outline", className: "h-8 w-8", onClick: () => handleExtractZip(item.id), disabled: extractingId === item.id, children: /* @__PURE__ */ jsx53(Archive, { className: "h-3 w-3" }) }),
8343
+ !isF && item.url && /* @__PURE__ */ jsx53(Button, { size: "icon", variant: "outline", className: "h-8 w-8", onClick: () => copyUrl(item.url), children: /* @__PURE__ */ jsx53(Copy, { className: "h-3 w-3" }) }),
8344
+ /* @__PURE__ */ jsx53(Button, { size: "icon", variant: "outline", className: "h-8 w-8", onClick: () => openEdit(item), children: /* @__PURE__ */ jsx53(Edit2, { className: "h-3 w-3" }) }),
8345
+ /* @__PURE__ */ jsx53(Button, { size: "icon", variant: "outline", className: "h-8 w-8 border-red-300 text-red-600 hover:text-red-700", onClick: () => setDeleteTarget(item), children: /* @__PURE__ */ jsx53(Trash24, { className: "h-3 w-3" }) })
8346
+ ] }) })
8347
+ ] }, item.id);
8348
+ }) })
8349
+ ] }) }),
7372
8350
  totalPages > 1 && /* @__PURE__ */ jsx53(Pagination, { className: "mt-6", children: /* @__PURE__ */ jsxs44(PaginationContent, { children: [
7373
8351
  /* @__PURE__ */ jsx53(PaginationItem, { children: /* @__PURE__ */ jsx53(
7374
8352
  PaginationPrevious,
@@ -7390,9 +8368,28 @@ function MediaLibraryPage() {
7390
8368
  ) })
7391
8369
  ] }) })
7392
8370
  ] }),
8371
+ /* @__PURE__ */ jsx53(Dialog, { open: newFolderOpen, onOpenChange: setNewFolderOpen, children: /* @__PURE__ */ jsxs44(DialogContent, { children: [
8372
+ /* @__PURE__ */ jsx53(DialogHeader, { children: /* @__PURE__ */ jsx53(DialogTitle, { children: "New folder" }) }),
8373
+ /* @__PURE__ */ jsx53(
8374
+ Input,
8375
+ {
8376
+ placeholder: "Folder name",
8377
+ value: newFolderName,
8378
+ onChange: (e) => setNewFolderName(e.target.value),
8379
+ onKeyDown: (e) => e.key === "Enter" && createFolder()
8380
+ }
8381
+ ),
8382
+ /* @__PURE__ */ jsxs44(DialogFooter, { children: [
8383
+ /* @__PURE__ */ jsx53(Button, { variant: "outline", onClick: () => setNewFolderOpen(false), children: "Cancel" }),
8384
+ /* @__PURE__ */ jsx53(Button, { onClick: createFolder, children: "Create" })
8385
+ ] })
8386
+ ] }) }),
7393
8387
  /* @__PURE__ */ jsx53(Dialog, { open: !!editModal, onOpenChange: (open) => !open && setEditModal(null), children: /* @__PURE__ */ jsxs44(DialogContent, { children: [
7394
- /* @__PURE__ */ jsx53(DialogHeader, { children: /* @__PURE__ */ jsx53(DialogTitle, { children: "Edit media" }) }),
7395
- editModal && /* @__PURE__ */ jsxs44("div", { className: "space-y-4 py-2", children: [
8388
+ /* @__PURE__ */ jsx53(DialogHeader, { children: /* @__PURE__ */ jsx53(DialogTitle, { children: editModal?.kind === "folder" ? "Rename folder" : "Edit media" }) }),
8389
+ editModal && /* @__PURE__ */ jsx53("div", { className: "space-y-4 py-2", children: editModal.kind === "folder" ? /* @__PURE__ */ jsxs44("div", { children: [
8390
+ /* @__PURE__ */ jsx53("label", { className: "text-sm font-medium", children: "Name" }),
8391
+ /* @__PURE__ */ jsx53(Input, { value: editFilename, onChange: (e) => setEditFilename(e.target.value), className: "mt-1" })
8392
+ ] }) : /* @__PURE__ */ jsxs44(Fragment12, { children: [
7396
8393
  /* @__PURE__ */ jsxs44("div", { children: [
7397
8394
  /* @__PURE__ */ jsx53("label", { className: "text-sm font-medium", children: "Alt text" }),
7398
8395
  /* @__PURE__ */ jsx53(
@@ -7417,20 +8414,37 @@ function MediaLibraryPage() {
7417
8414
  ),
7418
8415
  /* @__PURE__ */ jsx53("label", { htmlFor: "edit-public", className: "text-sm", children: "Public (visible on site)" })
7419
8416
  ] })
7420
- ] }),
8417
+ ] }) }),
7421
8418
  /* @__PURE__ */ jsxs44(DialogFooter, { children: [
7422
8419
  /* @__PURE__ */ jsx53(Button, { variant: "outline", onClick: () => setEditModal(null), children: "Cancel" }),
7423
8420
  /* @__PURE__ */ jsx53(Button, { onClick: handleSaveEdit, children: "Save" })
7424
8421
  ] })
8422
+ ] }) }),
8423
+ /* @__PURE__ */ jsx53(Dialog, { open: !!deleteTarget, onOpenChange: (open) => !open && setDeleteTarget(null), children: /* @__PURE__ */ jsxs44(DialogContent, { children: [
8424
+ /* @__PURE__ */ jsx53(DialogHeader, { children: /* @__PURE__ */ jsx53(DialogTitle, { children: "Confirm Delete" }) }),
8425
+ /* @__PURE__ */ jsx53("p", { className: "text-sm text-gray-600", children: deleteTarget?.kind === "folder" ? "Delete this folder and everything inside it?" : "Delete this file?" }),
8426
+ /* @__PURE__ */ jsxs44(DialogFooter, { children: [
8427
+ /* @__PURE__ */ jsx53(Button, { variant: "outline", onClick: () => setDeleteTarget(null), children: "Cancel" }),
8428
+ /* @__PURE__ */ jsx53(
8429
+ Button,
8430
+ {
8431
+ variant: "destructive",
8432
+ onClick: () => {
8433
+ if (deleteTarget) handleDelete(deleteTarget);
8434
+ },
8435
+ children: "Delete"
8436
+ }
8437
+ )
8438
+ ] })
7425
8439
  ] }) })
7426
8440
  ] });
7427
8441
  }
7428
8442
 
7429
8443
  // src/admin/pages/PageBuilderPage.tsx
7430
- import { useState as useState28, useEffect as useEffect26, useContext as useContext4, useRef as useRef9 } from "react";
8444
+ import { useState as useState29, useEffect as useEffect26, useContext as useContext5, useRef as useRef10 } from "react";
7431
8445
  import { Editor, Frame, Element, useEditor, useNode } from "@craftjs/core";
7432
8446
  import { Save as Save4, X as X17, ChevronDown as ChevronDown5, ChevronRight as ChevronRight4, LayoutDashboard as LayoutDashboard3, Layers as Layers2, Box, SlidersHorizontal } from "lucide-react";
7433
- import { useRouter as useRouter9 } from "next/navigation";
8447
+ import { useRouter as useRouter11 } from "next/navigation";
7434
8448
 
7435
8449
  // src/theme/registry.ts
7436
8450
  function buildResolver(theme) {
@@ -7456,7 +8470,7 @@ function getCatalog(theme) {
7456
8470
  // src/admin/pages/PageBuilderPage.tsx
7457
8471
  import * as LucideIcons from "lucide-react";
7458
8472
  import React18 from "react";
7459
- import { Fragment as Fragment11, jsx as jsx54, jsxs as jsxs45 } from "react/jsx-runtime";
8473
+ import { Fragment as Fragment13, jsx as jsx54, jsxs as jsxs45 } from "react/jsx-runtime";
7460
8474
  function createSelectable(Comp) {
7461
8475
  function SelectableWrapper(props) {
7462
8476
  const { id, connectors, displayName, isHovered } = useNode((node) => ({
@@ -7500,7 +8514,7 @@ function DraggableCatalogItem({
7500
8514
  Icon: Icon2,
7501
8515
  description
7502
8516
  }) {
7503
- const elRef = useRef9(null);
8517
+ const elRef = useRef10(null);
7504
8518
  useEffect26(() => {
7505
8519
  if (!elRef.current) return;
7506
8520
  if (meta.canContainChildren) {
@@ -7528,7 +8542,7 @@ function DraggableCatalogItem({
7528
8542
  function ComponentPickerContent({ theme, resolver }) {
7529
8543
  const { connectors } = useEditor();
7530
8544
  const catalog = getCatalog(theme);
7531
- const [collapsed, setCollapsed] = useState28({});
8545
+ const [collapsed, setCollapsed] = useState29({});
7532
8546
  const toggleCategory = (cat) => {
7533
8547
  setCollapsed((prev) => ({ ...prev, [cat]: !prev[cat] }));
7534
8548
  };
@@ -7733,7 +8747,7 @@ function LayersPanelContent() {
7733
8747
  nodes: state.nodes,
7734
8748
  selectedSet: state.events.selected
7735
8749
  }));
7736
- const [expanded, setExpanded] = useState28({});
8750
+ const [expanded, setExpanded] = useState29({});
7737
8751
  const nodeMap = nodes || {};
7738
8752
  const rootId = (() => {
7739
8753
  const ids = Object.keys(nodeMap);
@@ -7855,10 +8869,10 @@ function CollapsibleSection({
7855
8869
  ] });
7856
8870
  }
7857
8871
  function RightSidebar({ theme, resolver, activeTab, setActiveTab, seoProps }) {
7858
- const [componentsOpen, setComponentsOpen] = useState28(true);
7859
- const [propertiesOpen, setPropertiesOpen] = useState28(true);
7860
- const [layoutOpen, setLayoutOpen] = useState28(true);
7861
- const [layersOpen, setLayersOpen] = useState28(true);
8872
+ const [componentsOpen, setComponentsOpen] = useState29(true);
8873
+ const [propertiesOpen, setPropertiesOpen] = useState29(true);
8874
+ const [layoutOpen, setLayoutOpen] = useState29(true);
8875
+ const [layersOpen, setLayersOpen] = useState29(true);
7862
8876
  return /* @__PURE__ */ jsxs45("div", { className: "flex flex-col flex-1 overflow-hidden", children: [
7863
8877
  /* @__PURE__ */ jsx54("div", { className: "flex border-b flex-shrink-0", children: ["designer", "seo"].map((tab) => /* @__PURE__ */ jsx54(
7864
8878
  "button",
@@ -7870,7 +8884,7 @@ function RightSidebar({ theme, resolver, activeTab, setActiveTab, seoProps }) {
7870
8884
  tab
7871
8885
  )) }),
7872
8886
  /* @__PURE__ */ jsxs45("div", { className: "flex-1 overflow-y-auto flex flex-col min-h-0", children: [
7873
- activeTab === "designer" && /* @__PURE__ */ jsxs45(Fragment11, { children: [
8887
+ activeTab === "designer" && /* @__PURE__ */ jsxs45(Fragment13, { children: [
7874
8888
  /* @__PURE__ */ jsx54(
7875
8889
  CollapsibleSection,
7876
8890
  {
@@ -7926,7 +8940,7 @@ function SaveButton({
7926
8940
  className
7927
8941
  }) {
7928
8942
  const { query } = useEditor();
7929
- const [saving, setSaving] = useState28(false);
8943
+ const [saving, setSaving] = useState29(false);
7930
8944
  const handleSave = async () => {
7931
8945
  setSaving(true);
7932
8946
  try {
@@ -7998,21 +9012,21 @@ function SaveButton({
7998
9012
  );
7999
9013
  }
8000
9014
  function PageBuilderPage({ pageId }) {
8001
- const { theme } = useContext4(AdminConfigContext);
8002
- const router = useRouter9();
8003
- const [title, setTitle] = useState28("");
8004
- const [slug, setSlug] = useState28("");
8005
- const [published, setPublished] = useState28(false);
8006
- const [initialContent, setInitialContent] = useState28(null);
8007
- const [loading, setLoading] = useState28(!!pageId);
8008
- const [rightTab, setRightTab] = useState28("designer");
8009
- const [seoTitle, setSeoTitle] = useState28("");
8010
- const [seoDescription, setSeoDescription] = useState28("");
8011
- const [seoKeywords, setSeoKeywords] = useState28("");
8012
- const [seoOgTitle, setSeoOgTitle] = useState28("");
8013
- const [seoOgDescription, setSeoOgDescription] = useState28("");
8014
- const [seoOgImage, setSeoOgImage] = useState28("");
8015
- const [pageSeoId, setPageSeoId] = useState28(null);
9015
+ const { theme } = useContext5(AdminConfigContext);
9016
+ const router = useRouter11();
9017
+ const [title, setTitle] = useState29("");
9018
+ const [slug, setSlug] = useState29("");
9019
+ const [published, setPublished] = useState29(false);
9020
+ const [initialContent, setInitialContent] = useState29(null);
9021
+ const [loading, setLoading] = useState29(!!pageId);
9022
+ const [rightTab, setRightTab] = useState29("designer");
9023
+ const [seoTitle, setSeoTitle] = useState29("");
9024
+ const [seoDescription, setSeoDescription] = useState29("");
9025
+ const [seoKeywords, setSeoKeywords] = useState29("");
9026
+ const [seoOgTitle, setSeoOgTitle] = useState29("");
9027
+ const [seoOgDescription, setSeoOgDescription] = useState29("");
9028
+ const [seoOgImage, setSeoOgImage] = useState29("");
9029
+ const [pageSeoId, setPageSeoId] = useState29(null);
8016
9030
  useEffect26(() => {
8017
9031
  if (!pageId) {
8018
9032
  setInitialContent(null);
@@ -8087,19 +9101,49 @@ function PageBuilderPage({ pageId }) {
8087
9101
  onSaved: (id) => {
8088
9102
  if (!pageId) router.replace(`/admin/pages/${id}`);
8089
9103
  },
8090
- className: "flex items-center bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
9104
+ className: "md:hidden h-8 w-8 p-0 bg-white text-gray-800 hover:bg-gray-100 border-0",
9105
+ children: [
9106
+ /* @__PURE__ */ jsx54(Save4, { className: "h-4 w-4" }),
9107
+ /* @__PURE__ */ jsx54("span", { className: "sr-only", children: "Save" })
9108
+ ]
9109
+ }
9110
+ ),
9111
+ /* @__PURE__ */ jsxs45(
9112
+ SaveButton,
9113
+ {
9114
+ pageId,
9115
+ existingSeoId: pageSeoId,
9116
+ onSeoIdChange: setPageSeoId,
9117
+ pageData: { title, slug, published, seoTitle, seoDescription, seoKeywords, seoOgTitle, seoOgDescription, seoOgImage },
9118
+ onSaved: (id) => {
9119
+ if (!pageId) router.replace(`/admin/pages/${id}`);
9120
+ },
9121
+ className: "hidden md:inline-flex items-center bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
8091
9122
  children: [
8092
9123
  /* @__PURE__ */ jsx54(Save4, { className: "h-4 w-4 mr-1" }),
8093
9124
  " Save"
8094
9125
  ]
8095
9126
  }
8096
9127
  ),
9128
+ /* @__PURE__ */ jsxs45(
9129
+ Button,
9130
+ {
9131
+ variant: "outline",
9132
+ size: "icon",
9133
+ className: "md:hidden h-8 w-8 bg-white text-gray-800 hover:bg-gray-100 border-0",
9134
+ onClick: () => router.push("/admin/pages"),
9135
+ children: [
9136
+ /* @__PURE__ */ jsx54(X17, { className: "h-4 w-4" }),
9137
+ /* @__PURE__ */ jsx54("span", { className: "sr-only", children: "Close" })
9138
+ ]
9139
+ }
9140
+ ),
8097
9141
  /* @__PURE__ */ jsxs45(
8098
9142
  Button,
8099
9143
  {
8100
9144
  variant: "outline",
8101
9145
  size: "sm",
8102
- className: "flex items-center bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
9146
+ className: "hidden md:inline-flex items-center bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
8103
9147
  onClick: () => router.push("/admin/pages"),
8104
9148
  children: [
8105
9149
  /* @__PURE__ */ jsx54(X17, { className: "h-4 w-4 mr-1" }),
@@ -8160,7 +9204,7 @@ function PageBuilderPage({ pageId }) {
8160
9204
  }
8161
9205
 
8162
9206
  // src/admin/pages/PluginsPage.tsx
8163
- import { useContext as useContext5, useState as useState29, useEffect as useEffect27 } from "react";
9207
+ import { useContext as useContext6, useState as useState30, useEffect as useEffect27 } from "react";
8164
9208
  import { HardDrive, Mail, CreditCard as CreditCard2, MessageCircle, BarChart3 as BarChart32, Building2 as Building22, Puzzle as Puzzle2, CheckCircle2 as CheckCircle22, XCircle, Save as Save5, X as X18, Plus as Plus8, Smartphone } from "lucide-react";
8165
9209
 
8166
9210
  // src/lib/email-recipients.ts
@@ -8185,7 +9229,7 @@ function serializeEmailRecipients(emails) {
8185
9229
  // src/components/ui/checkbox.tsx
8186
9230
  import * as React19 from "react";
8187
9231
  import * as CheckboxPrimitive from "@radix-ui/react-checkbox";
8188
- import { Check as Check6 } from "lucide-react";
9232
+ import { Check as Check7 } from "lucide-react";
8189
9233
  import { jsx as jsx55 } from "react/jsx-runtime";
8190
9234
  var Checkbox = React19.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx55(
8191
9235
  CheckboxPrimitive.Root,
@@ -8200,7 +9244,7 @@ var Checkbox = React19.forwardRef(({ className, ...props }, ref) => /* @__PURE__
8200
9244
  CheckboxPrimitive.Indicator,
8201
9245
  {
8202
9246
  className: cn("flex items-center justify-center text-current"),
8203
- children: /* @__PURE__ */ jsx55(Check6, { className: "h-4 w-4" })
9247
+ children: /* @__PURE__ */ jsx55(Check7, { className: "h-4 w-4" })
8204
9248
  }
8205
9249
  )
8206
9250
  }
@@ -8208,8 +9252,8 @@ var Checkbox = React19.forwardRef(({ className, ...props }, ref) => /* @__PURE__
8208
9252
  Checkbox.displayName = CheckboxPrimitive.Root.displayName;
8209
9253
 
8210
9254
  // src/admin/pages/PluginsPage.tsx
8211
- import { toast as toast4 } from "sonner";
8212
- import { Fragment as Fragment12, jsx as jsx56, jsxs as jsxs46 } from "react/jsx-runtime";
9255
+ import { toast as toast5 } from "sonner";
9256
+ import { Fragment as Fragment14, jsx as jsx56, jsxs as jsxs46 } from "react/jsx-runtime";
8213
9257
  function normalizeChatMode(raw) {
8214
9258
  if (raw === "external" || raw === "llm") return raw;
8215
9259
  return "whatsapp";
@@ -8274,7 +9318,7 @@ function EmailRecipientTags({
8274
9318
  onChange,
8275
9319
  placeholder
8276
9320
  }) {
8277
- const [draft, setDraft] = useState29("");
9321
+ const [draft, setDraft] = useState30("");
8278
9322
  const commitDraft = () => {
8279
9323
  const parts = splitInputToEmails(draft);
8280
9324
  if (!parts.length) return;
@@ -8350,35 +9394,35 @@ function PluginSettingsPanel({
8350
9394
  const isEmail = settingsGroup === "email";
8351
9395
  const isErp = settingsGroup === "erp";
8352
9396
  const isSms = settingsGroup === "sms";
8353
- const [enabled, setEnabled] = useState29(true);
8354
- const [botName, setBotName] = useState29("");
8355
- const [icon, setIcon] = useState29("");
8356
- const [iconImageUrl, setIconImageUrl] = useState29("");
8357
- const [iconBackgroundColor, setIconBackgroundColor] = useState29("#6366f1");
8358
- const [headerColor, setHeaderColor] = useState29("#6366f1");
8359
- const [salesTeamEmails, setSalesTeamEmails] = useState29([]);
8360
- const [fulfilmentTeamEmails, setFulfilmentTeamEmails] = useState29([]);
8361
- const [crmEmails, setCrmEmails] = useState29([]);
8362
- const [logoUrl, setLogoUrl] = useState29("");
8363
- const [companyName, setCompanyName] = useState29("");
8364
- const [supportEmail, setSupportEmail] = useState29("");
8365
- const [supportPhone, setSupportPhone] = useState29("");
8366
- const [followUsTitle, setFollowUsTitle] = useState29("Follow Us");
8367
- const [socialLinkRows, setSocialLinkRows] = useState29([{ ...EMPTY_SOCIAL_ROW }]);
8368
- const [footerDisclaimer, setFooterDisclaimer] = useState29("");
8369
- const [chatMode, setChatMode] = useState29("whatsapp");
8370
- const [whatsappPhone, setWhatsappPhone] = useState29("");
8371
- const [externalChatSnippet, setExternalChatSnippet] = useState29("");
8372
- const [erpPipelineName, setErpPipelineName] = useState29("");
8373
- const [erpPipelineStageName, setErpPipelineStageName] = useState29("");
8374
- const [erpFormsCatalog, setErpFormsCatalog] = useState29([]);
8375
- const [erpOpportunityFormIds, setErpOpportunityFormIds] = useState29([]);
8376
- const [erpOpportunityIdsKeyPresent, setErpOpportunityIdsKeyPresent] = useState29(false);
8377
- const [smsProviderChoice, setSmsProviderChoice] = useState29("auto");
8378
- const [msg91ApiMode, setMsg91ApiMode] = useState29("auto");
8379
- const [smsTplItems, setSmsTplItems] = useState29([]);
8380
- const [loading, setLoading] = useState29(true);
8381
- const [saving, setSaving] = useState29(false);
9397
+ const [enabled, setEnabled] = useState30(true);
9398
+ const [botName, setBotName] = useState30("");
9399
+ const [icon, setIcon] = useState30("");
9400
+ const [iconImageUrl, setIconImageUrl] = useState30("");
9401
+ const [iconBackgroundColor, setIconBackgroundColor] = useState30("#6366f1");
9402
+ const [headerColor, setHeaderColor] = useState30("#6366f1");
9403
+ const [salesTeamEmails, setSalesTeamEmails] = useState30([]);
9404
+ const [fulfilmentTeamEmails, setFulfilmentTeamEmails] = useState30([]);
9405
+ const [crmEmails, setCrmEmails] = useState30([]);
9406
+ const [logoUrl, setLogoUrl] = useState30("");
9407
+ const [companyName, setCompanyName] = useState30("");
9408
+ const [supportEmail, setSupportEmail] = useState30("");
9409
+ const [supportPhone, setSupportPhone] = useState30("");
9410
+ const [followUsTitle, setFollowUsTitle] = useState30("Follow Us");
9411
+ const [socialLinkRows, setSocialLinkRows] = useState30([{ ...EMPTY_SOCIAL_ROW }]);
9412
+ const [footerDisclaimer, setFooterDisclaimer] = useState30("");
9413
+ const [chatMode, setChatMode] = useState30("whatsapp");
9414
+ const [whatsappPhone, setWhatsappPhone] = useState30("");
9415
+ const [externalChatSnippet, setExternalChatSnippet] = useState30("");
9416
+ const [erpPipelineName, setErpPipelineName] = useState30("");
9417
+ const [erpPipelineStageName, setErpPipelineStageName] = useState30("");
9418
+ const [erpFormsCatalog, setErpFormsCatalog] = useState30([]);
9419
+ const [erpOpportunityFormIds, setErpOpportunityFormIds] = useState30([]);
9420
+ const [erpOpportunityIdsKeyPresent, setErpOpportunityIdsKeyPresent] = useState30(false);
9421
+ const [smsProviderChoice, setSmsProviderChoice] = useState30("auto");
9422
+ const [msg91ApiMode, setMsg91ApiMode] = useState30("auto");
9423
+ const [smsTplItems, setSmsTplItems] = useState30([]);
9424
+ const [loading, setLoading] = useState30(true);
9425
+ const [saving, setSaving] = useState30(false);
8382
9426
  useEffect27(() => {
8383
9427
  setLoading(true);
8384
9428
  fetch(`/api/settings/${settingsGroup}`).then((r) => r.ok ? r.json() : {}).then(async (data) => {
@@ -8520,10 +9564,10 @@ function PluginSettingsPanel({
8520
9564
  });
8521
9565
  if (!res2.ok) throw new Error();
8522
9566
  }
8523
- toast4.success("Settings saved");
9567
+ toast5.success("Settings saved");
8524
9568
  onSaved?.();
8525
9569
  } catch {
8526
- toast4.error("Failed to save");
9570
+ toast5.error("Failed to save");
8527
9571
  } finally {
8528
9572
  setSaving(false);
8529
9573
  }
@@ -8968,7 +10012,7 @@ function PluginSettingsPanel({
8968
10012
  ),
8969
10013
  /* @__PURE__ */ jsx56("p", { className: "text-xs text-gray-500 dark:text-gray-400", children: "Only paste code from sources you trust." })
8970
10014
  ] }),
8971
- chatMode === "llm" && /* @__PURE__ */ jsxs46(Fragment12, { children: [
10015
+ chatMode === "llm" && /* @__PURE__ */ jsxs46(Fragment14, { children: [
8972
10016
  /* @__PURE__ */ jsxs46("div", { className: "space-y-1", children: [
8973
10017
  /* @__PURE__ */ jsx56(Label3, { htmlFor: `${settingsGroup}-botName`, className: "text-sm", children: "Name" }),
8974
10018
  /* @__PURE__ */ jsx56(
@@ -9139,9 +10183,9 @@ function PluginListItem({
9139
10183
  );
9140
10184
  }
9141
10185
  function PluginsPage() {
9142
- const { pluginDescriptors = [] } = useContext5(AdminConfigContext);
9143
- const [selectedName, setSelectedName] = useState29(null);
9144
- const [enabledMap, setEnabledMap] = useState29({});
10186
+ const { pluginDescriptors = [] } = useContext6(AdminConfigContext);
10187
+ const [selectedName, setSelectedName] = useState30(null);
10188
+ const [enabledMap, setEnabledMap] = useState30({});
9145
10189
  useEffect27(() => {
9146
10190
  pluginDescriptors.forEach((p) => {
9147
10191
  if (!p.settingsGroup) return;
@@ -9182,7 +10226,7 @@ function PluginsPage() {
9182
10226
  /* @__PURE__ */ jsx56("div", { className: "min-w-0 flex-1", children: !selectedName ? /* @__PURE__ */ jsxs46("div", { className: "flex flex-col items-center justify-center py-12 text-center", children: [
9183
10227
  /* @__PURE__ */ jsx56(Puzzle2, { className: "h-10 w-10 text-gray-300 dark:text-gray-600" }),
9184
10228
  /* @__PURE__ */ jsx56("p", { className: "mt-3 text-sm text-gray-500 dark:text-gray-400", children: "Select a plugin to view or edit its configuration." })
9185
- ] }) : /* @__PURE__ */ jsx56("div", { className: "rounded-lg border border-gray-200 bg-gray-50/50 p-5 dark:border-gray-700 dark:bg-gray-800/50", children: selectedDescriptor?.settingsGroup ? /* @__PURE__ */ jsxs46(Fragment12, { children: [
10229
+ ] }) : /* @__PURE__ */ jsx56("div", { className: "rounded-lg border border-gray-200 bg-gray-50/50 p-5 dark:border-gray-700 dark:bg-gray-800/50", children: selectedDescriptor?.settingsGroup ? /* @__PURE__ */ jsxs46(Fragment14, { children: [
9186
10230
  /* @__PURE__ */ jsxs46("h2", { className: "text-sm font-medium text-gray-700 dark:text-gray-300 mb-4", children: [
9187
10231
  selectedDescriptor.label || selectedDescriptor.name,
9188
10232
  " \u2014 Configuration"
@@ -9203,9 +10247,9 @@ function PluginsPage() {
9203
10247
  }
9204
10248
 
9205
10249
  // src/admin/pages/BrandEditPage.tsx
9206
- import { useState as useState30, useEffect as useEffect28 } from "react";
9207
- import { useRouter as useRouter10 } from "next/navigation";
9208
- import { AlertCircle as AlertCircle4 } from "lucide-react";
10250
+ import { useState as useState31, useEffect as useEffect28 } from "react";
10251
+ import { useRouter as useRouter12 } from "next/navigation";
10252
+ import { AlertCircle as AlertCircle4, Save as Save6, Power } from "lucide-react";
9209
10253
 
9210
10254
  // src/components/Admin/SeoSection.tsx
9211
10255
  import { jsx as jsx57, jsxs as jsxs47 } from "react/jsx-runtime";
@@ -9296,22 +10340,22 @@ async function fetchSeo(seoId) {
9296
10340
  }
9297
10341
 
9298
10342
  // src/admin/pages/BrandEditPage.tsx
9299
- import { Fragment as Fragment13, jsx as jsx58, jsxs as jsxs48 } from "react/jsx-runtime";
10343
+ import { Fragment as Fragment15, jsx as jsx58, jsxs as jsxs48 } from "react/jsx-runtime";
9300
10344
  var isCreate = (id) => id === "create";
9301
10345
  function BrandEditPage({ brandId }) {
9302
- const router = useRouter10();
10346
+ const router = useRouter12();
9303
10347
  const create = isCreate(brandId);
9304
- const [loading, setLoading] = useState30(!create);
9305
- const [saving, setSaving] = useState30(false);
9306
- const [errors, setErrors] = useState30([]);
9307
- const [name, setName] = useState30("");
9308
- const [slug, setSlug] = useState30("");
9309
- const [description, setDescription] = useState30("");
9310
- const [logo, setLogo] = useState30("");
9311
- const [active, setActive] = useState30(true);
9312
- const [sortOrder, setSortOrder] = useState30(0);
9313
- const [seoId, setSeoId] = useState30(null);
9314
- const [seo, setSeo] = useState30({ seoTitle: "", seoDescription: "", seoKeywords: "", seoOgTitle: "", seoOgDescription: "", seoOgImage: "" });
10348
+ const [loading, setLoading] = useState31(!create);
10349
+ const [saving, setSaving] = useState31(false);
10350
+ const [errors, setErrors] = useState31([]);
10351
+ const [name, setName] = useState31("");
10352
+ const [slug, setSlug] = useState31("");
10353
+ const [description, setDescription] = useState31("");
10354
+ const [logo, setLogo] = useState31("");
10355
+ const [active, setActive] = useState31(true);
10356
+ const [sortOrder, setSortOrder] = useState31(0);
10357
+ const [seoId, setSeoId] = useState31(null);
10358
+ const [seo, setSeo] = useState31({ seoTitle: "", seoDescription: "", seoKeywords: "", seoOgTitle: "", seoOgDescription: "", seoOgImage: "" });
9315
10359
  useEffect28(() => {
9316
10360
  if (create) return;
9317
10361
  let cancelled = false;
@@ -9392,8 +10436,8 @@ function BrandEditPage({ brandId }) {
9392
10436
  subtitle: create ? "Create a new brand" : "Update brand details",
9393
10437
  closeHref: "/admin/brands",
9394
10438
  menuItems: [
9395
- { label: saving ? "Saving..." : "Save", onClick: handleSave },
9396
- { label: active ? "Deactivate" : "Activate", onClick: () => setActive(!active) }
10439
+ { label: saving ? "Saving..." : "Save", icon: Save6, onClick: handleSave },
10440
+ { label: active ? "Deactivate" : "Activate", icon: Power, onClick: () => setActive(!active) }
9397
10441
  ]
9398
10442
  }
9399
10443
  ),
@@ -9407,7 +10451,7 @@ function BrandEditPage({ brandId }) {
9407
10451
  /* @__PURE__ */ jsx58(
9408
10452
  DetailPageLayout,
9409
10453
  {
9410
- main: /* @__PURE__ */ jsxs48(Fragment13, { children: [
10454
+ main: /* @__PURE__ */ jsxs48(Fragment15, { children: [
9411
10455
  /* @__PURE__ */ jsxs48("section", { children: [
9412
10456
  /* @__PURE__ */ jsx58("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Basic info" }),
9413
10457
  /* @__PURE__ */ jsxs48("div", { className: "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50 space-y-4", children: [
@@ -9480,7 +10524,7 @@ function BrandEditPage({ brandId }) {
9480
10524
  /* @__PURE__ */ jsx58("div", { className: "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50", children: /* @__PURE__ */ jsx58(SeoSection, { values: seo, onChange: (field, value) => setSeo((s) => ({ ...s, [field]: value })) }) })
9481
10525
  ] })
9482
10526
  ] }),
9483
- sidebar: /* @__PURE__ */ jsx58(Fragment13, { children: /* @__PURE__ */ jsxs48("section", { children: [
10527
+ sidebar: /* @__PURE__ */ jsx58(Fragment15, { children: /* @__PURE__ */ jsxs48("section", { children: [
9484
10528
  /* @__PURE__ */ jsx58("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Status" }),
9485
10529
  /* @__PURE__ */ jsx58("div", { className: "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50", children: /* @__PURE__ */ jsxs48("label", { className: "flex items-center gap-2 cursor-pointer", children: [
9486
10530
  /* @__PURE__ */ jsx58(
@@ -9501,12 +10545,12 @@ function BrandEditPage({ brandId }) {
9501
10545
  }
9502
10546
 
9503
10547
  // src/admin/pages/ProductEditPage.tsx
9504
- import { useState as useState32, useEffect as useEffect30 } from "react";
9505
- import { useRouter as useRouter11 } from "next/navigation";
9506
- import { AlertCircle as AlertCircle5, Plus as Plus9, Trash2 as Trash25, Star } from "lucide-react";
10548
+ import { useState as useState33, useEffect as useEffect30 } from "react";
10549
+ import { useRouter as useRouter13 } from "next/navigation";
10550
+ import { AlertCircle as AlertCircle5, Plus as Plus9, Trash2 as Trash25, Star, Save as Save7 } from "lucide-react";
9507
10551
 
9508
10552
  // src/components/Admin/AttributeFacetNameInput.tsx
9509
- import { useState as useState31, useEffect as useEffect29 } from "react";
10553
+ import { useState as useState32, useEffect as useEffect29, useRef as useRef11 } from "react";
9510
10554
  import { jsx as jsx59, jsxs as jsxs49 } from "react/jsx-runtime";
9511
10555
  function slugFromName(name) {
9512
10556
  const s = name.toLowerCase().trim().replace(/[^a-z0-9]+/g, "-").replace(/^-|-$/g, "");
@@ -9517,12 +10561,15 @@ function AttributeFacetNameInput({
9517
10561
  onChange,
9518
10562
  inputClassName
9519
10563
  }) {
9520
- const [draft, setDraft] = useState31(value);
9521
- const [open, setOpen] = useState31(false);
9522
- const [list, setList] = useState31([]);
10564
+ const [draft, setDraft] = useState32(value);
10565
+ const [open, setOpen] = useState32(false);
10566
+ const [list, setList] = useState32([]);
10567
+ const isFocusedRef = useRef11(false);
9523
10568
  useEffect29(() => {
9524
- setDraft(value);
9525
- }, [value]);
10569
+ if (!isFocusedRef.current && value !== draft) {
10570
+ setDraft(value);
10571
+ }
10572
+ }, [value, draft]);
9526
10573
  useEffect29(() => {
9527
10574
  const q = draft.trim();
9528
10575
  if (!q) {
@@ -9585,8 +10632,12 @@ function AttributeFacetNameInput({
9585
10632
  setDraft(e.target.value);
9586
10633
  setOpen(true);
9587
10634
  },
9588
- onFocus: () => setOpen(true),
10635
+ onFocus: () => {
10636
+ setOpen(true);
10637
+ isFocusedRef.current = true;
10638
+ },
9589
10639
  onBlur: () => setTimeout(() => {
10640
+ isFocusedRef.current = false;
9590
10641
  setOpen(false);
9591
10642
  onChange(draft.trim());
9592
10643
  }, 200),
@@ -9640,7 +10691,7 @@ function AttributeFacetNameInput({
9640
10691
  }
9641
10692
 
9642
10693
  // src/admin/pages/ProductEditPage.tsx
9643
- import { Fragment as Fragment14, jsx as jsx60, jsxs as jsxs50 } from "react/jsx-runtime";
10694
+ import { Fragment as Fragment16, jsx as jsx60, jsxs as jsxs50 } from "react/jsx-runtime";
9644
10695
  var isCreate2 = (id) => id === "create";
9645
10696
  var sectionCls = "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4 bg-gray-50/50";
9646
10697
  var labelCls = "block text-xs font-medium text-gray-600 mb-1";
@@ -9674,37 +10725,37 @@ function pickOtherMetadata(m) {
9674
10725
  return rest;
9675
10726
  }
9676
10727
  function ProductEditPage({ productId }) {
9677
- const router = useRouter11();
10728
+ const router = useRouter13();
9678
10729
  const create = isCreate2(productId);
9679
- const [loading, setLoading] = useState32(!create);
9680
- const [saving, setSaving] = useState32(false);
9681
- const [errors, setErrors] = useState32([]);
9682
- const [collections, setCollections] = useState32([]);
9683
- const [brands, setBrands] = useState32([]);
9684
- const [categories, setCategories] = useState32([]);
9685
- const [name, setName] = useState32("");
9686
- const [productSlug, setProductSlug] = useState32("");
9687
- const [sku, setSku] = useState32("");
9688
- const [hsn, setHsn] = useState32("");
9689
- const [uom, setUom] = useState32("");
9690
- const [productType, setProductType] = useState32("product");
9691
- const [collectionId, setCollectionId] = useState32(null);
9692
- const [brandId, setBrandId] = useState32(null);
9693
- const [categoryId, setCategoryId] = useState32(null);
9694
- const [price, setPrice] = useState32("");
9695
- const [compareAtPrice, setCompareAtPrice] = useState32("");
9696
- const [quantity, setQuantity] = useState32(1);
9697
- const [status, setStatus] = useState32("draft");
9698
- const [featured, setFeatured] = useState32(false);
9699
- const [description, setDescription] = useState32("");
9700
- const [images, setImages] = useState32([{ url: "", alt: "", isDefault: true }]);
9701
- const [specifications, setSpecifications] = useState32([{ key: "", value: "" }]);
9702
- const [otherMetadata, setOtherMetadata] = useState32({});
9703
- const [facetRows, setFacetRows] = useState32([{ name: "", value: "" }]);
9704
- const [taxMasterList, setTaxMasterList] = useState32([]);
9705
- const [taxRows, setTaxRows] = useState32([{ taxId: "", rate: "" }]);
9706
- const [seoId, setSeoId] = useState32(null);
9707
- const [seo, setSeo] = useState32({
10730
+ const [loading, setLoading] = useState33(!create);
10731
+ const [saving, setSaving] = useState33(false);
10732
+ const [errors, setErrors] = useState33([]);
10733
+ const [collections, setCollections] = useState33([]);
10734
+ const [brands, setBrands] = useState33([]);
10735
+ const [categories, setCategories] = useState33([]);
10736
+ const [name, setName] = useState33("");
10737
+ const [productSlug, setProductSlug] = useState33("");
10738
+ const [sku, setSku] = useState33("");
10739
+ const [hsn, setHsn] = useState33("");
10740
+ const [uom, setUom] = useState33("");
10741
+ const [productType, setProductType] = useState33("product");
10742
+ const [collectionId, setCollectionId] = useState33(null);
10743
+ const [brandId, setBrandId] = useState33(null);
10744
+ const [categoryId, setCategoryId] = useState33(null);
10745
+ const [price, setPrice] = useState33("");
10746
+ const [compareAtPrice, setCompareAtPrice] = useState33("");
10747
+ const [quantity, setQuantity] = useState33(1);
10748
+ const [status, setStatus] = useState33("draft");
10749
+ const [featured, setFeatured] = useState33(false);
10750
+ const [description, setDescription] = useState33("");
10751
+ const [images, setImages] = useState33([{ url: "", alt: "", isDefault: true }]);
10752
+ const [specifications, setSpecifications] = useState33([{ key: "", value: "" }]);
10753
+ const [otherMetadata, setOtherMetadata] = useState33({});
10754
+ const [facetRows, setFacetRows] = useState33([{ name: "", value: "" }]);
10755
+ const [taxMasterList, setTaxMasterList] = useState33([]);
10756
+ const [taxRows, setTaxRows] = useState33([{ taxId: "", rate: "" }]);
10757
+ const [seoId, setSeoId] = useState33(null);
10758
+ const [seo, setSeo] = useState33({
9708
10759
  seoTitle: "",
9709
10760
  seoDescription: "",
9710
10761
  seoKeywords: "",
@@ -10042,8 +11093,8 @@ function ProductEditPage({ productId }) {
10042
11093
  subtitle: create ? "Create a new product" : "Update product details",
10043
11094
  closeHref: "/admin/products",
10044
11095
  menuItems: [
10045
- { label: saving ? "Saving..." : "Save", onClick: handleSave },
10046
- { label: featured ? "Unfeature" : "Feature", onClick: () => setFeatured(!featured) }
11096
+ { label: saving ? "Saving..." : "Save", icon: Save7, onClick: handleSave },
11097
+ { label: featured ? "Unfeature" : "Feature", icon: Star, onClick: () => setFeatured(!featured) }
10047
11098
  ]
10048
11099
  }
10049
11100
  ),
@@ -10057,7 +11108,7 @@ function ProductEditPage({ productId }) {
10057
11108
  /* @__PURE__ */ jsx60(
10058
11109
  DetailPageLayout,
10059
11110
  {
10060
- main: /* @__PURE__ */ jsxs50(Fragment14, { children: [
11111
+ main: /* @__PURE__ */ jsxs50(Fragment16, { children: [
10061
11112
  /* @__PURE__ */ jsxs50("section", { children: [
10062
11113
  /* @__PURE__ */ jsx60("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Product details" }),
10063
11114
  /* @__PURE__ */ jsxs50("div", { className: `${sectionCls} space-y-4`, children: [
@@ -10361,10 +11412,10 @@ function ProductEditPage({ productId }) {
10361
11412
  }
10362
11413
 
10363
11414
  // src/admin/pages/CollectionEditPage.tsx
10364
- import { useState as useState33, useEffect as useEffect31 } from "react";
10365
- import { useRouter as useRouter12 } from "next/navigation";
10366
- import { AlertCircle as AlertCircle6, Plus as Plus10, Trash2 as Trash26, ChevronDown as ChevronDown6, ChevronUp as ChevronUp2 } from "lucide-react";
10367
- import { Fragment as Fragment15, jsx as jsx61, jsxs as jsxs51 } from "react/jsx-runtime";
11415
+ import { useState as useState34, useEffect as useEffect31 } from "react";
11416
+ import { useRouter as useRouter14 } from "next/navigation";
11417
+ import { AlertCircle as AlertCircle6, Plus as Plus10, Trash2 as Trash26, ChevronDown as ChevronDown6, ChevronUp as ChevronUp2, Save as Save8, Power as Power2 } from "lucide-react";
11418
+ import { Fragment as Fragment17, jsx as jsx61, jsxs as jsxs51 } from "react/jsx-runtime";
10368
11419
  var isCreate3 = (id) => id === "create";
10369
11420
  var emptySlide = () => ({ url: "", type: "image", caption: "" });
10370
11421
  var emptyVariant = () => ({ name: "", price: "", extraSpecs: [] });
@@ -10372,29 +11423,29 @@ var sectionCls2 = "min-w-0 overflow-hidden border border-gray-200 rounded-lg p-4
10372
11423
  var labelCls2 = "block text-xs font-medium text-gray-600 mb-1";
10373
11424
  var inputCls2 = "w-full rounded-md border border-gray-300 px-2 py-1.5 text-sm";
10374
11425
  function CollectionEditPage({ collectionId }) {
10375
- const router = useRouter12();
11426
+ const router = useRouter14();
10376
11427
  const create = isCreate3(collectionId);
10377
- const [loading, setLoading] = useState33(!create);
10378
- const [saving, setSaving] = useState33(false);
10379
- const [errors, setErrors] = useState33([]);
10380
- const [categories, setCategories] = useState33([]);
10381
- const [brands, setBrands] = useState33([]);
10382
- const [name, setName] = useState33("");
10383
- const [slug, setSlug] = useState33("");
10384
- const [hsn, setHsn] = useState33("");
10385
- const [categoryId, setCategoryId] = useState33(null);
10386
- const [brandId, setBrandId] = useState33(null);
10387
- const [description, setDescription] = useState33("");
10388
- const [image, setImage] = useState33("");
10389
- const [active, setActive] = useState33(true);
10390
- const [sortOrder, setSortOrder] = useState33(0);
10391
- const [advancedOpen, setAdvancedOpen] = useState33(false);
10392
- const [heroSlides, setHeroSlides] = useState33([emptySlide()]);
10393
- const [variants, setVariants] = useState33([emptyVariant()]);
10394
- const [experienceDescription, setExperienceDescription] = useState33("");
10395
- const [brochureUrl, setBrochureUrl] = useState33("");
10396
- const [seoId, setSeoId] = useState33(null);
10397
- const [seo, setSeo] = useState33({
11428
+ const [loading, setLoading] = useState34(!create);
11429
+ const [saving, setSaving] = useState34(false);
11430
+ const [errors, setErrors] = useState34([]);
11431
+ const [categories, setCategories] = useState34([]);
11432
+ const [brands, setBrands] = useState34([]);
11433
+ const [name, setName] = useState34("");
11434
+ const [slug, setSlug] = useState34("");
11435
+ const [hsn, setHsn] = useState34("");
11436
+ const [categoryId, setCategoryId] = useState34(null);
11437
+ const [brandId, setBrandId] = useState34(null);
11438
+ const [description, setDescription] = useState34("");
11439
+ const [image, setImage] = useState34("");
11440
+ const [active, setActive] = useState34(true);
11441
+ const [sortOrder, setSortOrder] = useState34(0);
11442
+ const [advancedOpen, setAdvancedOpen] = useState34(false);
11443
+ const [heroSlides, setHeroSlides] = useState34([emptySlide()]);
11444
+ const [variants, setVariants] = useState34([emptyVariant()]);
11445
+ const [experienceDescription, setExperienceDescription] = useState34("");
11446
+ const [brochureUrl, setBrochureUrl] = useState34("");
11447
+ const [seoId, setSeoId] = useState34(null);
11448
+ const [seo, setSeo] = useState34({
10398
11449
  seoTitle: "",
10399
11450
  seoDescription: "",
10400
11451
  seoKeywords: "",
@@ -10575,8 +11626,8 @@ function CollectionEditPage({ collectionId }) {
10575
11626
  subtitle: create ? "Create a new collection" : "Update collection and page content",
10576
11627
  closeHref: "/admin/collections",
10577
11628
  menuItems: [
10578
- { label: saving ? "Saving..." : "Save", onClick: handleSave },
10579
- { label: active ? "Deactivate" : "Activate", onClick: () => setActive(!active) }
11629
+ { label: saving ? "Saving..." : "Save", icon: Save8, onClick: handleSave },
11630
+ { label: active ? "Deactivate" : "Activate", icon: Power2, onClick: () => setActive(!active) }
10580
11631
  ]
10581
11632
  }
10582
11633
  ),
@@ -10590,7 +11641,7 @@ function CollectionEditPage({ collectionId }) {
10590
11641
  /* @__PURE__ */ jsx61(
10591
11642
  DetailPageLayout,
10592
11643
  {
10593
- main: /* @__PURE__ */ jsxs51(Fragment15, { children: [
11644
+ main: /* @__PURE__ */ jsxs51(Fragment17, { children: [
10594
11645
  /* @__PURE__ */ jsxs51("section", { children: [
10595
11646
  /* @__PURE__ */ jsx61("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Basic info" }),
10596
11647
  /* @__PURE__ */ jsxs51("div", { className: `${sectionCls2} space-y-4`, children: [
@@ -10700,7 +11751,7 @@ function CollectionEditPage({ collectionId }) {
10700
11751
  ] })
10701
11752
  ] })
10702
11753
  ] }),
10703
- sidebar: /* @__PURE__ */ jsxs51(Fragment15, { children: [
11754
+ sidebar: /* @__PURE__ */ jsxs51(Fragment17, { children: [
10704
11755
  /* @__PURE__ */ jsxs51("section", { children: [
10705
11756
  /* @__PURE__ */ jsx61("h2", { className: "text-xs font-semibold text-gray-400 uppercase tracking-wider mb-2", children: "Status" }),
10706
11757
  /* @__PURE__ */ jsx61("div", { className: sectionCls2, children: /* @__PURE__ */ jsxs51("label", { className: "flex items-center gap-2 cursor-pointer", children: [
@@ -10719,9 +11770,9 @@ function CollectionEditPage({ collectionId }) {
10719
11770
  }
10720
11771
 
10721
11772
  // src/admin/pages/RolesPage.tsx
10722
- import { useCallback as useCallback7, useEffect as useEffect32, useState as useState34 } from "react";
11773
+ import { useCallback as useCallback7, useEffect as useEffect32, useState as useState35 } from "react";
10723
11774
  import { useSession as useSession5 } from "next-auth/react";
10724
- import { Shield as Shield2, Save as Save6, Trash2 as Trash27 } from "lucide-react";
11775
+ import { Shield as Shield2, Save as Save9, Trash2 as Trash27 } from "lucide-react";
10725
11776
 
10726
11777
  // src/auth/permission-entities.ts
10727
11778
  var ADMIN_GROUP_NAME = "Administrator";
@@ -10754,14 +11805,15 @@ function RolesPage() {
10754
11805
  const { data: session, status } = useSession5();
10755
11806
  const u = session?.user;
10756
11807
  const canManage = !!u?.isRBACAdmin;
10757
- const [entities, setEntities] = useState34([]);
10758
- const [groups, setGroups] = useState34([]);
10759
- const [selectedId, setSelectedId] = useState34(null);
10760
- const [matrix, setMatrix] = useState34({});
10761
- const [loading, setLoading] = useState34(true);
10762
- const [saving, setSaving] = useState34(false);
10763
- const [newName, setNewName] = useState34("");
10764
- const [error, setError] = useState34(null);
11808
+ const [entities, setEntities] = useState35([]);
11809
+ const [groups, setGroups] = useState35([]);
11810
+ const [selectedId, setSelectedId] = useState35(null);
11811
+ const [matrix, setMatrix] = useState35({});
11812
+ const [loading, setLoading] = useState35(true);
11813
+ const [saving, setSaving] = useState35(false);
11814
+ const [newName, setNewName] = useState35("");
11815
+ const [deleteRoleOpen, setDeleteRoleOpen] = useState35(false);
11816
+ const [error, setError] = useState35(null);
10765
11817
  const load = useCallback7(async () => {
10766
11818
  setLoading(true);
10767
11819
  setError(null);
@@ -10816,6 +11868,45 @@ function RolesPage() {
10816
11868
  [entity]: { ...prev[entity], [key]: !prev[entity][key] }
10817
11869
  }));
10818
11870
  };
11871
+ const PERM_KEYS = [
11872
+ "canCreate",
11873
+ "canRead",
11874
+ "canUpdate",
11875
+ "canDelete"
11876
+ ];
11877
+ const isColumnAllChecked = (key) => entities.length > 0 && entities.every((entity) => matrix[entity]?.[key]);
11878
+ const toggleColumn = (key) => {
11879
+ const nextValue = !isColumnAllChecked(key);
11880
+ setMatrix((prev) => {
11881
+ const next = { ...prev };
11882
+ for (const entity of entities) {
11883
+ if (!next[entity]) continue;
11884
+ next[entity] = { ...next[entity], [key]: nextValue };
11885
+ }
11886
+ return next;
11887
+ });
11888
+ };
11889
+ const isAllChecked = entities.length > 0 && entities.every((entity) => {
11890
+ const row = matrix[entity];
11891
+ return row ? PERM_KEYS.every((k) => row[k]) : false;
11892
+ });
11893
+ const toggleAll = () => {
11894
+ const nextValue = !isAllChecked;
11895
+ setMatrix((prev) => {
11896
+ const next = { ...prev };
11897
+ for (const entity of entities) {
11898
+ if (!next[entity]) continue;
11899
+ next[entity] = {
11900
+ ...next[entity],
11901
+ canCreate: nextValue,
11902
+ canRead: nextValue,
11903
+ canUpdate: nextValue,
11904
+ canDelete: nextValue
11905
+ };
11906
+ }
11907
+ return next;
11908
+ });
11909
+ };
10819
11910
  const saveMatrix = async () => {
10820
11911
  if (!selectedId) return;
10821
11912
  setSaving(true);
@@ -10864,7 +11955,6 @@ function RolesPage() {
10864
11955
  };
10865
11956
  const deleteGroup = async () => {
10866
11957
  if (!selectedId || !selected || isSuperAdminGroupName(selected.name)) return;
10867
- if (!confirm(`Delete group "${selected.name}"?`)) return;
10868
11958
  try {
10869
11959
  const res = await fetch(`/api/admin/roles/${selectedId}`, { method: "DELETE" });
10870
11960
  if (!res.ok) {
@@ -10873,6 +11963,7 @@ function RolesPage() {
10873
11963
  return;
10874
11964
  }
10875
11965
  setSelectedId(null);
11966
+ setDeleteRoleOpen(false);
10876
11967
  await load();
10877
11968
  } catch {
10878
11969
  setError("Delete failed");
@@ -10923,21 +12014,36 @@ function RolesPage() {
10923
12014
  " \u2014 Permissions"
10924
12015
  ] }),
10925
12016
  /* @__PURE__ */ jsxs52(Button, { size: "sm", onClick: saveMatrix, disabled: saving, className: "gap-1", children: [
10926
- /* @__PURE__ */ jsx62(Save6, { className: "h-3.5 w-3.5" }),
12017
+ /* @__PURE__ */ jsx62(Save9, { className: "h-3.5 w-3.5" }),
10927
12018
  saving ? "Saving\u2026" : "Save"
10928
12019
  ] }),
10929
- selected && !isSuperAdminGroupName(selected.name) && /* @__PURE__ */ jsxs52(Button, { size: "sm", variant: "outline", className: "gap-1 text-red-600", onClick: deleteGroup, children: [
12020
+ selected && !isSuperAdminGroupName(selected.name) && /* @__PURE__ */ jsxs52(Button, { size: "sm", variant: "outline", className: "gap-1 text-red-600", onClick: () => setDeleteRoleOpen(true), children: [
10930
12021
  /* @__PURE__ */ jsx62(Trash27, { className: "h-3.5 w-3.5" }),
10931
12022
  "Delete role"
10932
12023
  ] })
10933
12024
  ] }),
10934
12025
  entities.length > 0 && /* @__PURE__ */ jsx62("div", { className: "overflow-x-auto rounded-md border border-gray-200 dark:border-gray-600", children: /* @__PURE__ */ jsxs52("table", { className: "w-full text-sm", children: [
10935
12026
  /* @__PURE__ */ jsx62("thead", { children: /* @__PURE__ */ jsxs52("tr", { className: "border-b bg-gray-50 dark:bg-gray-900/50", children: [
10936
- /* @__PURE__ */ jsx62("th", { className: "p-3 text-left font-medium", children: "Resource" }),
10937
- /* @__PURE__ */ jsx62("th", { className: "p-2", children: "C" }),
10938
- /* @__PURE__ */ jsx62("th", { className: "p-2", children: "R" }),
10939
- /* @__PURE__ */ jsx62("th", { className: "p-2", children: "U" }),
10940
- /* @__PURE__ */ jsx62("th", { className: "p-2", children: "D" })
12027
+ /* @__PURE__ */ jsx62("th", { className: "p-3 text-left font-medium", children: /* @__PURE__ */ jsxs52("div", { className: "flex items-center gap-2", children: [
12028
+ /* @__PURE__ */ jsx62("input", { type: "checkbox", checked: isAllChecked, onChange: toggleAll }),
12029
+ /* @__PURE__ */ jsx62("span", { children: "Resource" })
12030
+ ] }) }),
12031
+ /* @__PURE__ */ jsx62("th", { className: "p-2", children: /* @__PURE__ */ jsxs52("div", { className: "flex items-center justify-center gap-1", children: [
12032
+ /* @__PURE__ */ jsx62("span", { children: "C" }),
12033
+ /* @__PURE__ */ jsx62("input", { type: "checkbox", checked: isColumnAllChecked("canCreate"), onChange: () => toggleColumn("canCreate") })
12034
+ ] }) }),
12035
+ /* @__PURE__ */ jsx62("th", { className: "p-2", children: /* @__PURE__ */ jsxs52("div", { className: "flex items-center justify-center gap-1", children: [
12036
+ /* @__PURE__ */ jsx62("span", { children: "R" }),
12037
+ /* @__PURE__ */ jsx62("input", { type: "checkbox", checked: isColumnAllChecked("canRead"), onChange: () => toggleColumn("canRead") })
12038
+ ] }) }),
12039
+ /* @__PURE__ */ jsx62("th", { className: "p-2", children: /* @__PURE__ */ jsxs52("div", { className: "flex items-center justify-center gap-1", children: [
12040
+ /* @__PURE__ */ jsx62("span", { children: "U" }),
12041
+ /* @__PURE__ */ jsx62("input", { type: "checkbox", checked: isColumnAllChecked("canUpdate"), onChange: () => toggleColumn("canUpdate") })
12042
+ ] }) }),
12043
+ /* @__PURE__ */ jsx62("th", { className: "p-2", children: /* @__PURE__ */ jsxs52("div", { className: "flex items-center justify-center gap-1", children: [
12044
+ /* @__PURE__ */ jsx62("span", { children: "D" }),
12045
+ /* @__PURE__ */ jsx62("input", { type: "checkbox", checked: isColumnAllChecked("canDelete"), onChange: () => toggleColumn("canDelete") })
12046
+ ] }) })
10941
12047
  ] }) }),
10942
12048
  /* @__PURE__ */ jsx62("tbody", { children: entities.map((entity) => {
10943
12049
  const row = matrix[entity];
@@ -10961,7 +12067,15 @@ function RolesPage() {
10961
12067
  /* @__PURE__ */ jsx62(Input, { placeholder: "New role name", value: newName, onChange: (e) => setNewName(e.target.value), onKeyDown: (e) => e.key === "Enter" && createGroup() }),
10962
12068
  /* @__PURE__ */ jsx62(Button, { type: "button", onClick: createGroup, children: "Add role" })
10963
12069
  ] })
10964
- ] })
12070
+ ] }),
12071
+ /* @__PURE__ */ jsx62(Dialog, { open: deleteRoleOpen, onOpenChange: setDeleteRoleOpen, children: /* @__PURE__ */ jsxs52(DialogContent, { children: [
12072
+ /* @__PURE__ */ jsx62(DialogHeader, { children: /* @__PURE__ */ jsx62(DialogTitle, { children: "Delete Role" }) }),
12073
+ /* @__PURE__ */ jsx62("p", { className: "text-sm text-gray-600", children: selected ? `Delete group "${selected.name}"?` : "Delete selected role?" }),
12074
+ /* @__PURE__ */ jsxs52(DialogFooter, { children: [
12075
+ /* @__PURE__ */ jsx62(Button, { variant: "outline", onClick: () => setDeleteRoleOpen(false), children: "Cancel" }),
12076
+ /* @__PURE__ */ jsx62(Button, { variant: "destructive", onClick: deleteGroup, children: "Delete" })
12077
+ ] })
12078
+ ] }) })
10965
12079
  ] });
10966
12080
  }
10967
12081
 
@@ -11239,8 +12353,8 @@ var CRUD_CONFIGS = {
11239
12353
  }
11240
12354
  };
11241
12355
  function BlogEditorWrapper({ blogId }) {
11242
- const [blog, setBlog] = useState35(null);
11243
- const [loading, setLoading] = useState35(!!blogId);
12356
+ const [blog, setBlog] = useState36(null);
12357
+ const [loading, setLoading] = useState36(!!blogId);
11244
12358
  useEffect33(() => {
11245
12359
  if (!blogId) return;
11246
12360
  fetch(`/api/blogs/${blogId}`).then((res) => res.ok ? res.json() : null).then((data) => setBlog(data)).finally(() => setLoading(false));
@@ -11254,8 +12368,8 @@ function BlogEditorWrapper({ blogId }) {
11254
12368
  return /* @__PURE__ */ jsx63(BlogEditor, { existingBlog: blog });
11255
12369
  }
11256
12370
  function AdminPageResolver({ slug }) {
11257
- const router = useRouter13();
11258
- const { customCrudConfigs, storeEnabled } = useContext6(AdminConfigContext);
12371
+ const router = useRouter15();
12372
+ const { customCrudConfigs, storeEnabled } = useContext7(AdminConfigContext);
11259
12373
  const key = slug?.[0] || "dashboard";
11260
12374
  useEffect33(() => {
11261
12375
  if (key === "layout-settings") {
@@ -11317,7 +12431,7 @@ function AdminPageResolver({ slug }) {
11317
12431
  { field: "orderCount", displayName: "Orders" },
11318
12432
  { field: "totalPaid", displayName: "Total paid" }
11319
12433
  ] : crud.columns;
11320
- const extraListParams = useMemo2(
12434
+ const extraListParams = useMemo4(
11321
12435
  () => isContactsWithStore ? { includeSummary: "1" } : void 0,
11322
12436
  [isContactsWithStore]
11323
12437
  );
@@ -11340,21 +12454,21 @@ function AdminPageResolver({ slug }) {
11340
12454
  }
11341
12455
 
11342
12456
  // src/admin/pages/LayoutSettingsPage.tsx
11343
- import { useState as useState36, useEffect as useEffect34, useContext as useContext7 } from "react";
11344
- import { Save as Save7 } from "lucide-react";
12457
+ import { useState as useState37, useEffect as useEffect34, useContext as useContext8 } from "react";
12458
+ import { Save as Save10 } from "lucide-react";
11345
12459
  import { jsx as jsx64, jsxs as jsxs54 } from "react/jsx-runtime";
11346
12460
  function LayoutSettingsPage() {
11347
- const { theme } = useContext7(AdminConfigContext);
11348
- const [activeTab, setActiveTab] = useState36("navbar");
11349
- const [navbarConfig, setNavbarConfig] = useState36({
12461
+ const { theme } = useContext8(AdminConfigContext);
12462
+ const [activeTab, setActiveTab] = useState37("navbar");
12463
+ const [navbarConfig, setNavbarConfig] = useState37({
11350
12464
  logo: "",
11351
12465
  items: [],
11352
12466
  ctaLabel: "",
11353
12467
  ctaUrl: ""
11354
12468
  });
11355
- const [footerValues, setFooterValues] = useState36({});
11356
- const [saving, setSaving] = useState36(false);
11357
- const [loading, setLoading] = useState36(true);
12469
+ const [footerValues, setFooterValues] = useState37({});
12470
+ const [saving, setSaving] = useState37(false);
12471
+ const [loading, setLoading] = useState37(true);
11358
12472
  useEffect34(() => {
11359
12473
  fetch("/api/settings/theme").then((r) => r.ok ? r.json() : null).then((data) => {
11360
12474
  if (!data) return;
@@ -11413,7 +12527,7 @@ function LayoutSettingsPage() {
11413
12527
  disabled: saving,
11414
12528
  className: "bg-white text-gray-800 hover:bg-gray-100 border-0 text-xs",
11415
12529
  children: [
11416
- /* @__PURE__ */ jsx64(Save7, { className: "h-4 w-4 mr-2" }),
12530
+ /* @__PURE__ */ jsx64(Save10, { className: "h-4 w-4 mr-2" }),
11417
12531
  saving ? "Saving..." : "Save"
11418
12532
  ]
11419
12533
  }