@hanzo/ui 5.4.1 → 5.6.0
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/bin/create-registry.js +0 -0
- package/bin/npx-registry-mcp.js +0 -0
- package/bin/registry-mcp-wrapper.sh +0 -0
- package/bin/registry-mcp.js +0 -0
- package/bin/start-mcp-server.sh +0 -0
- package/bin/test-mcp.sh +0 -0
- package/dist/auth/index.js +3 -0
- package/dist/auth/index.mjs +3 -0
- package/dist/dash/crud.js +2 -0
- package/dist/dash/crud.mjs +2 -0
- package/dist/dash/form.js +2 -0
- package/dist/dash/form.mjs +2 -0
- package/dist/dash/{dash-header.js → header.js} +1 -1
- package/dist/dash/{dash-header.mjs → header.mjs} +1 -1
- package/dist/dash/index.js +2 -2
- package/dist/dash/index.mjs +2 -2
- package/dist/dash/{dash-layout.js → layout.js} +1 -1
- package/dist/dash/{dash-layout.mjs → layout.mjs} +1 -1
- package/dist/dash/sidebar.js +3 -0
- package/dist/dash/sidebar.mjs +3 -0
- package/dist/dash/{dash-data-table.js → table.js} +1 -1
- package/dist/dash/{dash-data-table.mjs → table.mjs} +1 -1
- package/dist/src/dash/{dash-crud.d.ts → crud.d.ts} +9 -9
- package/dist/src/dash/crud.d.ts.map +1 -0
- package/dist/src/dash/{dash-crud.js → crud.js} +5 -5
- package/dist/src/dash/{dash-form.d.ts → form.d.ts} +9 -9
- package/dist/src/dash/form.d.ts.map +1 -0
- package/dist/src/dash/{dash-form.js → form.js} +1 -1
- package/dist/src/dash/{dash-header.d.ts → header.d.ts} +3 -3
- package/dist/src/dash/header.d.ts.map +1 -0
- package/dist/src/dash/{dash-header.js → header.js} +1 -1
- package/dist/src/dash/index.d.ts +12 -12
- package/dist/src/dash/index.d.ts.map +1 -1
- package/dist/src/dash/index.js +6 -6
- package/dist/src/dash/{dash-layout.d.ts → layout.d.ts} +5 -5
- package/dist/src/dash/layout.d.ts.map +1 -0
- package/dist/src/dash/{dash-layout.js → layout.js} +1 -1
- package/dist/src/dash/{dash-sidebar.d.ts → sidebar.d.ts} +3 -3
- package/dist/src/dash/sidebar.d.ts.map +1 -0
- package/dist/src/dash/{dash-sidebar.js → sidebar.js} +1 -1
- package/dist/src/dash/{dash-data-table.d.ts → table.d.ts} +5 -5
- package/dist/src/dash/table.d.ts.map +1 -0
- package/dist/src/dash/{dash-data-table.js → table.js} +1 -1
- package/package.json +75 -74
- package/dist/dash/dash-crud.js +0 -2
- package/dist/dash/dash-crud.mjs +0 -2
- package/dist/dash/dash-form.js +0 -2
- package/dist/dash/dash-form.mjs +0 -2
- package/dist/dash/dash-sidebar.js +0 -3
- package/dist/dash/dash-sidebar.mjs +0 -3
- package/dist/src/dash/dash-crud.d.ts.map +0 -1
- package/dist/src/dash/dash-data-table.d.ts.map +0 -1
- package/dist/src/dash/dash-form.d.ts.map +0 -1
- package/dist/src/dash/dash-header.d.ts.map +0 -1
- package/dist/src/dash/dash-layout.d.ts.map +0 -1
- package/dist/src/dash/dash-sidebar.d.ts.map +0 -1
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import {clsx}from'clsx';import {twMerge}from'tailwind-merge';import {jsxs,jsx}from'react/jsx-runtime';var n=Object.defineProperty;var r=(e,a)=>n(e,"name",{value:a,configurable:true});function
|
|
2
|
+
import {clsx}from'clsx';import {twMerge}from'tailwind-merge';import {jsxs,jsx}from'react/jsx-runtime';var n=Object.defineProperty;var r=(e,a)=>n(e,"name",{value:a,configurable:true});function d(...e){return twMerge(clsx(e))}r(d,"cn");function N({sidebar:e,header:a,children:t,sidebarCollapsed:s=false,onSidebarCollapse:i,className:c}){return jsxs("div",{className:d("flex h-screen overflow-hidden","bg-[var(--dash-bg)] text-[var(--dash-text)]",c),children:[jsx("aside",{className:d("flex-shrink-0 overflow-y-auto overflow-x-hidden transition-[width] duration-200","border-r border-[var(--dash-border)] bg-[var(--dash-surface)]",s?"w-[var(--dash-sidebar-collapsed-width)]":"w-[var(--dash-sidebar-width)]"),children:e}),jsxs("div",{className:"flex flex-1 flex-col overflow-hidden",children:[a&&jsx("header",{className:"flex-shrink-0 border-b border-[var(--dash-border)] bg-[var(--dash-surface)]",children:a}),jsx("main",{className:"flex-1 overflow-y-auto p-6",children:t})]}),!s&&jsx("div",{className:"fixed inset-0 z-40 bg-black/60 lg:hidden",onClick:()=>i?.(true)})]})}r(N,"Layout");export{N as Layout};
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
'use strict';var u=require('react'),clsx=require('clsx'),tailwindMerge=require('tailwind-merge'),jsxRuntime=require('react/jsx-runtime');function _interopNamespace(e){if(e&&e.__esModule)return e;var n=Object.create(null);if(e){Object.keys(e).forEach(function(k){if(k!=='default'){var d=Object.getOwnPropertyDescriptor(e,k);Object.defineProperty(n,k,d.get?d:{enumerable:true,get:function(){return e[k]}});}})}n.default=e;return Object.freeze(n)}var u__namespace=/*#__PURE__*/_interopNamespace(u);var p=Object.defineProperty;var n=(t,r)=>p(t,"name",{value:r,configurable:true});function i(...t){return tailwindMerge.twMerge(clsx.clsx(t))}n(i,"cn");function b({size:t=28}){return jsxRuntime.jsx("svg",{width:t,height:t,viewBox:"0 0 24 24",fill:"none",xmlns:"http://www.w3.org/2000/svg",children:jsxRuntime.jsx("path",{d:"M4 4h4v6h8V4h4v16h-4v-6H8v6H4V4z",fill:"currentColor"})})}n(b,"HanzoMark");function L({logo:t,groups:r,userMenu:v,collapsed:o=false,onToggleCollapse:s,onNavigate:l,className:a}){return jsxRuntime.jsxs("nav",{className:i("flex h-full flex-col","bg-[var(--dash-surface)] text-[var(--dash-text)]",a),children:[jsxRuntime.jsxs("div",{className:i("flex h-[var(--dash-header-height)] items-center border-b border-[var(--dash-border)]",o?"justify-center px-2":"px-4"),children:[t??jsxRuntime.jsx(b,{}),!o&&s&&jsxRuntime.jsx("button",{type:"button",onClick:s,className:"ml-auto rounded p-1 text-[var(--dash-text-dim)] hover:bg-[var(--dash-surface-hover)] hover:text-[var(--dash-text)]","aria-label":"Collapse sidebar",children:jsxRuntime.jsx("svg",{width:"16",height:"16",viewBox:"0 0 16 16",fill:"none",children:jsxRuntime.jsx("path",{d:"M10 4L6 8l4 4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})}),o&&s&&jsxRuntime.jsx("button",{type:"button",onClick:s,className:"absolute -right-3 top-4 z-50 hidden rounded-full border border-[var(--dash-border)] bg-[var(--dash-surface)] p-1 text-[var(--dash-text-dim)] hover:text-[var(--dash-text)] lg:flex","aria-label":"Expand sidebar",children:jsxRuntime.jsx("svg",{width:"12",height:"12",viewBox:"0 0 16 16",fill:"none",children:jsxRuntime.jsx("path",{d:"M6 4l4 4-4 4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})})]}),jsxRuntime.jsx("div",{className:"flex-1 overflow-y-auto py-2",children:r.map((h,c)=>jsxRuntime.jsx(m,{group:h,collapsed:o,onNavigate:l},c))}),v&&jsxRuntime.jsx("div",{className:"border-t border-[var(--dash-border)] p-2",children:v})]})}n(L,"Sidebar");function m({group:t,collapsed:r,onNavigate:v}){let[o,s]=u__namespace.useState(t.defaultOpen!==false),l=t.collapsible!==false&&!!t.title;return jsxRuntime.jsxs("div",{className:"mb-1",children:[t.title&&!r&&jsxRuntime.jsxs("button",{type:"button",onClick:()=>l&&s(a=>!a),className:i("flex w-full items-center px-4 py-1.5 text-[11px] font-semibold uppercase tracking-wider text-[var(--dash-text-dim)]",l&&"cursor-pointer hover:text-[var(--dash-text-muted)]"),children:[jsxRuntime.jsx("span",{className:"flex-1 text-left",children:t.title}),l&&jsxRuntime.jsx("svg",{width:"12",height:"12",viewBox:"0 0 16 16",fill:"none",className:i("transition-transform",o?"rotate-0":"-rotate-90"),children:jsxRuntime.jsx("path",{d:"M4 6l4 4 4-4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})]}),(o||r)&&jsxRuntime.jsx("ul",{className:"space-y-0.5 px-2",children:t.items.map(a=>jsxRuntime.jsx("li",{children:jsxRuntime.jsxs("button",{type:"button",onClick:()=>v?.(a.href),title:r?a.label:void 0,className:i("flex w-full items-center gap-2 rounded-[var(--dash-radius-sm)] px-2 py-1.5 text-sm transition-colors",a.active?"bg-[var(--dash-primary)] text-[var(--dash-primary-text)]":"text-[var(--dash-text-muted)] hover:bg-[var(--dash-surface-hover)] hover:text-[var(--dash-text)]",r&&"justify-center px-0"),children:[a.icon&&jsxRuntime.jsx("span",{className:"flex h-5 w-5 items-center justify-center flex-shrink-0",children:a.icon}),!r&&jsxRuntime.jsx("span",{className:"flex-1 truncate text-left",children:a.label}),!r&&a.badge!==void 0&&jsxRuntime.jsx("span",{className:"ml-auto rounded-full bg-[var(--dash-primary)] px-1.5 py-0.5 text-[10px] font-medium text-[var(--dash-primary-text)]",children:a.badge})]})},a.href))})]})}n(m,"SidebarGroup");
|
|
3
|
+
exports.Sidebar=L;
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import*as u from'react';import {clsx}from'clsx';import {twMerge}from'tailwind-merge';import {jsxs,jsx}from'react/jsx-runtime';var p=Object.defineProperty;var n=(t,r)=>p(t,"name",{value:r,configurable:true});function i(...t){return twMerge(clsx(t))}n(i,"cn");function b({size:t=28}){return jsx("svg",{width:t,height:t,viewBox:"0 0 24 24",fill:"none",xmlns:"http://www.w3.org/2000/svg",children:jsx("path",{d:"M4 4h4v6h8V4h4v16h-4v-6H8v6H4V4z",fill:"currentColor"})})}n(b,"HanzoMark");function L({logo:t,groups:r,userMenu:v,collapsed:o=false,onToggleCollapse:s,onNavigate:l,className:a}){return jsxs("nav",{className:i("flex h-full flex-col","bg-[var(--dash-surface)] text-[var(--dash-text)]",a),children:[jsxs("div",{className:i("flex h-[var(--dash-header-height)] items-center border-b border-[var(--dash-border)]",o?"justify-center px-2":"px-4"),children:[t??jsx(b,{}),!o&&s&&jsx("button",{type:"button",onClick:s,className:"ml-auto rounded p-1 text-[var(--dash-text-dim)] hover:bg-[var(--dash-surface-hover)] hover:text-[var(--dash-text)]","aria-label":"Collapse sidebar",children:jsx("svg",{width:"16",height:"16",viewBox:"0 0 16 16",fill:"none",children:jsx("path",{d:"M10 4L6 8l4 4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})}),o&&s&&jsx("button",{type:"button",onClick:s,className:"absolute -right-3 top-4 z-50 hidden rounded-full border border-[var(--dash-border)] bg-[var(--dash-surface)] p-1 text-[var(--dash-text-dim)] hover:text-[var(--dash-text)] lg:flex","aria-label":"Expand sidebar",children:jsx("svg",{width:"12",height:"12",viewBox:"0 0 16 16",fill:"none",children:jsx("path",{d:"M6 4l4 4-4 4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})})]}),jsx("div",{className:"flex-1 overflow-y-auto py-2",children:r.map((h,c)=>jsx(m,{group:h,collapsed:o,onNavigate:l},c))}),v&&jsx("div",{className:"border-t border-[var(--dash-border)] p-2",children:v})]})}n(L,"Sidebar");function m({group:t,collapsed:r,onNavigate:v}){let[o,s]=u.useState(t.defaultOpen!==false),l=t.collapsible!==false&&!!t.title;return jsxs("div",{className:"mb-1",children:[t.title&&!r&&jsxs("button",{type:"button",onClick:()=>l&&s(a=>!a),className:i("flex w-full items-center px-4 py-1.5 text-[11px] font-semibold uppercase tracking-wider text-[var(--dash-text-dim)]",l&&"cursor-pointer hover:text-[var(--dash-text-muted)]"),children:[jsx("span",{className:"flex-1 text-left",children:t.title}),l&&jsx("svg",{width:"12",height:"12",viewBox:"0 0 16 16",fill:"none",className:i("transition-transform",o?"rotate-0":"-rotate-90"),children:jsx("path",{d:"M4 6l4 4 4-4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})]}),(o||r)&&jsx("ul",{className:"space-y-0.5 px-2",children:t.items.map(a=>jsx("li",{children:jsxs("button",{type:"button",onClick:()=>v?.(a.href),title:r?a.label:void 0,className:i("flex w-full items-center gap-2 rounded-[var(--dash-radius-sm)] px-2 py-1.5 text-sm transition-colors",a.active?"bg-[var(--dash-primary)] text-[var(--dash-primary-text)]":"text-[var(--dash-text-muted)] hover:bg-[var(--dash-surface-hover)] hover:text-[var(--dash-text)]",r&&"justify-center px-0"),children:[a.icon&&jsx("span",{className:"flex h-5 w-5 items-center justify-center flex-shrink-0",children:a.icon}),!r&&jsx("span",{className:"flex-1 truncate text-left",children:a.label}),!r&&a.badge!==void 0&&jsx("span",{className:"ml-auto rounded-full bg-[var(--dash-primary)] px-1.5 py-0.5 text-[10px] font-medium text-[var(--dash-primary-text)]",children:a.badge})]})},a.href))})]})}n(m,"SidebarGroup");
|
|
3
|
+
export{L as Sidebar};
|
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
'use strict';var u=require('react'),clsx=require('clsx'),tailwindMerge=require('tailwind-merge'),jsxRuntime=require('react/jsx-runtime');function _interopNamespace(e){if(e&&e.__esModule)return e;var n=Object.create(null);if(e){Object.keys(e).forEach(function(k){if(k!=='default'){var d=Object.getOwnPropertyDescriptor(e,k);Object.defineProperty(n,k,d.get?d:{enumerable:true,get:function(){return e[k]}});}})}n.default=e;return Object.freeze(n)}var u__namespace=/*#__PURE__*/_interopNamespace(u);var J=Object.defineProperty;var i=(s,h)=>J(s,"name",{value:h,configurable:true});function c(...s){return tailwindMerge.twMerge(clsx.clsx(s))}i(c,"cn");function ee({columns:s,data:h,rowKey:f,selectable:l=false,selectedKeys:
|
|
2
|
+
'use strict';var u=require('react'),clsx=require('clsx'),tailwindMerge=require('tailwind-merge'),jsxRuntime=require('react/jsx-runtime');function _interopNamespace(e){if(e&&e.__esModule)return e;var n=Object.create(null);if(e){Object.keys(e).forEach(function(k){if(k!=='default'){var d=Object.getOwnPropertyDescriptor(e,k);Object.defineProperty(n,k,d.get?d:{enumerable:true,get:function(){return e[k]}});}})}n.default=e;return Object.freeze(n)}var u__namespace=/*#__PURE__*/_interopNamespace(u);var J=Object.defineProperty;var i=(s,h)=>J(s,"name",{value:h,configurable:true});function c(...s){return tailwindMerge.twMerge(clsx.clsx(s))}i(c,"cn");function ee({columns:s,data:h,rowKey:f,selectable:l=false,selectedKeys:j,onSelectionChange:m,searchable:L=false,searchPlaceholder:z="Search...",totalRows:B,page:o=0,pageSize:g=20,onPageChange:w,onPageSizeChange:V,actions:y,loading:W=false,emptyMessage:_="No data",className:q}){let[x,A]=u__namespace.useState(""),[p,D]=u__namespace.useState(null),N=u__namespace.useMemo(()=>{if(!x)return h;let e=x.toLowerCase();return h.filter(r=>s.some(d=>(d.cell?"":String(r[d.id]??"")).toLowerCase().includes(e)))},[h,x,s]),k=u__namespace.useMemo(()=>{if(!p)return N;let{column:e,direction:r}=p;return [...N].sort((d,n)=>{let C=d[e],T=n[e];if(C==null&&T==null)return 0;if(C==null)return 1;if(T==null)return -1;let P=String(C).localeCompare(String(T),void 0,{numeric:true});return r==="asc"?P:-P})},[N,p]),E=B??k.length,S=Math.max(1,Math.ceil(E/g)),b=w?k:k.slice(o*g,(o+1)*g),v=j??new Set,M=b.length>0&&b.every(e=>v.has(f(e)));function F(){m&&m(M?new Set:new Set(b.map(f)));}i(F,"toggleAll");function G(e){if(!m)return;let r=new Set(v);r.has(e)?r.delete(e):r.add(e),m(r);}i(G,"toggleRow");function H(e){D(r=>r?.column===e?r.direction==="asc"?{column:e,direction:"desc"}:null:{column:e,direction:"asc"});}i(H,"handleSort");let R=y?[...s,{id:"__actions",header:"",width:"auto"}]:s;return jsxRuntime.jsxs("div",{className:c("rounded-[var(--dash-radius-lg)] border border-[var(--dash-border)] bg-[var(--dash-surface)]",q),children:[(L||l)&&jsxRuntime.jsxs("div",{className:"flex items-center gap-3 border-b border-[var(--dash-border)] px-4 py-3",children:[L&&jsxRuntime.jsx("input",{type:"text",placeholder:z,value:x,onChange:e=>A(e.target.value),className:c("h-8 w-64 max-w-full rounded-[var(--dash-radius-sm)] border border-[var(--dash-border)] bg-[var(--dash-bg)] px-3 text-sm text-[var(--dash-text)]","placeholder:text-[var(--dash-text-dim)]","focus:border-[var(--dash-primary)] focus:outline-none focus:ring-1 focus:ring-[var(--dash-primary)]")}),l&&v.size>0&&jsxRuntime.jsxs("span",{className:"text-xs text-[var(--dash-text-muted)]",children:[v.size," selected"]})]}),jsxRuntime.jsx("div",{className:"overflow-x-auto",children:jsxRuntime.jsxs("table",{className:"w-full text-sm",children:[jsxRuntime.jsx("thead",{children:jsxRuntime.jsxs("tr",{className:"border-b border-[var(--dash-border)]",children:[l&&jsxRuntime.jsx("th",{className:"w-10 px-4 py-2.5",children:jsxRuntime.jsx("input",{type:"checkbox",checked:M,onChange:F,className:"h-4 w-4 rounded border-[var(--dash-border)] accent-[var(--dash-primary)]"})}),R.map(e=>jsxRuntime.jsx("th",{style:e.width?{width:e.width}:void 0,className:c("px-4 py-2.5 text-[var(--dash-text-dim)] font-medium",e.align==="center"&&"text-center",e.align==="right"&&"text-right",!e.align&&"text-left",e.sortable&&"cursor-pointer select-none hover:text-[var(--dash-text-muted)]"),onClick:e.sortable?()=>H(e.id):void 0,children:jsxRuntime.jsxs("span",{className:"inline-flex items-center gap-1",children:[e.header,e.sortable&&p?.column===e.id&&jsxRuntime.jsx("span",{className:"text-[10px]",children:p.direction==="asc"?"\u2191":"\u2193"})]})},e.id))]})}),jsxRuntime.jsx("tbody",{children:W?jsxRuntime.jsx("tr",{children:jsxRuntime.jsx("td",{colSpan:R.length+(l?1:0),className:"px-4 py-8 text-center text-[var(--dash-text-dim)]",children:"Loading..."})}):b.length===0?jsxRuntime.jsx("tr",{children:jsxRuntime.jsx("td",{colSpan:R.length+(l?1:0),className:"px-4 py-8 text-center text-[var(--dash-text-dim)]",children:_})}):b.map(e=>{let r=f(e),d=v.has(r);return jsxRuntime.jsxs("tr",{className:c("border-b border-[var(--dash-border)] transition-colors",d?"bg-[var(--dash-surface-active)]":"hover:bg-[var(--dash-surface-hover)]"),children:[l&&jsxRuntime.jsx("td",{className:"w-10 px-4 py-2.5",children:jsxRuntime.jsx("input",{type:"checkbox",checked:d,onChange:()=>G(r),className:"h-4 w-4 rounded border-[var(--dash-border)] accent-[var(--dash-primary)]"})}),s.map(n=>jsxRuntime.jsx("td",{className:c("px-4 py-2.5",n.align==="center"&&"text-center",n.align==="right"&&"text-right"),children:n.cell?n.cell(e):String(e[n.id]??"")},n.id)),y&&jsxRuntime.jsx("td",{className:"px-4 py-2.5 text-right",children:y(e)})]},r)})})]})}),S>1&&jsxRuntime.jsxs("div",{className:"flex items-center justify-between border-t border-[var(--dash-border)] px-4 py-2.5 text-xs text-[var(--dash-text-muted)]",children:[jsxRuntime.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntime.jsx("span",{children:"Rows per page"}),jsxRuntime.jsx("select",{value:g,onChange:e=>V?.(Number(e.target.value)),className:"h-7 rounded border border-[var(--dash-border)] bg-[var(--dash-bg)] px-2 text-xs text-[var(--dash-text)] focus:outline-none",children:[10,20,50,100].map(e=>jsxRuntime.jsx("option",{value:e,children:e},e))})]}),jsxRuntime.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntime.jsxs("span",{children:["Page ",o+1," of ",S]}),jsxRuntime.jsx("button",{type:"button",disabled:o===0,onClick:()=>w?.(o-1),className:"rounded p-1 hover:bg-[var(--dash-surface-hover)] disabled:opacity-30 disabled:cursor-not-allowed",children:jsxRuntime.jsx("svg",{width:"14",height:"14",viewBox:"0 0 16 16",fill:"none",children:jsxRuntime.jsx("path",{d:"M10 4L6 8l4 4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})}),jsxRuntime.jsx("button",{type:"button",disabled:o>=S-1,onClick:()=>w?.(o+1),className:"rounded p-1 hover:bg-[var(--dash-surface-hover)] disabled:opacity-30 disabled:cursor-not-allowed",children:jsxRuntime.jsx("svg",{width:"14",height:"14",viewBox:"0 0 16 16",fill:"none",children:jsxRuntime.jsx("path",{d:"M6 4l4 4-4 4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})})]})]})]})}i(ee,"Table");exports.Table=ee;
|
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import*as u from'react';import {clsx}from'clsx';import {twMerge}from'tailwind-merge';import {jsxs,jsx}from'react/jsx-runtime';var J=Object.defineProperty;var i=(s,h)=>J(s,"name",{value:h,configurable:true});function c(...s){return twMerge(clsx(s))}i(c,"cn");function ee({columns:s,data:h,rowKey:f,selectable:l=false,selectedKeys:
|
|
2
|
+
import*as u from'react';import {clsx}from'clsx';import {twMerge}from'tailwind-merge';import {jsxs,jsx}from'react/jsx-runtime';var J=Object.defineProperty;var i=(s,h)=>J(s,"name",{value:h,configurable:true});function c(...s){return twMerge(clsx(s))}i(c,"cn");function ee({columns:s,data:h,rowKey:f,selectable:l=false,selectedKeys:j,onSelectionChange:m,searchable:L=false,searchPlaceholder:z="Search...",totalRows:B,page:o=0,pageSize:g=20,onPageChange:w,onPageSizeChange:V,actions:y,loading:W=false,emptyMessage:_="No data",className:q}){let[x,A]=u.useState(""),[p,D]=u.useState(null),N=u.useMemo(()=>{if(!x)return h;let e=x.toLowerCase();return h.filter(r=>s.some(d=>(d.cell?"":String(r[d.id]??"")).toLowerCase().includes(e)))},[h,x,s]),k=u.useMemo(()=>{if(!p)return N;let{column:e,direction:r}=p;return [...N].sort((d,n)=>{let C=d[e],T=n[e];if(C==null&&T==null)return 0;if(C==null)return 1;if(T==null)return -1;let P=String(C).localeCompare(String(T),void 0,{numeric:true});return r==="asc"?P:-P})},[N,p]),E=B??k.length,S=Math.max(1,Math.ceil(E/g)),b=w?k:k.slice(o*g,(o+1)*g),v=j??new Set,M=b.length>0&&b.every(e=>v.has(f(e)));function F(){m&&m(M?new Set:new Set(b.map(f)));}i(F,"toggleAll");function G(e){if(!m)return;let r=new Set(v);r.has(e)?r.delete(e):r.add(e),m(r);}i(G,"toggleRow");function H(e){D(r=>r?.column===e?r.direction==="asc"?{column:e,direction:"desc"}:null:{column:e,direction:"asc"});}i(H,"handleSort");let R=y?[...s,{id:"__actions",header:"",width:"auto"}]:s;return jsxs("div",{className:c("rounded-[var(--dash-radius-lg)] border border-[var(--dash-border)] bg-[var(--dash-surface)]",q),children:[(L||l)&&jsxs("div",{className:"flex items-center gap-3 border-b border-[var(--dash-border)] px-4 py-3",children:[L&&jsx("input",{type:"text",placeholder:z,value:x,onChange:e=>A(e.target.value),className:c("h-8 w-64 max-w-full rounded-[var(--dash-radius-sm)] border border-[var(--dash-border)] bg-[var(--dash-bg)] px-3 text-sm text-[var(--dash-text)]","placeholder:text-[var(--dash-text-dim)]","focus:border-[var(--dash-primary)] focus:outline-none focus:ring-1 focus:ring-[var(--dash-primary)]")}),l&&v.size>0&&jsxs("span",{className:"text-xs text-[var(--dash-text-muted)]",children:[v.size," selected"]})]}),jsx("div",{className:"overflow-x-auto",children:jsxs("table",{className:"w-full text-sm",children:[jsx("thead",{children:jsxs("tr",{className:"border-b border-[var(--dash-border)]",children:[l&&jsx("th",{className:"w-10 px-4 py-2.5",children:jsx("input",{type:"checkbox",checked:M,onChange:F,className:"h-4 w-4 rounded border-[var(--dash-border)] accent-[var(--dash-primary)]"})}),R.map(e=>jsx("th",{style:e.width?{width:e.width}:void 0,className:c("px-4 py-2.5 text-[var(--dash-text-dim)] font-medium",e.align==="center"&&"text-center",e.align==="right"&&"text-right",!e.align&&"text-left",e.sortable&&"cursor-pointer select-none hover:text-[var(--dash-text-muted)]"),onClick:e.sortable?()=>H(e.id):void 0,children:jsxs("span",{className:"inline-flex items-center gap-1",children:[e.header,e.sortable&&p?.column===e.id&&jsx("span",{className:"text-[10px]",children:p.direction==="asc"?"\u2191":"\u2193"})]})},e.id))]})}),jsx("tbody",{children:W?jsx("tr",{children:jsx("td",{colSpan:R.length+(l?1:0),className:"px-4 py-8 text-center text-[var(--dash-text-dim)]",children:"Loading..."})}):b.length===0?jsx("tr",{children:jsx("td",{colSpan:R.length+(l?1:0),className:"px-4 py-8 text-center text-[var(--dash-text-dim)]",children:_})}):b.map(e=>{let r=f(e),d=v.has(r);return jsxs("tr",{className:c("border-b border-[var(--dash-border)] transition-colors",d?"bg-[var(--dash-surface-active)]":"hover:bg-[var(--dash-surface-hover)]"),children:[l&&jsx("td",{className:"w-10 px-4 py-2.5",children:jsx("input",{type:"checkbox",checked:d,onChange:()=>G(r),className:"h-4 w-4 rounded border-[var(--dash-border)] accent-[var(--dash-primary)]"})}),s.map(n=>jsx("td",{className:c("px-4 py-2.5",n.align==="center"&&"text-center",n.align==="right"&&"text-right"),children:n.cell?n.cell(e):String(e[n.id]??"")},n.id)),y&&jsx("td",{className:"px-4 py-2.5 text-right",children:y(e)})]},r)})})]})}),S>1&&jsxs("div",{className:"flex items-center justify-between border-t border-[var(--dash-border)] px-4 py-2.5 text-xs text-[var(--dash-text-muted)]",children:[jsxs("div",{className:"flex items-center gap-2",children:[jsx("span",{children:"Rows per page"}),jsx("select",{value:g,onChange:e=>V?.(Number(e.target.value)),className:"h-7 rounded border border-[var(--dash-border)] bg-[var(--dash-bg)] px-2 text-xs text-[var(--dash-text)] focus:outline-none",children:[10,20,50,100].map(e=>jsx("option",{value:e,children:e},e))})]}),jsxs("div",{className:"flex items-center gap-2",children:[jsxs("span",{children:["Page ",o+1," of ",S]}),jsx("button",{type:"button",disabled:o===0,onClick:()=>w?.(o-1),className:"rounded p-1 hover:bg-[var(--dash-surface-hover)] disabled:opacity-30 disabled:cursor-not-allowed",children:jsx("svg",{width:"14",height:"14",viewBox:"0 0 16 16",fill:"none",children:jsx("path",{d:"M10 4L6 8l4 4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})}),jsx("button",{type:"button",disabled:o>=S-1,onClick:()=>w?.(o+1),className:"rounded p-1 hover:bg-[var(--dash-surface-hover)] disabled:opacity-30 disabled:cursor-not-allowed",children:jsx("svg",{width:"14",height:"14",viewBox:"0 0 16 16",fill:"none",children:jsx("path",{d:"M6 4l4 4-4 4",stroke:"currentColor",strokeWidth:"1.5",strokeLinecap:"round",strokeLinejoin:"round"})})})]})]})]})}i(ee,"Table");export{ee as Table};
|
|
@@ -1,18 +1,18 @@
|
|
|
1
|
-
import { type
|
|
2
|
-
import { type
|
|
3
|
-
export interface
|
|
1
|
+
import { type Column, type TableProps } from './table';
|
|
2
|
+
import { type FieldDef } from './form';
|
|
3
|
+
export interface CrudProps<T> {
|
|
4
4
|
/** Resource name (e.g. "User", "API Key") used in UI labels */
|
|
5
5
|
resourceName: string;
|
|
6
6
|
/** Plural resource name (defaults to resourceName + "s") */
|
|
7
7
|
resourceNamePlural?: string;
|
|
8
8
|
/** Column definitions for the list table */
|
|
9
|
-
columns:
|
|
9
|
+
columns: Column<T>[];
|
|
10
10
|
/** Row data */
|
|
11
11
|
data: T[];
|
|
12
12
|
/** Unique key extractor per row */
|
|
13
13
|
rowKey: (row: T) => string;
|
|
14
14
|
/** Field definitions for create/edit form */
|
|
15
|
-
fields:
|
|
15
|
+
fields: FieldDef[];
|
|
16
16
|
/** Convert a row to form values for editing */
|
|
17
17
|
rowToValues?: (row: T) => Record<string, unknown>;
|
|
18
18
|
/** Called when creating a new record */
|
|
@@ -27,11 +27,11 @@ export interface DashCrudProps<T> {
|
|
|
27
27
|
canEdit?: boolean;
|
|
28
28
|
/** Whether delete is available */
|
|
29
29
|
canDelete?: boolean;
|
|
30
|
-
/** Pass-through
|
|
31
|
-
tableProps?: Partial<
|
|
30
|
+
/** Pass-through Table props */
|
|
31
|
+
tableProps?: Partial<TableProps<T>>;
|
|
32
32
|
/** Loading state */
|
|
33
33
|
loading?: boolean;
|
|
34
34
|
className?: string;
|
|
35
35
|
}
|
|
36
|
-
export declare function
|
|
37
|
-
//# sourceMappingURL=
|
|
36
|
+
export declare function Crud<T>({ resourceName, resourceNamePlural, columns, data, rowKey, fields, rowToValues, onCreate, onUpdate, onDelete, canCreate, canEdit, canDelete, tableProps, loading, className, }: CrudProps<T>): import("react/jsx-runtime").JSX.Element;
|
|
37
|
+
//# sourceMappingURL=crud.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"crud.d.ts","sourceRoot":"","sources":["../../../src/dash/crud.tsx"],"names":[],"mappings":"AAIA,OAAO,EAAS,KAAK,MAAM,EAAE,KAAK,UAAU,EAAE,MAAM,SAAS,CAAA;AAC7D,OAAO,EAAQ,KAAK,QAAQ,EAAE,MAAM,QAAQ,CAAA;AAM5C,MAAM,WAAW,SAAS,CAAC,CAAC;IAC1B,+DAA+D;IAC/D,YAAY,EAAE,MAAM,CAAA;IACpB,4DAA4D;IAC5D,kBAAkB,CAAC,EAAE,MAAM,CAAA;IAC3B,4CAA4C;IAC5C,OAAO,EAAE,MAAM,CAAC,CAAC,CAAC,EAAE,CAAA;IACpB,eAAe;IACf,IAAI,EAAE,CAAC,EAAE,CAAA;IACT,mCAAmC;IACnC,MAAM,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,MAAM,CAAA;IAC1B,6CAA6C;IAC7C,MAAM,EAAE,QAAQ,EAAE,CAAA;IAClB,+CAA+C;IAC/C,WAAW,CAAC,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;IACjD,wCAAwC;IACxC,QAAQ,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,OAAO,CAAC,IAAI,CAAC,CAAA;IAC7D,8CAA8C;IAC9C,QAAQ,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,OAAO,CAAC,IAAI,CAAC,CAAA;IAC1E,oCAAoC;IACpC,QAAQ,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAA;IACzC,kCAAkC;IAClC,SAAS,CAAC,EAAE,OAAO,CAAA;IACnB,gCAAgC;IAChC,OAAO,CAAC,EAAE,OAAO,CAAA;IACjB,kCAAkC;IAClC,SAAS,CAAC,EAAE,OAAO,CAAA;IACnB,+BAA+B;IAC/B,UAAU,CAAC,EAAE,OAAO,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,CAAA;IACnC,oBAAoB;IACpB,OAAO,CAAC,EAAE,OAAO,CAAA;IACjB,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AAQD,wBAAgB,IAAI,CAAC,CAAC,EAAE,EACtB,YAAY,EACZ,kBAAkB,EAClB,OAAO,EACP,IAAI,EACJ,MAAM,EACN,MAAM,EACN,WAAW,EACX,QAAQ,EACR,QAAQ,EACR,QAAQ,EACR,SAAgB,EAChB,OAAc,EACd,SAAgB,EAChB,UAAU,EACV,OAAe,EACf,SAAS,GACV,EAAE,SAAS,CAAC,CAAC,CAAC,2CAgJd"}
|
|
@@ -2,12 +2,12 @@
|
|
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
3
|
import * as React from 'react';
|
|
4
4
|
import { cn } from '../../utils';
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
5
|
+
import { Table } from './table';
|
|
6
|
+
import { Form } from './form';
|
|
7
7
|
/* ------------------------------------------------------------------ */
|
|
8
8
|
/* Component */
|
|
9
9
|
/* ------------------------------------------------------------------ */
|
|
10
|
-
export function
|
|
10
|
+
export function Crud({ resourceName, resourceNamePlural, columns, data, rowKey, fields, rowToValues, onCreate, onUpdate, onDelete, canCreate = true, canEdit = true, canDelete = true, tableProps, loading = false, className, }) {
|
|
11
11
|
const plural = resourceNamePlural ?? `${resourceName}s`;
|
|
12
12
|
const [view, setView] = React.useState('list');
|
|
13
13
|
const [editingKey, setEditingKey] = React.useState(null);
|
|
@@ -47,10 +47,10 @@ export function DashCrud({ resourceName, resourceNamePlural, columns, data, rowK
|
|
|
47
47
|
setEditingKey(null);
|
|
48
48
|
setEditValues({});
|
|
49
49
|
setView('create');
|
|
50
|
-
}, className: cn('rounded-[var(--dash-radius)] px-3 py-1.5 text-sm font-medium transition-colors', 'bg-[var(--dash-primary)] text-[var(--dash-primary-text)]', 'hover:bg-[var(--dash-primary-hover)]'), children: ["Create ", resourceName] }))] }), _jsx(
|
|
50
|
+
}, className: cn('rounded-[var(--dash-radius)] px-3 py-1.5 text-sm font-medium transition-colors', 'bg-[var(--dash-primary)] text-[var(--dash-primary-text)]', 'hover:bg-[var(--dash-primary-hover)]'), children: ["Create ", resourceName] }))] }), _jsx(Table, { columns: columns, data: data, rowKey: rowKey, actions: (canEdit || canDelete) ? actionsRenderer : undefined, loading: loading, searchable: true, emptyMessage: `No ${plural.toLowerCase()} found`, ...tableProps }), deleteKey !== null && (_jsx(DeleteDialog, { resourceName: resourceName, loading: submitting, onConfirm: confirmDelete, onCancel: () => setDeleteKey(null) }))] }));
|
|
51
51
|
}
|
|
52
52
|
/* ------ create / edit view ------ */
|
|
53
|
-
return (_jsxs("div", { className: cn('space-y-4', className), children: [_jsxs("button", { type: "button", onClick: () => setView('list'), className: "inline-flex items-center gap-1 text-sm text-[var(--dash-text-muted)] hover:text-[var(--dash-text)] transition-colors", children: [_jsx("svg", { width: "14", height: "14", viewBox: "0 0 16 16", fill: "none", children: _jsx("path", { d: "M10 4L6 8l4 4", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round" }) }), "Back to ", plural] }), _jsx(
|
|
53
|
+
return (_jsxs("div", { className: cn('space-y-4', className), children: [_jsxs("button", { type: "button", onClick: () => setView('list'), className: "inline-flex items-center gap-1 text-sm text-[var(--dash-text-muted)] hover:text-[var(--dash-text)] transition-colors", children: [_jsx("svg", { width: "14", height: "14", viewBox: "0 0 16 16", fill: "none", children: _jsx("path", { d: "M10 4L6 8l4 4", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round" }) }), "Back to ", plural] }), _jsx(Form, { title: view === 'create' ? `Create ${resourceName}` : `Edit ${resourceName}`, fields: fields, values: view === 'edit' ? editValues : undefined, loading: submitting, submitLabel: view === 'create' ? 'Create' : 'Save changes', onCancel: () => setView('list'), onSubmit: async (vals) => {
|
|
54
54
|
setSubmitting(true);
|
|
55
55
|
try {
|
|
56
56
|
if (view === 'create' && onCreate) {
|
|
@@ -1,15 +1,15 @@
|
|
|
1
|
-
export type
|
|
2
|
-
export interface
|
|
1
|
+
export type FieldType = 'text' | 'number' | 'email' | 'password' | 'select' | 'toggle' | 'textarea' | 'json' | 'relation' | 'file';
|
|
2
|
+
export interface FieldOption {
|
|
3
3
|
label: string;
|
|
4
4
|
value: string;
|
|
5
5
|
}
|
|
6
|
-
export interface
|
|
6
|
+
export interface FieldDef {
|
|
7
7
|
/** Field key (maps to form value key) */
|
|
8
8
|
name: string;
|
|
9
9
|
/** Display label */
|
|
10
10
|
label: string;
|
|
11
11
|
/** Field type */
|
|
12
|
-
type:
|
|
12
|
+
type: FieldType;
|
|
13
13
|
/** Placeholder text */
|
|
14
14
|
placeholder?: string;
|
|
15
15
|
/** Description shown below field */
|
|
@@ -17,7 +17,7 @@ export interface DashFieldDef {
|
|
|
17
17
|
/** Whether the field is required */
|
|
18
18
|
required?: boolean;
|
|
19
19
|
/** Select options (for type=select or type=relation) */
|
|
20
|
-
options?:
|
|
20
|
+
options?: FieldOption[];
|
|
21
21
|
/** Default value */
|
|
22
22
|
defaultValue?: unknown;
|
|
23
23
|
/** Disabled */
|
|
@@ -29,11 +29,11 @@ export interface DashFieldDef {
|
|
|
29
29
|
/** Zod-style validation function. Return error string or null. */
|
|
30
30
|
validate?: (value: unknown) => string | null;
|
|
31
31
|
}
|
|
32
|
-
export interface
|
|
32
|
+
export interface FormProps {
|
|
33
33
|
/** Form title */
|
|
34
34
|
title?: string;
|
|
35
35
|
/** Field definitions */
|
|
36
|
-
fields:
|
|
36
|
+
fields: FieldDef[];
|
|
37
37
|
/** Initial values */
|
|
38
38
|
values?: Record<string, unknown>;
|
|
39
39
|
/** Called on submit with validated values */
|
|
@@ -48,5 +48,5 @@ export interface DashFormProps {
|
|
|
48
48
|
loading?: boolean;
|
|
49
49
|
className?: string;
|
|
50
50
|
}
|
|
51
|
-
export declare function
|
|
52
|
-
//# sourceMappingURL=
|
|
51
|
+
export declare function Form({ title, fields, values: initialValues, onSubmit, onCancel, submitLabel, cancelLabel, loading, className, }: FormProps): import("react/jsx-runtime").JSX.Element;
|
|
52
|
+
//# sourceMappingURL=form.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"form.d.ts","sourceRoot":"","sources":["../../../src/dash/form.tsx"],"names":[],"mappings":"AASA,MAAM,MAAM,SAAS,GACjB,MAAM,GACN,QAAQ,GACR,OAAO,GACP,UAAU,GACV,QAAQ,GACR,QAAQ,GACR,UAAU,GACV,MAAM,GACN,UAAU,GACV,MAAM,CAAA;AAEV,MAAM,WAAW,WAAW;IAC1B,KAAK,EAAE,MAAM,CAAA;IACb,KAAK,EAAE,MAAM,CAAA;CACd;AAED,MAAM,WAAW,QAAQ;IACvB,yCAAyC;IACzC,IAAI,EAAE,MAAM,CAAA;IACZ,oBAAoB;IACpB,KAAK,EAAE,MAAM,CAAA;IACb,iBAAiB;IACjB,IAAI,EAAE,SAAS,CAAA;IACf,uBAAuB;IACvB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,oCAAoC;IACpC,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,oCAAoC;IACpC,QAAQ,CAAC,EAAE,OAAO,CAAA;IAClB,wDAAwD;IACxD,OAAO,CAAC,EAAE,WAAW,EAAE,CAAA;IACvB,oBAAoB;IACpB,YAAY,CAAC,EAAE,OAAO,CAAA;IACtB,eAAe;IACf,QAAQ,CAAC,EAAE,OAAO,CAAA;IAClB,0CAA0C;IAC1C,MAAM,CAAC,EAAE,MAAM,CAAA;IACf,8BAA8B;IAC9B,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,kEAAkE;IAClE,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,MAAM,GAAG,IAAI,CAAA;CAC7C;AAED,MAAM,WAAW,SAAS;IACxB,iBAAiB;IACjB,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,wBAAwB;IACxB,MAAM,EAAE,QAAQ,EAAE,CAAA;IAClB,qBAAqB;IACrB,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;IAChC,6CAA6C;IAC7C,QAAQ,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAA;IACnE,uBAAuB;IACvB,QAAQ,CAAC,EAAE,MAAM,IAAI,CAAA;IACrB,0BAA0B;IAC1B,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,0BAA0B;IAC1B,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,oBAAoB;IACpB,OAAO,CAAC,EAAE,OAAO,CAAA;IACjB,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AAMD,wBAAgB,IAAI,CAAC,EACnB,KAAK,EACL,MAAM,EACN,MAAM,EAAE,aAAa,EACrB,QAAQ,EACR,QAAQ,EACR,WAAoB,EACpB,WAAsB,EACtB,OAAe,EACf,SAAS,GACV,EAAE,SAAS,2CAmGX"}
|
|
@@ -5,7 +5,7 @@ import { cn } from '../../utils';
|
|
|
5
5
|
/* ------------------------------------------------------------------ */
|
|
6
6
|
/* Component */
|
|
7
7
|
/* ------------------------------------------------------------------ */
|
|
8
|
-
export function
|
|
8
|
+
export function Form({ title, fields, values: initialValues, onSubmit, onCancel, submitLabel = 'Save', cancelLabel = 'Cancel', loading = false, className, }) {
|
|
9
9
|
const [values, setValues] = React.useState(() => {
|
|
10
10
|
const init = {};
|
|
11
11
|
for (const f of fields) {
|
|
@@ -3,7 +3,7 @@ export interface BreadcrumbItem {
|
|
|
3
3
|
label: string;
|
|
4
4
|
href?: string;
|
|
5
5
|
}
|
|
6
|
-
export interface
|
|
6
|
+
export interface HeaderProps {
|
|
7
7
|
/** Breadcrumb trail */
|
|
8
8
|
breadcrumbs?: BreadcrumbItem[];
|
|
9
9
|
/** Search input placeholder */
|
|
@@ -24,5 +24,5 @@ export interface DashHeaderProps {
|
|
|
24
24
|
actions?: React.ReactNode;
|
|
25
25
|
className?: string;
|
|
26
26
|
}
|
|
27
|
-
export declare function
|
|
28
|
-
//# sourceMappingURL=
|
|
27
|
+
export declare function Header({ breadcrumbs, searchPlaceholder, onSearch, avatarUrl, userName, userDropdown, onToggleTheme, theme, actions, className, }: HeaderProps): import("react/jsx-runtime").JSX.Element;
|
|
28
|
+
//# sourceMappingURL=header.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"header.d.ts","sourceRoot":"","sources":["../../../src/dash/header.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAA;AAO9B,MAAM,WAAW,cAAc;IAC7B,KAAK,EAAE,MAAM,CAAA;IACb,IAAI,CAAC,EAAE,MAAM,CAAA;CACd;AAED,MAAM,WAAW,WAAW;IAC1B,uBAAuB;IACvB,WAAW,CAAC,EAAE,cAAc,EAAE,CAAA;IAC9B,+BAA+B;IAC/B,iBAAiB,CAAC,EAAE,MAAM,CAAA;IAC1B,uCAAuC;IACvC,QAAQ,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAA;IAClC,sBAAsB;IACtB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,wBAAwB;IACxB,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,6CAA6C;IAC7C,YAAY,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IAC9B,8BAA8B;IAC9B,aAAa,CAAC,EAAE,MAAM,IAAI,CAAA;IAC1B,oBAAoB;IACpB,KAAK,CAAC,EAAE,MAAM,GAAG,OAAO,CAAA;IACxB,6DAA6D;IAC7D,OAAO,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IACzB,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AAMD,wBAAgB,MAAM,CAAC,EACrB,WAAW,EACX,iBAA+B,EAC/B,QAAQ,EACR,SAAS,EACT,QAAQ,EACR,YAAY,EACZ,aAAa,EACb,KAAc,EACd,OAAO,EACP,SAAS,GACV,EAAE,WAAW,2CAmIb"}
|
|
@@ -5,7 +5,7 @@ import { cn } from '../../utils';
|
|
|
5
5
|
/* ------------------------------------------------------------------ */
|
|
6
6
|
/* Component */
|
|
7
7
|
/* ------------------------------------------------------------------ */
|
|
8
|
-
export function
|
|
8
|
+
export function Header({ breadcrumbs, searchPlaceholder = 'Search...', onSearch, avatarUrl, userName, userDropdown, onToggleTheme, theme = 'dark', actions, className, }) {
|
|
9
9
|
const [dropdownOpen, setDropdownOpen] = React.useState(false);
|
|
10
10
|
const dropdownRef = React.useRef(null);
|
|
11
11
|
// Close dropdown on outside click
|
package/dist/src/dash/index.d.ts
CHANGED
|
@@ -6,16 +6,16 @@
|
|
|
6
6
|
*
|
|
7
7
|
* Design tokens in tokens.css work in both React and Svelte.
|
|
8
8
|
*/
|
|
9
|
-
export {
|
|
10
|
-
export type {
|
|
11
|
-
export {
|
|
12
|
-
export type {
|
|
13
|
-
export {
|
|
14
|
-
export type {
|
|
15
|
-
export {
|
|
16
|
-
export type {
|
|
17
|
-
export {
|
|
18
|
-
export type {
|
|
19
|
-
export {
|
|
20
|
-
export type {
|
|
9
|
+
export { Layout } from './layout';
|
|
10
|
+
export type { LayoutProps } from './layout';
|
|
11
|
+
export { Sidebar } from './sidebar';
|
|
12
|
+
export type { SidebarProps, NavItem, NavGroup } from './sidebar';
|
|
13
|
+
export { Header } from './header';
|
|
14
|
+
export type { HeaderProps, BreadcrumbItem } from './header';
|
|
15
|
+
export { Table } from './table';
|
|
16
|
+
export type { TableProps, Column } from './table';
|
|
17
|
+
export { Form } from './form';
|
|
18
|
+
export type { FormProps, FieldDef, FieldType, FieldOption } from './form';
|
|
19
|
+
export { Crud } from './crud';
|
|
20
|
+
export type { CrudProps } from './crud';
|
|
21
21
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/dash/index.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAGH,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/dash/index.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAGH,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAA;AACjC,YAAY,EAAE,WAAW,EAAE,MAAM,UAAU,CAAA;AAG3C,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,YAAY,EAAE,YAAY,EAAE,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAA;AAGhE,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAA;AACjC,YAAY,EAAE,WAAW,EAAE,cAAc,EAAE,MAAM,UAAU,CAAA;AAG3D,OAAO,EAAE,KAAK,EAAE,MAAM,SAAS,CAAA;AAC/B,YAAY,EAAE,UAAU,EAAE,MAAM,EAAE,MAAM,SAAS,CAAA;AAGjD,OAAO,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAA;AAC7B,YAAY,EAAE,SAAS,EAAE,QAAQ,EAAE,SAAS,EAAE,WAAW,EAAE,MAAM,QAAQ,CAAA;AAGzE,OAAO,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAA;AAC7B,YAAY,EAAE,SAAS,EAAE,MAAM,QAAQ,CAAA"}
|
package/dist/src/dash/index.js
CHANGED
|
@@ -7,14 +7,14 @@
|
|
|
7
7
|
* Design tokens in tokens.css work in both React and Svelte.
|
|
8
8
|
*/
|
|
9
9
|
// Layout
|
|
10
|
-
export {
|
|
10
|
+
export { Layout } from './layout';
|
|
11
11
|
// Sidebar
|
|
12
|
-
export {
|
|
12
|
+
export { Sidebar } from './sidebar';
|
|
13
13
|
// Header
|
|
14
|
-
export {
|
|
14
|
+
export { Header } from './header';
|
|
15
15
|
// Data Table
|
|
16
|
-
export {
|
|
16
|
+
export { Table } from './table';
|
|
17
17
|
// Form
|
|
18
|
-
export {
|
|
18
|
+
export { Form } from './form';
|
|
19
19
|
// CRUD
|
|
20
|
-
export {
|
|
20
|
+
export { Crud } from './crud';
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
|
-
export interface
|
|
3
|
-
/** Sidebar element (use
|
|
2
|
+
export interface LayoutProps {
|
|
3
|
+
/** Sidebar element (use Sidebar) */
|
|
4
4
|
sidebar: React.ReactNode;
|
|
5
|
-
/** Top header element (use
|
|
5
|
+
/** Top header element (use Header) */
|
|
6
6
|
header?: React.ReactNode;
|
|
7
7
|
/** Main content */
|
|
8
8
|
children: React.ReactNode;
|
|
@@ -12,5 +12,5 @@ export interface DashLayoutProps {
|
|
|
12
12
|
onSidebarCollapse?: (collapsed: boolean) => void;
|
|
13
13
|
className?: string;
|
|
14
14
|
}
|
|
15
|
-
export declare function
|
|
16
|
-
//# sourceMappingURL=
|
|
15
|
+
export declare function Layout({ sidebar, header, children, sidebarCollapsed, onSidebarCollapse, className, }: LayoutProps): import("react/jsx-runtime").JSX.Element;
|
|
16
|
+
//# sourceMappingURL=layout.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"layout.d.ts","sourceRoot":"","sources":["../../../src/dash/layout.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAA;AAG9B,MAAM,WAAW,WAAW;IAC1B,oCAAoC;IACpC,OAAO,EAAE,KAAK,CAAC,SAAS,CAAA;IACxB,sCAAsC;IACtC,MAAM,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IACxB,mBAAmB;IACnB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAA;IACzB,uCAAuC;IACvC,gBAAgB,CAAC,EAAE,OAAO,CAAA;IAC1B,mDAAmD;IACnD,iBAAiB,CAAC,EAAE,CAAC,SAAS,EAAE,OAAO,KAAK,IAAI,CAAA;IAChD,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AAED,wBAAgB,MAAM,CAAC,EACrB,OAAO,EACP,MAAM,EACN,QAAQ,EACR,gBAAwB,EACxB,iBAAiB,EACjB,SAAS,GACV,EAAE,WAAW,2CAyCb"}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
3
|
import { cn } from '../../utils';
|
|
4
|
-
export function
|
|
4
|
+
export function Layout({ sidebar, header, children, sidebarCollapsed = false, onSidebarCollapse, className, }) {
|
|
5
5
|
return (_jsxs("div", { className: cn('flex h-screen overflow-hidden', 'bg-[var(--dash-bg)] text-[var(--dash-text)]', className), children: [_jsx("aside", { className: cn('flex-shrink-0 overflow-y-auto overflow-x-hidden transition-[width] duration-200', 'border-r border-[var(--dash-border)] bg-[var(--dash-surface)]', sidebarCollapsed
|
|
6
6
|
? 'w-[var(--dash-sidebar-collapsed-width)]'
|
|
7
7
|
: 'w-[var(--dash-sidebar-width)]'), children: sidebar }), _jsxs("div", { className: "flex flex-1 flex-col overflow-hidden", children: [header && (_jsx("header", { className: "flex-shrink-0 border-b border-[var(--dash-border)] bg-[var(--dash-surface)]", children: header })), _jsx("main", { className: "flex-1 overflow-y-auto p-6", children: children })] }), !sidebarCollapsed && (_jsx("div", { className: "fixed inset-0 z-40 bg-black/60 lg:hidden", onClick: () => onSidebarCollapse?.(true) }))] }));
|
|
@@ -12,7 +12,7 @@ export interface NavGroup {
|
|
|
12
12
|
collapsible?: boolean;
|
|
13
13
|
defaultOpen?: boolean;
|
|
14
14
|
}
|
|
15
|
-
export interface
|
|
15
|
+
export interface SidebarProps {
|
|
16
16
|
/** Logo or brand element rendered at the top */
|
|
17
17
|
logo?: React.ReactNode;
|
|
18
18
|
/** Navigation groups */
|
|
@@ -27,5 +27,5 @@ export interface DashSidebarProps {
|
|
|
27
27
|
onNavigate?: (href: string) => void;
|
|
28
28
|
className?: string;
|
|
29
29
|
}
|
|
30
|
-
export declare function
|
|
31
|
-
//# sourceMappingURL=
|
|
30
|
+
export declare function Sidebar({ logo, groups, userMenu, collapsed, onToggleCollapse, onNavigate, className, }: SidebarProps): import("react/jsx-runtime").JSX.Element;
|
|
31
|
+
//# sourceMappingURL=sidebar.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sidebar.d.ts","sourceRoot":"","sources":["../../../src/dash/sidebar.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAA;AAO9B,MAAM,WAAW,OAAO;IACtB,KAAK,EAAE,MAAM,CAAA;IACb,IAAI,EAAE,MAAM,CAAA;IACZ,IAAI,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IACtB,KAAK,CAAC,EAAE,MAAM,GAAG,MAAM,CAAA;IACvB,MAAM,CAAC,EAAE,OAAO,CAAA;CACjB;AAED,MAAM,WAAW,QAAQ;IACvB,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,KAAK,EAAE,OAAO,EAAE,CAAA;IAChB,WAAW,CAAC,EAAE,OAAO,CAAA;IACrB,WAAW,CAAC,EAAE,OAAO,CAAA;CACtB;AAED,MAAM,WAAW,YAAY;IAC3B,gDAAgD;IAChD,IAAI,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IACtB,wBAAwB;IACxB,MAAM,EAAE,QAAQ,EAAE,CAAA;IAClB,uCAAuC;IACvC,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IAC1B,wDAAwD;IACxD,SAAS,CAAC,EAAE,OAAO,CAAA;IACnB,sBAAsB;IACtB,gBAAgB,CAAC,EAAE,MAAM,IAAI,CAAA;IAC7B,wCAAwC;IACxC,UAAU,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAA;IACnC,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AA2BD,wBAAgB,OAAO,CAAC,EACtB,IAAI,EACJ,MAAM,EACN,QAAQ,EACR,SAAiB,EACjB,gBAAgB,EAChB,UAAU,EACV,SAAS,GACV,EAAE,YAAY,2CA+Dd"}
|
|
@@ -11,7 +11,7 @@ function HanzoMark({ size = 28 }) {
|
|
|
11
11
|
/* ------------------------------------------------------------------ */
|
|
12
12
|
/* Component */
|
|
13
13
|
/* ------------------------------------------------------------------ */
|
|
14
|
-
export function
|
|
14
|
+
export function Sidebar({ logo, groups, userMenu, collapsed = false, onToggleCollapse, onNavigate, className, }) {
|
|
15
15
|
return (_jsxs("nav", { className: cn('flex h-full flex-col', 'bg-[var(--dash-surface)] text-[var(--dash-text)]', className), children: [_jsxs("div", { className: cn('flex h-[var(--dash-header-height)] items-center border-b border-[var(--dash-border)]', collapsed ? 'justify-center px-2' : 'px-4'), children: [logo ?? _jsx(HanzoMark, {}), !collapsed && onToggleCollapse && (_jsx("button", { type: "button", onClick: onToggleCollapse, className: "ml-auto rounded p-1 text-[var(--dash-text-dim)] hover:bg-[var(--dash-surface-hover)] hover:text-[var(--dash-text)]", "aria-label": "Collapse sidebar", children: _jsx("svg", { width: "16", height: "16", viewBox: "0 0 16 16", fill: "none", children: _jsx("path", { d: "M10 4L6 8l4 4", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round" }) }) })), collapsed && onToggleCollapse && (_jsx("button", { type: "button", onClick: onToggleCollapse, className: "absolute -right-3 top-4 z-50 hidden rounded-full border border-[var(--dash-border)] bg-[var(--dash-surface)] p-1 text-[var(--dash-text-dim)] hover:text-[var(--dash-text)] lg:flex", "aria-label": "Expand sidebar", children: _jsx("svg", { width: "12", height: "12", viewBox: "0 0 16 16", fill: "none", children: _jsx("path", { d: "M6 4l4 4-4 4", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round" }) }) }))] }), _jsx("div", { className: "flex-1 overflow-y-auto py-2", children: groups.map((group, gi) => (_jsx(SidebarGroup, { group: group, collapsed: collapsed, onNavigate: onNavigate }, gi))) }), userMenu && (_jsx("div", { className: "border-t border-[var(--dash-border)] p-2", children: userMenu }))] }));
|
|
16
16
|
}
|
|
17
17
|
/* ------------------------------------------------------------------ */
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
|
-
export interface
|
|
2
|
+
export interface Column<T> {
|
|
3
3
|
id: string;
|
|
4
4
|
header: string;
|
|
5
5
|
/** Render cell content. Falls back to (row as any)[id]. */
|
|
@@ -11,9 +11,9 @@ export interface DashColumn<T> {
|
|
|
11
11
|
/** Alignment */
|
|
12
12
|
align?: 'left' | 'center' | 'right';
|
|
13
13
|
}
|
|
14
|
-
export interface
|
|
14
|
+
export interface TableProps<T> {
|
|
15
15
|
/** Column definitions */
|
|
16
|
-
columns:
|
|
16
|
+
columns: Column<T>[];
|
|
17
17
|
/** Row data */
|
|
18
18
|
data: T[];
|
|
19
19
|
/** Unique key extractor per row */
|
|
@@ -46,5 +46,5 @@ export interface DashDataTableProps<T> {
|
|
|
46
46
|
emptyMessage?: string;
|
|
47
47
|
className?: string;
|
|
48
48
|
}
|
|
49
|
-
export declare function
|
|
50
|
-
//# sourceMappingURL=
|
|
49
|
+
export declare function Table<T>({ columns, data, rowKey, selectable, selectedKeys, onSelectionChange, searchable, searchPlaceholder, totalRows, page, pageSize, onPageChange, onPageSizeChange, actions, loading, emptyMessage, className, }: TableProps<T>): import("react/jsx-runtime").JSX.Element;
|
|
50
|
+
//# sourceMappingURL=table.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"table.d.ts","sourceRoot":"","sources":["../../../src/dash/table.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAA;AAO9B,MAAM,WAAW,MAAM,CAAC,CAAC;IACvB,EAAE,EAAE,MAAM,CAAA;IACV,MAAM,EAAE,MAAM,CAAA;IACd,2DAA2D;IAC3D,IAAI,CAAC,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,KAAK,CAAC,SAAS,CAAA;IAClC,oCAAoC;IACpC,QAAQ,CAAC,EAAE,OAAO,CAAA;IAClB,6BAA6B;IAC7B,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,gBAAgB;IAChB,KAAK,CAAC,EAAE,MAAM,GAAG,QAAQ,GAAG,OAAO,CAAA;CACpC;AAED,MAAM,WAAW,UAAU,CAAC,CAAC;IAC3B,yBAAyB;IACzB,OAAO,EAAE,MAAM,CAAC,CAAC,CAAC,EAAE,CAAA;IACpB,eAAe;IACf,IAAI,EAAE,CAAC,EAAE,CAAA;IACT,mCAAmC;IACnC,MAAM,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,MAAM,CAAA;IAC1B,sCAAsC;IACtC,UAAU,CAAC,EAAE,OAAO,CAAA;IACpB,kCAAkC;IAClC,YAAY,CAAC,EAAE,GAAG,CAAC,MAAM,CAAC,CAAA;IAC1B,oCAAoC;IACpC,iBAAiB,CAAC,EAAE,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,KAAK,IAAI,CAAA;IAC/C,kDAAkD;IAClD,UAAU,CAAC,EAAE,OAAO,CAAA;IACpB,yBAAyB;IACzB,iBAAiB,CAAC,EAAE,MAAM,CAAA;IAC1B,sFAAsF;IACtF,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,+BAA+B;IAC/B,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,oBAAoB;IACpB,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,+BAA+B;IAC/B,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAA;IACrC,oCAAoC;IACpC,gBAAgB,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAA;IACzC,0DAA0D;IAC1D,OAAO,CAAC,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,KAAK,CAAC,SAAS,CAAA;IACrC,oBAAoB;IACpB,OAAO,CAAC,EAAE,OAAO,CAAA;IACjB,0BAA0B;IAC1B,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AAQD,wBAAgB,KAAK,CAAC,CAAC,EAAE,EACvB,OAAO,EACP,IAAI,EACJ,MAAM,EACN,UAAkB,EAClB,YAAY,EACZ,iBAAiB,EACjB,UAAkB,EAClB,iBAA+B,EAC/B,SAAS,EACT,IAAQ,EACR,QAAa,EACb,YAAY,EACZ,gBAAgB,EAChB,OAAO,EACP,OAAe,EACf,YAAwB,EACxB,SAAS,GACV,EAAE,UAAU,CAAC,CAAC,CAAC,2CAyPf"}
|
|
@@ -5,7 +5,7 @@ import { cn } from '../../utils';
|
|
|
5
5
|
/* ------------------------------------------------------------------ */
|
|
6
6
|
/* Component */
|
|
7
7
|
/* ------------------------------------------------------------------ */
|
|
8
|
-
export function
|
|
8
|
+
export function Table({ columns, data, rowKey, selectable = false, selectedKeys, onSelectionChange, searchable = false, searchPlaceholder = 'Search...', totalRows, page = 0, pageSize = 20, onPageChange, onPageSizeChange, actions, loading = false, emptyMessage = 'No data', className, }) {
|
|
9
9
|
const [search, setSearch] = React.useState('');
|
|
10
10
|
const [sort, setSort] = React.useState(null);
|
|
11
11
|
/* ---------- filtering ---------- */
|