denwa-react-shared 1.0.87 → 1.0.89

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.
@@ -1,4 +1,4 @@
1
- import { _ as F, u as Ce, C as Re, a as G, c as X, b as de, d as je, e as Oe, o as Ne, f as ie, g as L, h as ue, i as Me, m as Ee, r as Ie, j as He, k as B, l as Pe, t as Ve, n as De, p as Be, q as Te, I as Ae, s as _e, v as ze, w as Fe, x as Ke, T as Le, y as v, F as U, z as W, S as Z, B as We, A as Xe, D as qe, E as Ue, G as J, H as oe, R as Ge } from "./index-BsL--dhU.js";
1
+ import { _ as F, u as Ce, C as Re, a as G, c as X, b as de, d as je, e as Oe, o as Ne, f as ie, g as L, h as ue, i as Me, m as Ee, r as Ie, j as He, k as B, l as Pe, t as Ve, n as De, p as Be, q as Te, I as Ae, s as _e, v as ze, w as Fe, x as Ke, T as Le, y as v, F as U, z as W, S as Z, B as We, A as Xe, D as qe, E as Ue, G as J, H as oe, R as Ge } from "./index-DQufMkbF.js";
2
2
  import * as i from "react";
3
3
  import { useState as Ye, useMemo as Je, createElement as Ze } from "react";
4
4
  var le = function(t, n) {
@@ -1 +1 @@
1
- "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const n=require("./index-UAPQw7y7.cjs"),K=require("react");function me(e){const t=Object.create(null,{[Symbol.toStringTag]:{value:"Module"}});if(e){for(const i in e)if(i!=="default"){const a=Object.getOwnPropertyDescriptor(e,i);Object.defineProperty(t,i,a.get?a:{enumerable:!0,get:()=>e[i]})}}return t.default=e,Object.freeze(t)}const o=me(K);var J=function(t,i){if(!t)return null;var a={left:t.offsetLeft,right:t.parentElement.clientWidth-t.clientWidth-t.offsetLeft,width:t.clientWidth,top:t.offsetTop,bottom:t.parentElement.clientHeight-t.clientHeight-t.offsetTop,height:t.clientHeight};return i?{left:0,right:0,width:0,top:a.top,bottom:a.bottom,height:a.height}:{left:a.left,right:a.right,width:a.width,top:0,bottom:0,height:0}},T=function(t){return t!==void 0?"".concat(t,"px"):void 0};function fe(e){var t=e.prefixCls,i=e.containerRef,a=e.value,r=e.getValueIndex,s=e.motionName,p=e.onMotionStart,h=e.onMotionEnd,b=e.direction,S=e.vertical,d=S===void 0?!1:S,$=o.useRef(null),w=o.useState(a),R=n._slicedToArray(w,2),v=R[0],M=R[1],C=function(P){var m,B=r(P),_=(m=i.current)===null||m===void 0?void 0:m.querySelectorAll(".".concat(t,"-item"))[B];return(_==null?void 0:_.offsetParent)&&_},E=o.useState(null),f=n._slicedToArray(E,2),l=f[0],N=f[1],V=o.useState(null),x=n._slicedToArray(V,2),c=x[0],I=x[1];n.useLayoutEffect(function(){if(v!==a){var u=C(v),P=C(a),m=J(u,d),B=J(P,d);M(a),N(m),I(B),u&&P?p():h()}},[a]);var y=o.useMemo(function(){if(d){var u;return T((u=l==null?void 0:l.top)!==null&&u!==void 0?u:0)}return T(b==="rtl"?-(l==null?void 0:l.right):l==null?void 0:l.left)},[d,b,l]),O=o.useMemo(function(){if(d){var u;return T((u=c==null?void 0:c.top)!==null&&u!==void 0?u:0)}return T(b==="rtl"?-(c==null?void 0:c.right):c==null?void 0:c.left)},[d,b,c]),D=function(){return d?{transform:"translateY(var(--thumb-start-top))",height:"var(--thumb-start-height)"}:{transform:"translateX(var(--thumb-start-left))",width:"var(--thumb-start-width)"}},H=function(){return d?{transform:"translateY(var(--thumb-active-top))",height:"var(--thumb-active-height)"}:{transform:"translateX(var(--thumb-active-left))",width:"var(--thumb-active-width)"}},A=function(){N(null),I(null),h()};return!l||!c?null:o.createElement(n.CSSMotion,{visible:!0,motionName:s,motionAppear:!0,onAppearStart:D,onAppearActive:H,onVisibleChanged:A},function(u,P){var m=u.className,B=u.style,_=n._objectSpread2(n._objectSpread2({},B),{},{"--thumb-start-left":y,"--thumb-start-width":T(l==null?void 0:l.width),"--thumb-active-left":O,"--thumb-active-width":T(c==null?void 0:c.width),"--thumb-start-top":y,"--thumb-start-height":T(l==null?void 0:l.height),"--thumb-active-top":O,"--thumb-active-height":T(c==null?void 0:c.height)}),F={ref:n.composeRef($,P),style:_,className:n.cn("".concat(t,"-thumb"),m)};return process.env.NODE_ENV==="test"&&(F["data-test-style"]=JSON.stringify(_)),o.createElement("div",F)})}var ve=["prefixCls","direction","vertical","options","disabled","defaultValue","value","name","onChange","className","motionName"];function ge(e){if(typeof e.title<"u")return e.title;if(n._typeof(e.label)!=="object"){var t;return(t=e.label)===null||t===void 0?void 0:t.toString()}}function he(e){return e.map(function(t){if(n._typeof(t)==="object"&&t!==null){var i=ge(t);return n._objectSpread2(n._objectSpread2({},t),{},{title:i})}return{label:t==null?void 0:t.toString(),title:t==null?void 0:t.toString(),value:t}})}var be=function(t){var i=t.prefixCls,a=t.className,r=t.disabled,s=t.checked,p=t.label,h=t.title,b=t.value,S=t.name,d=t.onChange,$=t.onFocus,w=t.onBlur,R=t.onKeyDown,v=t.onKeyUp,M=t.onMouseDown,C=function(f){r||d(f,b)};return o.createElement("label",{className:n.cn(a,n._defineProperty({},"".concat(i,"-item-disabled"),r)),onMouseDown:M},o.createElement("input",{name:S,className:"".concat(i,"-item-input"),type:"radio",disabled:r,checked:s,onChange:C,onFocus:$,onBlur:w,onKeyDown:R,onKeyUp:v}),o.createElement("div",{className:"".concat(i,"-item-label"),title:h,"aria-selected":s},p))},ee=o.forwardRef(function(e,t){var i,a,r=e.prefixCls,s=r===void 0?"rc-segmented":r,p=e.direction,h=e.vertical,b=e.options,S=b===void 0?[]:b,d=e.disabled,$=e.defaultValue,w=e.value,R=e.name,v=e.onChange,M=e.className,C=M===void 0?"":M,E=e.motionName,f=E===void 0?"thumb-motion":E,l=n._objectWithoutProperties(e,ve),N=o.useRef(null),V=o.useMemo(function(){return n.composeRef(N,t)},[N,t]),x=o.useMemo(function(){return he(S)},[S]),c=n.useMergedState((i=x[0])===null||i===void 0?void 0:i.value,{value:w,defaultValue:$}),I=n._slicedToArray(c,2),y=I[0],O=I[1],D=o.useState(!1),H=n._slicedToArray(D,2),A=H[0],u=H[1],P=function(j,z){O(z),v==null||v(z)},m=n.omit(l,["children"]),B=o.useState(!1),_=n._slicedToArray(B,2),F=_[0],X=_[1],ae=o.useState(!1),q=n._slicedToArray(ae,2),ie=q[0],U=q[1],oe=function(){U(!0)},re=function(){U(!1)},le=function(){X(!1)},se=function(j){j.key==="Tab"&&X(!0)},G=function(j){var z=x.findIndex(function(de){return de.value===y}),Y=x.length,ue=(z+j+Y)%Y,L=x[ue];L&&(O(L.value),v==null||v(L.value))},ce=function(j){switch(j.key){case"ArrowLeft":case"ArrowUp":G(-1);break;case"ArrowRight":case"ArrowDown":G(1);break}};return o.createElement("div",n._extends({role:"radiogroup","aria-label":"segmented control",tabIndex:d?void 0:0},m,{className:n.cn(s,(a={},n._defineProperty(a,"".concat(s,"-rtl"),p==="rtl"),n._defineProperty(a,"".concat(s,"-disabled"),d),n._defineProperty(a,"".concat(s,"-vertical"),h),a),C),ref:V}),o.createElement("div",{className:"".concat(s,"-group")},o.createElement(fe,{vertical:h,prefixCls:s,value:y,containerRef:N,motionName:"".concat(s,"-").concat(f),direction:p,getValueIndex:function(j){return x.findIndex(function(z){return z.value===j})},onMotionStart:function(){u(!0)},onMotionEnd:function(){u(!1)}}),x.map(function(g){var j;return o.createElement(be,n._extends({},g,{name:R,key:g.value,prefixCls:s,className:n.cn(g.className,"".concat(s,"-item"),(j={},n._defineProperty(j,"".concat(s,"-item-selected"),g.value===y&&!A),n._defineProperty(j,"".concat(s,"-item-focused"),ie&&F&&g.value===y),j)),checked:g.value===y,onChange:P,onFocus:oe,onBlur:re,onKeyDown:ce,onKeyUp:se,onMouseDown:le,disabled:!!d||!!g.disabled}))})))});process.env.NODE_ENV!=="production"&&(ee.displayName="Segmented");var pe=ee;function Z(e,t){return{[`${e}, ${e}:hover, ${e}:focus`]:{color:t.colorTextDisabled,cursor:"not-allowed"}}}function Q(e){return{backgroundColor:e.itemSelectedBg,boxShadow:e.boxShadowTertiary}}const xe=Object.assign({overflow:"hidden"},n.textEllipsis),Se=e=>{const{componentCls:t}=e,i=e.calc(e.controlHeight).sub(e.calc(e.trackPadding).mul(2)).equal(),a=e.calc(e.controlHeightLG).sub(e.calc(e.trackPadding).mul(2)).equal(),r=e.calc(e.controlHeightSM).sub(e.calc(e.trackPadding).mul(2)).equal();return{[t]:Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign({},n.resetComponent(e)),{display:"inline-block",padding:e.trackPadding,color:e.itemColor,background:e.trackBg,borderRadius:e.borderRadius,transition:`all ${e.motionDurationMid} ${e.motionEaseInOut}`}),n.genFocusStyle(e)),{[`${t}-group`]:{position:"relative",display:"flex",alignItems:"stretch",justifyItems:"flex-start",flexDirection:"row",width:"100%"},[`&${t}-rtl`]:{direction:"rtl"},[`&${t}-vertical`]:{[`${t}-group`]:{flexDirection:"column"},[`${t}-thumb`]:{width:"100%",height:0,padding:`0 ${n.unit(e.paddingXXS)}`}},[`&${t}-block`]:{display:"flex"},[`&${t}-block ${t}-item`]:{flex:1,minWidth:0},[`${t}-item`]:{position:"relative",textAlign:"center",cursor:"pointer",transition:`color ${e.motionDurationMid} ${e.motionEaseInOut}`,borderRadius:e.borderRadiusSM,transform:"translateZ(0)","&-selected":Object.assign(Object.assign({},Q(e)),{color:e.itemSelectedColor}),"&-focused":Object.assign({},n.genFocusOutline(e)),"&::after":{content:'""',position:"absolute",zIndex:-1,width:"100%",height:"100%",top:0,insetInlineStart:0,borderRadius:"inherit",opacity:0,transition:`opacity ${e.motionDurationMid}`,pointerEvents:"none"},[`&:hover:not(${t}-item-selected):not(${t}-item-disabled)`]:{color:e.itemHoverColor,"&::after":{opacity:1,backgroundColor:e.itemHoverBg}},[`&:active:not(${t}-item-selected):not(${t}-item-disabled)`]:{color:e.itemHoverColor,"&::after":{opacity:1,backgroundColor:e.itemActiveBg}},"&-label":Object.assign({minHeight:i,lineHeight:n.unit(i),padding:`0 ${n.unit(e.segmentedPaddingHorizontal)}`},xe),"&-icon + *":{marginInlineStart:e.calc(e.marginSM).div(2).equal()},"&-input":{position:"absolute",insetBlockStart:0,insetInlineStart:0,width:0,height:0,opacity:0,pointerEvents:"none"}},[`${t}-thumb`]:Object.assign(Object.assign({},Q(e)),{position:"absolute",insetBlockStart:0,insetInlineStart:0,width:0,height:"100%",padding:`${n.unit(e.paddingXXS)} 0`,borderRadius:e.borderRadiusSM,transition:`transform ${e.motionDurationSlow} ${e.motionEaseInOut}, height ${e.motionDurationSlow} ${e.motionEaseInOut}`,[`& ~ ${t}-item:not(${t}-item-selected):not(${t}-item-disabled)::after`]:{backgroundColor:"transparent"}}),[`&${t}-lg`]:{borderRadius:e.borderRadiusLG,[`${t}-item-label`]:{minHeight:a,lineHeight:n.unit(a),padding:`0 ${n.unit(e.segmentedPaddingHorizontal)}`,fontSize:e.fontSizeLG},[`${t}-item, ${t}-thumb`]:{borderRadius:e.borderRadius}},[`&${t}-sm`]:{borderRadius:e.borderRadiusSM,[`${t}-item-label`]:{minHeight:r,lineHeight:n.unit(r),padding:`0 ${n.unit(e.segmentedPaddingHorizontalSM)}`},[`${t}-item, ${t}-thumb`]:{borderRadius:e.borderRadiusXS}}}),Z(`&-disabled ${t}-item`,e)),Z(`${t}-item-disabled`,e)),{[`${t}-thumb-motion-appear-active`]:{transition:`transform ${e.motionDurationSlow} ${e.motionEaseInOut}, width ${e.motionDurationSlow} ${e.motionEaseInOut}`,willChange:"transform, width"},[`&${t}-shape-round`]:{borderRadius:9999,[`${t}-item, ${t}-thumb`]:{borderRadius:9999}}})}},ye=e=>{const{colorTextLabel:t,colorText:i,colorFillSecondary:a,colorBgElevated:r,colorFill:s,lineWidthBold:p,colorBgLayout:h}=e;return{trackPadding:p,trackBg:h,itemColor:t,itemHoverColor:i,itemHoverBg:a,itemSelectedBg:r,itemActiveBg:s,itemSelectedColor:i}},je=n.genStyleHooks("Segmented",e=>{const{lineWidth:t,calc:i}=e,a=n.merge(e,{segmentedPaddingHorizontal:i(e.controlPaddingHorizontal).sub(t).equal(),segmentedPaddingHorizontalSM:i(e.controlPaddingHorizontalSM).sub(t).equal()});return[Se(a)]},ye);var k=function(e,t){var i={};for(var a in e)Object.prototype.hasOwnProperty.call(e,a)&&t.indexOf(a)<0&&(i[a]=e[a]);if(e!=null&&typeof Object.getOwnPropertySymbols=="function")for(var r=0,a=Object.getOwnPropertySymbols(e);r<a.length;r++)t.indexOf(a[r])<0&&Object.prototype.propertyIsEnumerable.call(e,a[r])&&(i[a[r]]=e[a[r]]);return i};function $e(e){return typeof e=="object"&&!!(e!=null&&e.icon)}const we=o.forwardRef((e,t)=>{const i=n.useId(),{prefixCls:a,className:r,rootClassName:s,block:p,options:h=[],size:b="middle",style:S,vertical:d,shape:$="default",name:w=i}=e,R=k(e,["prefixCls","className","rootClassName","block","options","size","style","vertical","shape","name"]),{getPrefixCls:v,direction:M,className:C,style:E}=n.useComponentConfig("segmented"),f=v("segmented",a),[l,N,V]=je(f),x=n.useSize(b),c=o.useMemo(()=>h.map(O=>{if($e(O)){const{icon:D,label:H}=O,A=k(O,["icon","label"]);return Object.assign(Object.assign({},A),{label:o.createElement(o.Fragment,null,o.createElement("span",{className:`${f}-item-icon`},D),H&&o.createElement("span",null,H))})}return O}),[h,f]),I=n.cn(r,s,C,{[`${f}-block`]:p,[`${f}-sm`]:x==="small",[`${f}-lg`]:x==="large",[`${f}-vertical`]:d,[`${f}-shape-${$}`]:$==="round"},N,V),y=Object.assign(Object.assign({},E),S);return l(o.createElement(pe,Object.assign({},R,{name:w,className:I,style:y,options:c,ref:t,prefixCls:f,direction:M,vertical:d})))}),te=we;process.env.NODE_ENV!=="production"&&(te.displayName="Segmented");var Re={icon:{tag:"svg",attrs:{viewBox:"64 64 896 896",focusable:"false"},children:[{tag:"path",attrs:{d:"M758.2 839.1C851.8 765.9 912 651.9 912 523.9 912 303 733.5 124.3 512.6 124 291.4 123.7 112 302.8 112 523.9c0 125.2 57.5 236.9 147.6 310.2 3.5 2.8 8.6 2.2 11.4-1.3l39.4-50.5c2.7-3.4 2.1-8.3-1.2-11.1-8.1-6.6-15.9-13.7-23.4-21.2a318.64 318.64 0 01-68.6-101.7C200.4 609 192 567.1 192 523.9s8.4-85.1 25.1-124.5c16.1-38.1 39.2-72.3 68.6-101.7 29.4-29.4 63.6-52.5 101.7-68.6C426.9 212.4 468.8 204 512 204s85.1 8.4 124.5 25.1c38.1 16.1 72.3 39.2 101.7 68.6 29.4 29.4 52.5 63.6 68.6 101.7 16.7 39.4 25.1 81.3 25.1 124.5s-8.4 85.1-25.1 124.5a318.64 318.64 0 01-68.6 101.7c-9.3 9.3-19.1 18-29.3 26L668.2 724a8 8 0 00-14.1 3l-39.6 162.2c-1.2 5 2.6 9.9 7.7 9.9l167 .8c6.7 0 10.5-7.7 6.3-12.9l-37.3-47.9z"}}]},name:"redo",theme:"outlined"};function W(){return W=Object.assign?Object.assign.bind():function(e){for(var t=1;t<arguments.length;t++){var i=arguments[t];for(var a in i)Object.prototype.hasOwnProperty.call(i,a)&&(e[a]=i[a])}return e},W.apply(this,arguments)}const Ce=(e,t)=>o.createElement(n.Icon,W({},e,{ref:t,icon:Re})),ne=o.forwardRef(Ce);process.env.NODE_ENV!=="production"&&(ne.displayName="RedoOutlined");const Oe=({datePickerComponent:e,searchText:t,noDateText:i,emptyText:a,searchSelect:r,radioOptions:s,searchOptions:p,searchType:h,textSearchValue:b="",dateSearchValue:S,numberSearchValue:d,multiselectSearchValue:$,multiselectOptions:w,onChangeSearch:R,onChangeTextSearch:v,onChangeRadioSearch:M,onChangeDateSearch:C,onChangeNumberSearch:E,onChangeMultiselectSearch:f})=>{const[l,N]=K.useState(b),{token:{borderRadius:V,colorBgBase:x,paddingXXS:c}}=n.theme.useToken(),{isMobileMaxWidth:I}=n.useMobileViewPort(),{isSmallMaxWidth:y}=n.useSmallViewPort(),O=K.useMemo(()=>y?2:I?5:15,[I,y]);n.useDebounce(()=>{v==null||v(l)},n.TIME.milliseconds.milliseconds500,[l]);const D=()=>{N("")},H=m=>{R(m),D()},A=m=>{N(m.target.value.replace(/"/g,""))},u=m=>{C==null||C(m)},P=m=>{!m&&m!==0||E==null||E(+m)};return n.jsxRuntimeExports.jsxs(n.Flex,{className:n.styles.flex,gap:"small",style:{padding:c,borderRadius:V,background:x},children:[n.jsxRuntimeExports.jsx(n.Select,{defaultValue:r,value:r,style:{width:120,minWidth:120},options:p,onChange:H}),{text:n.jsxRuntimeExports.jsx(n.Input,{placeholder:t,value:l,allowClear:!0,onChange:A}),radio:n.jsxRuntimeExports.jsx(te,{options:s,defaultValue:n.searchRadioDefaultValue,onChange:M}),date:K.createElement(e,{noDateText:i,currentValue:S??"",onChangeDate:u}),number:n.jsxRuntimeExports.jsx(n.BaseInputNumber,{emptyText:a,value:d,placeholder:t,min:0,max:2147483647,onChange:P}),multiselect:n.jsxRuntimeExports.jsx(n.Select,{className:n.styles.select,mode:"multiple",placeholder:t,maxTagCount:1,maxTagTextLength:O,showSearch:!1,allowClear:!0,options:w,value:$,onChange:f})}[h]]})},Ee=({sortTooltipText:e,updateDataText:t,refreshText:i,createText:a,createNewElementText:r,order:s,orderOptions:p,createButtonTooltip:h,searchProps:b,isCanCreate:S,isHiddenCreate:d,onCreate:$,onRefetch:w,onChangeOrder:R})=>n.jsxRuntimeExports.jsxs(n.Flex,{gap:"middle",justify:"space-between",wrap:"wrap",style:{marginBottom:n.THEME.OFFSET[1]},children:[n.jsxRuntimeExports.jsxs(n.Flex,{align:"center",gap:"middle",wrap:"wrap",children:[n.jsxRuntimeExports.jsx(Oe,{...b}),n.jsxRuntimeExports.jsx(n.Tooltip,{title:e,children:n.jsxRuntimeExports.jsx(n.Select,{className:n.styles.sort,value:s,options:p,onChange:R})})]}),n.jsxRuntimeExports.jsxs(n.Flex,{className:n.styles.buttonsContainer,gap:"small",align:"center",children:[w&&n.jsxRuntimeExports.jsx(n.Tooltip,{title:t,children:n.jsxRuntimeExports.jsx(n.Button,{className:n.styles.button,icon:n.jsxRuntimeExports.jsx(ne,{}),onClick:w,children:i})}),!d&&S&&n.jsxRuntimeExports.jsx(n.Tooltip,{title:h??r,children:n.jsxRuntimeExports.jsx(n.Button,{className:n.styles.button,type:"primary",icon:n.jsxRuntimeExports.jsx(n.RefIcon,{}),onClick:$,children:a})})]})]});exports.TableHead=Ee;
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const n=require("./index-n5OyW3Ln.cjs"),K=require("react");function me(e){const t=Object.create(null,{[Symbol.toStringTag]:{value:"Module"}});if(e){for(const i in e)if(i!=="default"){const a=Object.getOwnPropertyDescriptor(e,i);Object.defineProperty(t,i,a.get?a:{enumerable:!0,get:()=>e[i]})}}return t.default=e,Object.freeze(t)}const o=me(K);var J=function(t,i){if(!t)return null;var a={left:t.offsetLeft,right:t.parentElement.clientWidth-t.clientWidth-t.offsetLeft,width:t.clientWidth,top:t.offsetTop,bottom:t.parentElement.clientHeight-t.clientHeight-t.offsetTop,height:t.clientHeight};return i?{left:0,right:0,width:0,top:a.top,bottom:a.bottom,height:a.height}:{left:a.left,right:a.right,width:a.width,top:0,bottom:0,height:0}},T=function(t){return t!==void 0?"".concat(t,"px"):void 0};function fe(e){var t=e.prefixCls,i=e.containerRef,a=e.value,r=e.getValueIndex,s=e.motionName,p=e.onMotionStart,h=e.onMotionEnd,b=e.direction,S=e.vertical,d=S===void 0?!1:S,$=o.useRef(null),w=o.useState(a),R=n._slicedToArray(w,2),v=R[0],M=R[1],C=function(P){var m,B=r(P),_=(m=i.current)===null||m===void 0?void 0:m.querySelectorAll(".".concat(t,"-item"))[B];return(_==null?void 0:_.offsetParent)&&_},E=o.useState(null),f=n._slicedToArray(E,2),l=f[0],N=f[1],V=o.useState(null),x=n._slicedToArray(V,2),c=x[0],I=x[1];n.useLayoutEffect(function(){if(v!==a){var u=C(v),P=C(a),m=J(u,d),B=J(P,d);M(a),N(m),I(B),u&&P?p():h()}},[a]);var y=o.useMemo(function(){if(d){var u;return T((u=l==null?void 0:l.top)!==null&&u!==void 0?u:0)}return T(b==="rtl"?-(l==null?void 0:l.right):l==null?void 0:l.left)},[d,b,l]),O=o.useMemo(function(){if(d){var u;return T((u=c==null?void 0:c.top)!==null&&u!==void 0?u:0)}return T(b==="rtl"?-(c==null?void 0:c.right):c==null?void 0:c.left)},[d,b,c]),D=function(){return d?{transform:"translateY(var(--thumb-start-top))",height:"var(--thumb-start-height)"}:{transform:"translateX(var(--thumb-start-left))",width:"var(--thumb-start-width)"}},H=function(){return d?{transform:"translateY(var(--thumb-active-top))",height:"var(--thumb-active-height)"}:{transform:"translateX(var(--thumb-active-left))",width:"var(--thumb-active-width)"}},A=function(){N(null),I(null),h()};return!l||!c?null:o.createElement(n.CSSMotion,{visible:!0,motionName:s,motionAppear:!0,onAppearStart:D,onAppearActive:H,onVisibleChanged:A},function(u,P){var m=u.className,B=u.style,_=n._objectSpread2(n._objectSpread2({},B),{},{"--thumb-start-left":y,"--thumb-start-width":T(l==null?void 0:l.width),"--thumb-active-left":O,"--thumb-active-width":T(c==null?void 0:c.width),"--thumb-start-top":y,"--thumb-start-height":T(l==null?void 0:l.height),"--thumb-active-top":O,"--thumb-active-height":T(c==null?void 0:c.height)}),F={ref:n.composeRef($,P),style:_,className:n.cn("".concat(t,"-thumb"),m)};return process.env.NODE_ENV==="test"&&(F["data-test-style"]=JSON.stringify(_)),o.createElement("div",F)})}var ve=["prefixCls","direction","vertical","options","disabled","defaultValue","value","name","onChange","className","motionName"];function ge(e){if(typeof e.title<"u")return e.title;if(n._typeof(e.label)!=="object"){var t;return(t=e.label)===null||t===void 0?void 0:t.toString()}}function he(e){return e.map(function(t){if(n._typeof(t)==="object"&&t!==null){var i=ge(t);return n._objectSpread2(n._objectSpread2({},t),{},{title:i})}return{label:t==null?void 0:t.toString(),title:t==null?void 0:t.toString(),value:t}})}var be=function(t){var i=t.prefixCls,a=t.className,r=t.disabled,s=t.checked,p=t.label,h=t.title,b=t.value,S=t.name,d=t.onChange,$=t.onFocus,w=t.onBlur,R=t.onKeyDown,v=t.onKeyUp,M=t.onMouseDown,C=function(f){r||d(f,b)};return o.createElement("label",{className:n.cn(a,n._defineProperty({},"".concat(i,"-item-disabled"),r)),onMouseDown:M},o.createElement("input",{name:S,className:"".concat(i,"-item-input"),type:"radio",disabled:r,checked:s,onChange:C,onFocus:$,onBlur:w,onKeyDown:R,onKeyUp:v}),o.createElement("div",{className:"".concat(i,"-item-label"),title:h,"aria-selected":s},p))},ee=o.forwardRef(function(e,t){var i,a,r=e.prefixCls,s=r===void 0?"rc-segmented":r,p=e.direction,h=e.vertical,b=e.options,S=b===void 0?[]:b,d=e.disabled,$=e.defaultValue,w=e.value,R=e.name,v=e.onChange,M=e.className,C=M===void 0?"":M,E=e.motionName,f=E===void 0?"thumb-motion":E,l=n._objectWithoutProperties(e,ve),N=o.useRef(null),V=o.useMemo(function(){return n.composeRef(N,t)},[N,t]),x=o.useMemo(function(){return he(S)},[S]),c=n.useMergedState((i=x[0])===null||i===void 0?void 0:i.value,{value:w,defaultValue:$}),I=n._slicedToArray(c,2),y=I[0],O=I[1],D=o.useState(!1),H=n._slicedToArray(D,2),A=H[0],u=H[1],P=function(j,z){O(z),v==null||v(z)},m=n.omit(l,["children"]),B=o.useState(!1),_=n._slicedToArray(B,2),F=_[0],X=_[1],ae=o.useState(!1),q=n._slicedToArray(ae,2),ie=q[0],U=q[1],oe=function(){U(!0)},re=function(){U(!1)},le=function(){X(!1)},se=function(j){j.key==="Tab"&&X(!0)},G=function(j){var z=x.findIndex(function(de){return de.value===y}),Y=x.length,ue=(z+j+Y)%Y,L=x[ue];L&&(O(L.value),v==null||v(L.value))},ce=function(j){switch(j.key){case"ArrowLeft":case"ArrowUp":G(-1);break;case"ArrowRight":case"ArrowDown":G(1);break}};return o.createElement("div",n._extends({role:"radiogroup","aria-label":"segmented control",tabIndex:d?void 0:0},m,{className:n.cn(s,(a={},n._defineProperty(a,"".concat(s,"-rtl"),p==="rtl"),n._defineProperty(a,"".concat(s,"-disabled"),d),n._defineProperty(a,"".concat(s,"-vertical"),h),a),C),ref:V}),o.createElement("div",{className:"".concat(s,"-group")},o.createElement(fe,{vertical:h,prefixCls:s,value:y,containerRef:N,motionName:"".concat(s,"-").concat(f),direction:p,getValueIndex:function(j){return x.findIndex(function(z){return z.value===j})},onMotionStart:function(){u(!0)},onMotionEnd:function(){u(!1)}}),x.map(function(g){var j;return o.createElement(be,n._extends({},g,{name:R,key:g.value,prefixCls:s,className:n.cn(g.className,"".concat(s,"-item"),(j={},n._defineProperty(j,"".concat(s,"-item-selected"),g.value===y&&!A),n._defineProperty(j,"".concat(s,"-item-focused"),ie&&F&&g.value===y),j)),checked:g.value===y,onChange:P,onFocus:oe,onBlur:re,onKeyDown:ce,onKeyUp:se,onMouseDown:le,disabled:!!d||!!g.disabled}))})))});process.env.NODE_ENV!=="production"&&(ee.displayName="Segmented");var pe=ee;function Z(e,t){return{[`${e}, ${e}:hover, ${e}:focus`]:{color:t.colorTextDisabled,cursor:"not-allowed"}}}function Q(e){return{backgroundColor:e.itemSelectedBg,boxShadow:e.boxShadowTertiary}}const xe=Object.assign({overflow:"hidden"},n.textEllipsis),Se=e=>{const{componentCls:t}=e,i=e.calc(e.controlHeight).sub(e.calc(e.trackPadding).mul(2)).equal(),a=e.calc(e.controlHeightLG).sub(e.calc(e.trackPadding).mul(2)).equal(),r=e.calc(e.controlHeightSM).sub(e.calc(e.trackPadding).mul(2)).equal();return{[t]:Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign({},n.resetComponent(e)),{display:"inline-block",padding:e.trackPadding,color:e.itemColor,background:e.trackBg,borderRadius:e.borderRadius,transition:`all ${e.motionDurationMid} ${e.motionEaseInOut}`}),n.genFocusStyle(e)),{[`${t}-group`]:{position:"relative",display:"flex",alignItems:"stretch",justifyItems:"flex-start",flexDirection:"row",width:"100%"},[`&${t}-rtl`]:{direction:"rtl"},[`&${t}-vertical`]:{[`${t}-group`]:{flexDirection:"column"},[`${t}-thumb`]:{width:"100%",height:0,padding:`0 ${n.unit(e.paddingXXS)}`}},[`&${t}-block`]:{display:"flex"},[`&${t}-block ${t}-item`]:{flex:1,minWidth:0},[`${t}-item`]:{position:"relative",textAlign:"center",cursor:"pointer",transition:`color ${e.motionDurationMid} ${e.motionEaseInOut}`,borderRadius:e.borderRadiusSM,transform:"translateZ(0)","&-selected":Object.assign(Object.assign({},Q(e)),{color:e.itemSelectedColor}),"&-focused":Object.assign({},n.genFocusOutline(e)),"&::after":{content:'""',position:"absolute",zIndex:-1,width:"100%",height:"100%",top:0,insetInlineStart:0,borderRadius:"inherit",opacity:0,transition:`opacity ${e.motionDurationMid}`,pointerEvents:"none"},[`&:hover:not(${t}-item-selected):not(${t}-item-disabled)`]:{color:e.itemHoverColor,"&::after":{opacity:1,backgroundColor:e.itemHoverBg}},[`&:active:not(${t}-item-selected):not(${t}-item-disabled)`]:{color:e.itemHoverColor,"&::after":{opacity:1,backgroundColor:e.itemActiveBg}},"&-label":Object.assign({minHeight:i,lineHeight:n.unit(i),padding:`0 ${n.unit(e.segmentedPaddingHorizontal)}`},xe),"&-icon + *":{marginInlineStart:e.calc(e.marginSM).div(2).equal()},"&-input":{position:"absolute",insetBlockStart:0,insetInlineStart:0,width:0,height:0,opacity:0,pointerEvents:"none"}},[`${t}-thumb`]:Object.assign(Object.assign({},Q(e)),{position:"absolute",insetBlockStart:0,insetInlineStart:0,width:0,height:"100%",padding:`${n.unit(e.paddingXXS)} 0`,borderRadius:e.borderRadiusSM,transition:`transform ${e.motionDurationSlow} ${e.motionEaseInOut}, height ${e.motionDurationSlow} ${e.motionEaseInOut}`,[`& ~ ${t}-item:not(${t}-item-selected):not(${t}-item-disabled)::after`]:{backgroundColor:"transparent"}}),[`&${t}-lg`]:{borderRadius:e.borderRadiusLG,[`${t}-item-label`]:{minHeight:a,lineHeight:n.unit(a),padding:`0 ${n.unit(e.segmentedPaddingHorizontal)}`,fontSize:e.fontSizeLG},[`${t}-item, ${t}-thumb`]:{borderRadius:e.borderRadius}},[`&${t}-sm`]:{borderRadius:e.borderRadiusSM,[`${t}-item-label`]:{minHeight:r,lineHeight:n.unit(r),padding:`0 ${n.unit(e.segmentedPaddingHorizontalSM)}`},[`${t}-item, ${t}-thumb`]:{borderRadius:e.borderRadiusXS}}}),Z(`&-disabled ${t}-item`,e)),Z(`${t}-item-disabled`,e)),{[`${t}-thumb-motion-appear-active`]:{transition:`transform ${e.motionDurationSlow} ${e.motionEaseInOut}, width ${e.motionDurationSlow} ${e.motionEaseInOut}`,willChange:"transform, width"},[`&${t}-shape-round`]:{borderRadius:9999,[`${t}-item, ${t}-thumb`]:{borderRadius:9999}}})}},ye=e=>{const{colorTextLabel:t,colorText:i,colorFillSecondary:a,colorBgElevated:r,colorFill:s,lineWidthBold:p,colorBgLayout:h}=e;return{trackPadding:p,trackBg:h,itemColor:t,itemHoverColor:i,itemHoverBg:a,itemSelectedBg:r,itemActiveBg:s,itemSelectedColor:i}},je=n.genStyleHooks("Segmented",e=>{const{lineWidth:t,calc:i}=e,a=n.merge(e,{segmentedPaddingHorizontal:i(e.controlPaddingHorizontal).sub(t).equal(),segmentedPaddingHorizontalSM:i(e.controlPaddingHorizontalSM).sub(t).equal()});return[Se(a)]},ye);var k=function(e,t){var i={};for(var a in e)Object.prototype.hasOwnProperty.call(e,a)&&t.indexOf(a)<0&&(i[a]=e[a]);if(e!=null&&typeof Object.getOwnPropertySymbols=="function")for(var r=0,a=Object.getOwnPropertySymbols(e);r<a.length;r++)t.indexOf(a[r])<0&&Object.prototype.propertyIsEnumerable.call(e,a[r])&&(i[a[r]]=e[a[r]]);return i};function $e(e){return typeof e=="object"&&!!(e!=null&&e.icon)}const we=o.forwardRef((e,t)=>{const i=n.useId(),{prefixCls:a,className:r,rootClassName:s,block:p,options:h=[],size:b="middle",style:S,vertical:d,shape:$="default",name:w=i}=e,R=k(e,["prefixCls","className","rootClassName","block","options","size","style","vertical","shape","name"]),{getPrefixCls:v,direction:M,className:C,style:E}=n.useComponentConfig("segmented"),f=v("segmented",a),[l,N,V]=je(f),x=n.useSize(b),c=o.useMemo(()=>h.map(O=>{if($e(O)){const{icon:D,label:H}=O,A=k(O,["icon","label"]);return Object.assign(Object.assign({},A),{label:o.createElement(o.Fragment,null,o.createElement("span",{className:`${f}-item-icon`},D),H&&o.createElement("span",null,H))})}return O}),[h,f]),I=n.cn(r,s,C,{[`${f}-block`]:p,[`${f}-sm`]:x==="small",[`${f}-lg`]:x==="large",[`${f}-vertical`]:d,[`${f}-shape-${$}`]:$==="round"},N,V),y=Object.assign(Object.assign({},E),S);return l(o.createElement(pe,Object.assign({},R,{name:w,className:I,style:y,options:c,ref:t,prefixCls:f,direction:M,vertical:d})))}),te=we;process.env.NODE_ENV!=="production"&&(te.displayName="Segmented");var Re={icon:{tag:"svg",attrs:{viewBox:"64 64 896 896",focusable:"false"},children:[{tag:"path",attrs:{d:"M758.2 839.1C851.8 765.9 912 651.9 912 523.9 912 303 733.5 124.3 512.6 124 291.4 123.7 112 302.8 112 523.9c0 125.2 57.5 236.9 147.6 310.2 3.5 2.8 8.6 2.2 11.4-1.3l39.4-50.5c2.7-3.4 2.1-8.3-1.2-11.1-8.1-6.6-15.9-13.7-23.4-21.2a318.64 318.64 0 01-68.6-101.7C200.4 609 192 567.1 192 523.9s8.4-85.1 25.1-124.5c16.1-38.1 39.2-72.3 68.6-101.7 29.4-29.4 63.6-52.5 101.7-68.6C426.9 212.4 468.8 204 512 204s85.1 8.4 124.5 25.1c38.1 16.1 72.3 39.2 101.7 68.6 29.4 29.4 52.5 63.6 68.6 101.7 16.7 39.4 25.1 81.3 25.1 124.5s-8.4 85.1-25.1 124.5a318.64 318.64 0 01-68.6 101.7c-9.3 9.3-19.1 18-29.3 26L668.2 724a8 8 0 00-14.1 3l-39.6 162.2c-1.2 5 2.6 9.9 7.7 9.9l167 .8c6.7 0 10.5-7.7 6.3-12.9l-37.3-47.9z"}}]},name:"redo",theme:"outlined"};function W(){return W=Object.assign?Object.assign.bind():function(e){for(var t=1;t<arguments.length;t++){var i=arguments[t];for(var a in i)Object.prototype.hasOwnProperty.call(i,a)&&(e[a]=i[a])}return e},W.apply(this,arguments)}const Ce=(e,t)=>o.createElement(n.Icon,W({},e,{ref:t,icon:Re})),ne=o.forwardRef(Ce);process.env.NODE_ENV!=="production"&&(ne.displayName="RedoOutlined");const Oe=({datePickerComponent:e,searchText:t,noDateText:i,emptyText:a,searchSelect:r,radioOptions:s,searchOptions:p,searchType:h,textSearchValue:b="",dateSearchValue:S,numberSearchValue:d,multiselectSearchValue:$,multiselectOptions:w,onChangeSearch:R,onChangeTextSearch:v,onChangeRadioSearch:M,onChangeDateSearch:C,onChangeNumberSearch:E,onChangeMultiselectSearch:f})=>{const[l,N]=K.useState(b),{token:{borderRadius:V,colorBgBase:x,paddingXXS:c}}=n.theme.useToken(),{isMobileMaxWidth:I}=n.useMobileViewPort(),{isSmallMaxWidth:y}=n.useSmallViewPort(),O=K.useMemo(()=>y?2:I?5:15,[I,y]);n.useDebounce(()=>{v==null||v(l)},n.TIME.milliseconds.milliseconds500,[l]);const D=()=>{N("")},H=m=>{R(m),D()},A=m=>{N(m.target.value.replace(/"/g,""))},u=m=>{C==null||C(m)},P=m=>{!m&&m!==0||E==null||E(+m)};return n.jsxRuntimeExports.jsxs(n.Flex,{className:n.styles.flex,gap:"small",style:{padding:c,borderRadius:V,background:x},children:[n.jsxRuntimeExports.jsx(n.Select,{defaultValue:r,value:r,style:{width:120,minWidth:120},options:p,onChange:H}),{text:n.jsxRuntimeExports.jsx(n.Input,{placeholder:t,value:l,allowClear:!0,onChange:A}),radio:n.jsxRuntimeExports.jsx(te,{options:s,defaultValue:n.searchRadioDefaultValue,onChange:M}),date:K.createElement(e,{noDateText:i,currentValue:S??"",onChangeDate:u}),number:n.jsxRuntimeExports.jsx(n.BaseInputNumber,{emptyText:a,value:d,placeholder:t,min:0,max:2147483647,onChange:P}),multiselect:n.jsxRuntimeExports.jsx(n.Select,{className:n.styles.select,mode:"multiple",placeholder:t,maxTagCount:1,maxTagTextLength:O,showSearch:!1,allowClear:!0,options:w,value:$,onChange:f})}[h]]})},Ee=({sortTooltipText:e,updateDataText:t,refreshText:i,createText:a,createNewElementText:r,order:s,orderOptions:p,createButtonTooltip:h,searchProps:b,isCanCreate:S,isHiddenCreate:d,onCreate:$,onRefetch:w,onChangeOrder:R})=>n.jsxRuntimeExports.jsxs(n.Flex,{gap:"middle",justify:"space-between",wrap:"wrap",style:{marginBottom:n.THEME.OFFSET[1]},children:[n.jsxRuntimeExports.jsxs(n.Flex,{align:"center",gap:"middle",wrap:"wrap",children:[n.jsxRuntimeExports.jsx(Oe,{...b}),n.jsxRuntimeExports.jsx(n.Tooltip,{title:e,children:n.jsxRuntimeExports.jsx(n.Select,{className:n.styles.sort,value:s,options:p,onChange:R})})]}),n.jsxRuntimeExports.jsxs(n.Flex,{className:n.styles.buttonsContainer,gap:"small",align:"center",children:[w&&n.jsxRuntimeExports.jsx(n.Tooltip,{title:t,children:n.jsxRuntimeExports.jsx(n.Button,{className:n.styles.button,icon:n.jsxRuntimeExports.jsx(ne,{}),onClick:w,children:i})}),!d&&S&&n.jsxRuntimeExports.jsx(n.Tooltip,{title:h??r,children:n.jsxRuntimeExports.jsx(n.Button,{className:n.styles.button,type:"primary",icon:n.jsxRuntimeExports.jsx(n.RefIcon,{}),onClick:$,children:a})})]})]});exports.TableHead=Ee;
package/package.json CHANGED
@@ -1,13 +1,21 @@
1
1
  {
2
2
  "name": "denwa-react-shared",
3
3
  "private": false,
4
- "version": "1.0.87",
4
+ "version": "1.0.89",
5
5
  "type": "module",
6
6
  "author": "Denwa",
7
+ "keywords": [
8
+ "react",
9
+ "shared",
10
+ "admin",
11
+ "tanstack-intent"
12
+ ],
7
13
  "main": "dist/denwa-react-shared.umd.js",
8
14
  "module": "dist/denwa-react-shared.es.js",
9
15
  "files": [
10
- "dist"
16
+ "dist",
17
+ "skills",
18
+ "!skills/_artifacts"
11
19
  ],
12
20
  "types": "dist/index.d.ts",
13
21
  "exports": {
@@ -63,6 +71,7 @@
63
71
  "@types/react": "^19.1.6",
64
72
  "@types/react-dom": "^19.1.6",
65
73
  "@types/validator": "^13.15.1",
74
+ "@tanstack/intent": "latest",
66
75
  "@vitejs/plugin-react-swc": "^3.10.1",
67
76
  "autoprefixer": "^10.4.21",
68
77
  "eslint": "^9.28.0",
@@ -0,0 +1,121 @@
1
+ ---
2
+ name: admin-forms
3
+ description: >
4
+ Implement entity editor forms using DrawerForm and specialized inputs.
5
+ Covers form submission, language switching, and integration with
6
+ AdminTable actions.
7
+ type: framework
8
+ library: denwa-react-shared
9
+ framework: react
10
+ library_version: "1.0.88"
11
+ requires:
12
+ - session-auth
13
+ ---
14
+
15
+ # Drawer Forms & Inputs
16
+
17
+ Most entity management in the admin panel happens within `Drawer` panels using `BaseDrawerForm`. This component standardizes the appearance of save buttons and multi-language controls.
18
+
19
+ ## Setup
20
+
21
+ ```tsx
22
+ import { BaseDrawerForm, AdminDrawerFormProps } from 'denwa-react-shared';
23
+
24
+ const UserForm = ({ id, action, onClose, onRefetch }: AdminDrawerFormProps<'create' | 'update' | 'read'>) => {
25
+ const { control, handleSubmit } = useForm();
26
+
27
+ const isReadOnly = action === 'read';
28
+
29
+ return (
30
+ <BaseDrawerForm
31
+ saveText="Сохранить"
32
+ submitButtonText={action === 'create' ? 'Создать' : 'Обновить'}
33
+ isVisibleSubmit={!isReadOnly}
34
+ onSubmitClick={handleSubmit(onSave)}
35
+ >
36
+ <Controller
37
+ name="name"
38
+ control={control}
39
+ render={({ field }) => <Input {...field} disabled={isReadOnly} />}
40
+ />
41
+ {/* ... form content */}
42
+ </BaseDrawerForm>
43
+ );
44
+ };
45
+ ```
46
+
47
+ ## Core Patterns
48
+
49
+ ### Language Switching
50
+ If the entity supports multiple languages, enable `isVisibleLanguage` and provide `languagesData`.
51
+
52
+ ```tsx
53
+ <BaseDrawerForm
54
+ isVisibleLanguage
55
+ language={currentLang}
56
+ languagesData={[
57
+ { label: 'Русский', value: 'ru' },
58
+ { label: 'English', value: 'en' },
59
+ ]}
60
+ onChangeLang={(lang) => setLang(lang)}
61
+ // Optional: Bulk translation button
62
+ isVisibleLanguageButton
63
+ translateAllText="Перевести все"
64
+ onTranslateAllClick={handleTranslate}
65
+ >
66
+ {/* ... fields */}
67
+ </BaseDrawerForm>
68
+ ```
69
+
70
+ ### Integration with AdminTable
71
+ The `AdminTable` orchestration passes `id`, `action`, `onClose`, and `onRefetch` to the `drawerContent` component.
72
+
73
+ ```tsx
74
+ // In AdminTable:
75
+ <AdminTable
76
+ drawerContent={UserForm}
77
+ readAction="read"
78
+ createAction="create"
79
+ updateAction="update"
80
+ // ...
81
+ />
82
+ ```
83
+
84
+ ## Common Mistakes
85
+
86
+ ### MEDIUM Using raw antd Form
87
+ Wrong:
88
+ ```tsx
89
+ import { Form } from 'antd';
90
+ return <Form>{children}</Form>;
91
+ ```
92
+ Correct:
93
+ ```tsx
94
+ import { BaseDrawerForm } from 'denwa-react-shared';
95
+ return <BaseDrawerForm>{children}</BaseDrawerForm>;
96
+ ```
97
+ `BaseDrawerForm` wraps `antd` Form but adds standardized footer buttons and integrated logic for language switching and submission loading states.
98
+
99
+ Source: maintainer interview
100
+
101
+ ### HIGH Mismanaging "read" action state
102
+ Wrong:
103
+ ```tsx
104
+ const UserForm = ({ action }) => {
105
+ return <BaseDrawerForm>{/* inputs are always enabled */}</BaseDrawerForm>;
106
+ };
107
+ ```
108
+ Correct:
109
+ ```tsx
110
+ const UserForm = ({ action }) => {
111
+ const isReadOnly = action === 'read';
112
+ return (
113
+ <BaseDrawerForm isVisibleSubmit={!isReadOnly}>
114
+ <Input disabled={isReadOnly} />
115
+ </BaseDrawerForm>
116
+ );
117
+ };
118
+ ```
119
+ When `action` is 'read', the form should visually hide the submit button and disable all input fields.
120
+
121
+ Source: src/shared/ui/admin-table/index.tsx
@@ -0,0 +1,153 @@
1
+ ---
2
+ name: admin-table
3
+ description: >
4
+ Implement complex data tables using AdminTable and useFetchTableData.
5
+ Covers columns configuration, server-side filtering, sorting,
6
+ and search state mapping.
7
+ type: framework
8
+ library: denwa-react-shared
9
+ framework: react
10
+ library_version: "1.0.88"
11
+ requires:
12
+ - session-auth
13
+ sources:
14
+ - "Denwa799/react-shared:src/shared/ui/admin-table/index.tsx"
15
+ - "Denwa799/react-shared:src/shared/lib/hooks/use-fetch-table-data.ts"
16
+ ---
17
+
18
+ # Admin Table & Data Fetching
19
+
20
+ The `AdminTable` component is the centerpiece for building resource lists. It works in conjunction with `useFetchTableData` to map UI states (search, sort, page) to API filters.
21
+
22
+ ## Setup
23
+
24
+ ```tsx
25
+ import { AdminTable, useFetchTableData } from 'denwa-react-shared';
26
+ import { ColumnsType } from 'antd/es/table';
27
+
28
+ const UsersPage = () => {
29
+ // 1. Setup state setters (usually from nuqs or local state)
30
+ const [order, setOrder] = useState('createdAtDesc');
31
+ const [search, setSearch] = useState('');
32
+
33
+ // 2. Use hook to get mapped filters/sort for API
34
+ const { filter, sort, onChangeOrder, ...searchHandlers } = useFetchTableData({
35
+ order,
36
+ search,
37
+ onSetOrder: setOrder,
38
+ onSetSearch: setSearch,
39
+ // ... other setters for pagination, radio, date search
40
+ sortFields: [{ key: 'createdAtDesc', field: 'createdAt', order: 'desc' }],
41
+ searchFields: ['name', 'email'],
42
+ // ... field configuration
43
+ });
44
+
45
+ // 3. Render table
46
+ return (
47
+ <AdminTable
48
+ tableData={data}
49
+ columns={columns}
50
+ order={order}
51
+ onChangeOrder={onChangeOrder}
52
+ searchProps={{
53
+ ...searchHandlers,
54
+ // ... text labels
55
+ }}
56
+ // ... actions and text props
57
+ />
58
+ );
59
+ };
60
+ ```
61
+
62
+ ## Core Patterns
63
+
64
+ ### Configuring Search and Filters
65
+ `searchProps` expects a `TableSearchProps` object. Ensure you provide the `datePickerComponent` and all required handlers from `useFetchTableData`.
66
+
67
+ ```tsx
68
+ <AdminTable
69
+ searchProps={{
70
+ datePickerComponent: BaseDatePicker,
71
+ searchText: 'Поиск',
72
+ noDateText: 'Нет даты',
73
+ emptyText: 'Ничего не найдено',
74
+ searchSelect: currentSearchField,
75
+ radioOptions: [{ label: 'Все', value: 'all' }],
76
+ searchOptions: [{ label: 'Имя', value: 'name' }],
77
+ searchType: 'text',
78
+ onChangeSearch: handleFieldChange,
79
+ onChangeTextSearch: handleTextChange,
80
+ }}
81
+ // ...
82
+ />
83
+ ```
84
+
85
+ ### Server-Side Pagination
86
+ The table expects `serverPagination` prop of type `IPaginate`.
87
+
88
+ ```tsx
89
+ <AdminTable
90
+ serverPagination={{
91
+ total: totalItems,
92
+ page: currentPage,
93
+ limit: pageSize,
94
+ }}
95
+ onSetPaginate={(page, limit) => {
96
+ setPage(page);
97
+ setLimit(limit);
98
+ }}
99
+ />
100
+ ```
101
+
102
+ ## Common Mistakes
103
+
104
+ ### HIGH Hallucinating internal state management
105
+ Wrong:
106
+ ```tsx
107
+ // Trying to use useFetchTableData without passing external setters
108
+ const tableInfo = useFetchTableData({
109
+ order: 'desc', // Static value
110
+ // Missing onSetOrder, onSetSearch, etc.
111
+ });
112
+ ```
113
+ Correct:
114
+ ```tsx
115
+ const [order, setOrder] = useState('desc');
116
+ const tableInfo = useFetchTableData({
117
+ order,
118
+ onSetOrder: setOrder,
119
+ // Must provide setters to allow the hook to update external state
120
+ });
121
+ ```
122
+ The hook acts as a logic mapper and relies on external state (like `nuqs` or `useState`) to persist changes.
123
+
124
+ Source: maintainer interview
125
+
126
+ ### HIGH Passings wrong pagination format
127
+ Wrong:
128
+ ```tsx
129
+ // Using antd internal pagination object
130
+ <AdminTable serverPagination={{ current: 1, pageSize: 10 }} />
131
+ ```
132
+ Correct:
133
+ ```tsx
134
+ <AdminTable serverPagination={{ page: 1, limit: 10, total: 100 }} />
135
+ ```
136
+ `AdminTable` expects a custom `IPaginate` shape, not the standard Ant Design pagination object.
137
+
138
+ Source: src/shared/ui/admin-table/types.ts
139
+
140
+ ### MEDIUM Using raw antd Table
141
+ Wrong:
142
+ ```tsx
143
+ import { Table } from 'antd';
144
+ return <Table dataSource={data} columns={columns} />;
145
+ ```
146
+ Correct:
147
+ ```tsx
148
+ import { AdminTable } from 'denwa-react-shared';
149
+ return <AdminTable tableData={data} columns={columns} ... />;
150
+ ```
151
+ Using raw `Table` loses integrated search UI, standardized skeletons, and the "Drawer Form" orchestration.
152
+
153
+ Source: maintainer interview
@@ -0,0 +1,65 @@
1
+ ---
2
+ name: material-map
3
+ description: >
4
+ Integrate Yandex Maps for coordinate selection. Covers map initialization,
5
+ setting markers, and coordinate synchronization.
6
+ type: framework
7
+ library: denwa-react-shared
8
+ framework: react
9
+ library_version: "1.0.88"
10
+ requires:
11
+ - session-auth
12
+ sources:
13
+ - "Denwa799/react-shared:src/shared/ui/material-map/index.tsx"
14
+ ---
15
+
16
+ # Yandex Maps Integration
17
+
18
+ `BaseMaterialMap` uses Yandex Maps to allow users to select geographic coordinates. It requires a Yandex Maps API key and provides a simple interface for single-point selection.
19
+
20
+ ## Setup
21
+
22
+ ```tsx
23
+ import { BaseMaterialMap } from 'denwa-react-shared';
24
+
25
+ const LocationPicker = () => {
26
+ return (
27
+ <BaseMaterialMap
28
+ apiKey="your-yandex-api-key"
29
+ value={{ lat: 55.751244, lng: 37.618423 }}
30
+ onChange={(coords) => setLocation(coords)}
31
+ height={400}
32
+ zoom={10}
33
+ noDataText="Координаты не выбраны"
34
+ />
35
+ );
36
+ };
37
+ ```
38
+
39
+ ## Core Patterns
40
+
41
+ ### Manual Coordinate Entry
42
+ The component displays the current coordinates in inputs. Users can either click on the map or type values manually. Always ensure `onChange` is provided to capture changes from both sources.
43
+
44
+ ### Custom Height and Styling
45
+ The map container should be constrained by the `height` prop. It defaults to `100%` width of the parent container.
46
+
47
+ ## Common Mistakes
48
+
49
+ ### CRITICAL Missing API Key
50
+ Wrong:
51
+ ```tsx
52
+ <BaseMaterialMap value={coords} />
53
+ ```
54
+ Correct:
55
+ ```tsx
56
+ <BaseMaterialMap apiKey={import.meta.env.VITE_YAMAP_KEY} value={coords} />
57
+ ```
58
+ The map uses `@iminside/react-yandex-maps` internally. If the `apiKey` is missing or invalid, the map will fail to load or will show a "Demo mode" watermark.
59
+
60
+ Source: src/shared/ui/material-map/index.tsx
61
+
62
+ ### HIGH Forgetting default center for empty values
63
+ If the `value` is undefined, the map might center on a default (often 0,0) or fail. Always provide a fallback `defaultCenter` or check for existence.
64
+
65
+ Source: maintainer interview
@@ -0,0 +1,107 @@
1
+ ---
2
+ name: media-management
3
+ description: >
4
+ Handle single/multiple image uploads and file attachments.
5
+ Covers drag-and-drop sorting, temporary upload patterns,
6
+ and media deletion.
7
+ type: framework
8
+ library: denwa-react-shared
9
+ framework: react
10
+ library_version: "1.0.88"
11
+ requires:
12
+ - session-auth
13
+ sources:
14
+ - "Denwa799/react-shared:src/shared/ui/image-upload/base-image-upload.tsx"
15
+ - "Denwa799/react-shared:src/shared/ui/file-upload/file-upload.tsx"
16
+ ---
17
+
18
+ # Media & File Management
19
+
20
+ The library provides `BaseImageUpload` for image galleries and `FileUpload` for general documents. Both rely on a two-step process: uploading to a temporary location first, then associating the path with the entity.
21
+
22
+ ## Setup
23
+
24
+ ### Image Upload with Sorting
25
+ ```tsx
26
+ import { BaseImageUpload, TAdminImage } from 'denwa-react-shared';
27
+
28
+ const Gallery = () => {
29
+ return (
30
+ <BaseImageUpload
31
+ isMultiple
32
+ label="Галерея"
33
+ images={images}
34
+ onUpdateTempImage={handleTempUpload}
35
+ onUpdateItems={handleReorder}
36
+ onUpdateDeleteItems={handleDelete}
37
+ />
38
+ );
39
+ };
40
+ ```
41
+
42
+ ## Core Patterns
43
+
44
+ ### Two-Step Upload Process
45
+ Components emit native File objects. You must upload these to a temporary storage API and return the resulting path to the component's state.
46
+
47
+ ```tsx
48
+ const handleTempUpload = async (file: File) => {
49
+ const formData = new FormData();
50
+ formData.append('file', file);
51
+
52
+ const response = await api.upload(formData); // Your API
53
+ return response.path; // e.g. "/temp/random-id.png"
54
+ };
55
+ ```
56
+
57
+ ### File Attachments
58
+ For non-image files, use `FileUpload`. It supports single or multiple files with size/extension limits.
59
+
60
+ ```tsx
61
+ import { FileUpload } from 'denwa-react-shared';
62
+
63
+ <FileUpload
64
+ label="Документ"
65
+ onUpload={handleFileUpload}
66
+ onRemove={handleFileRemove}
67
+ items={data.files}
68
+ isMultiple={false}
69
+ />
70
+ ```
71
+
72
+ ## Common Mistakes
73
+
74
+ ### CRITICAL Forgetting to handle reordering
75
+ Wrong:
76
+ ```tsx
77
+ // Only handling uploads
78
+ <BaseImageUpload onUpdateTempImage={upload} />
79
+ ```
80
+ Correct:
81
+ ```tsx
82
+ <BaseImageUpload
83
+ onUpdateTempImage={upload}
84
+ onUpdateItems={(newItems) => setImages(newItems)}
85
+ />
86
+ ```
87
+ If `onUpdateItems` is missing, drag-and-drop reordering will visually work but won't persist to state.
88
+
89
+ Source: src/shared/ui/image-upload/base-image-upload.tsx
90
+
91
+ ### HIGH Passing only URLs instead of Image objects
92
+ Wrong:
93
+ ```tsx
94
+ <BaseImageUpload images={["/image1.png"]} />
95
+ ```
96
+ Correct:
97
+ ```tsx
98
+ <BaseImageUpload images={[{ id: 1, path: "/image1.png" }]} />
99
+ ```
100
+ `BaseImageUpload` expects an array of objects containing `id` and `path`, not raw strings.
101
+
102
+ Source: src/shared/ui/image-upload/types.ts
103
+
104
+ ### MEDIUM Missing upload button due to limits
105
+ If the `limit` prop is reached, the "Upload" button disappears. Ensure you communicate this UI behavior or provide a way to delete items.
106
+
107
+ Source: src/shared/ui/image-upload/base-image-upload.tsx:55
@@ -0,0 +1,100 @@
1
+ ---
2
+ name: session-auth
3
+ description: >
4
+ Manage authentication sessions, parse server responses, and validate identity
5
+ cookies using Zod schemas. Use for handling login flow results and
6
+ session integrity checks.
7
+ type: core
8
+ library: denwa-react-shared
9
+ library_version: "1.0.88"
10
+ sources:
11
+ - "Denwa799/react-shared:src/shared/schemas/index.ts"
12
+ ---
13
+
14
+ # Session & Auth Management
15
+
16
+ This skill covers the standardization of server responses and session state validation using Zod schemas. All API interactions should be validated against these schemas to ensure data consistency.
17
+
18
+ ## Setup
19
+
20
+ ```typescript
21
+ import { responseSchema, sessionCookieSchema } from 'denwa-react-shared';
22
+
23
+ // Example: Validating an API response
24
+ const handleApiResponse = (data: unknown) => {
25
+ const result = responseSchema.safeParse(data);
26
+ if (!result.success) {
27
+ console.error('API format mismatch:', result.error);
28
+ return;
29
+ }
30
+ return result.data;
31
+ };
32
+ ```
33
+
34
+ ## Core Patterns
35
+
36
+ ### Parsing Session Cookies
37
+ Use `sessionCookieSchema` to validate the structure of the authentication cookie before using it in the application.
38
+
39
+ ```typescript
40
+ import { sessionCookieSchema } from 'denwa-react-shared';
41
+
42
+ const validateSession = (cookieData: unknown) => {
43
+ const session = sessionCookieSchema.parse(cookieData);
44
+ return {
45
+ isLoggedIn: !!session.tokens.accessToken.token,
46
+ userRoles: session.roles,
47
+ isAdmin: session.roles.includes('admin'),
48
+ };
49
+ };
50
+ ```
51
+
52
+ ### Handling Standard Error Envelopes
53
+ The `responseSchema` includes a structured `error` field. Always check for both the top-level `error` object and `statusCode`.
54
+
55
+ ```typescript
56
+ import { responseSchema } from 'denwa-react-shared';
57
+
58
+ async function fetchData(url: string) {
59
+ const response = await fetch(url);
60
+ const data = await response.json();
61
+
62
+ const parsed = responseSchema.parse(data);
63
+ if (parsed.error) {
64
+ throw new Error(parsed.error.message || 'Unknown error');
65
+ }
66
+
67
+ return parsed.data;
68
+ }
69
+ ```
70
+
71
+ ## Common Mistakes
72
+
73
+ ### MEDIUM Manually parsing cookies without schema
74
+ Wrong:
75
+ ```typescript
76
+ const id = JSON.parse(cookies.get('session')).id;
77
+ ```
78
+ Correct:
79
+ ```typescript
80
+ const session = sessionCookieSchema.parse(cookies.get('session'));
81
+ const id = session.id;
82
+ ```
83
+ Manually accessing properties bypasses validation and creates runtime risks if the session structure changes.
84
+
85
+ Source: maintainer interview
86
+
87
+ ### HIGH Ignoring the data/response duality
88
+ Wrong:
89
+ ```typescript
90
+ // Expecting data to always be the result
91
+ const users = response.data;
92
+ ```
93
+ Correct:
94
+ ```typescript
95
+ // Checking both data and any legacy response fields
96
+ const users = response.data ?? response.response;
97
+ ```
98
+ The `responseSchema` allows for flexibility in return fields (`data` vs `response`). Agents should account for both.
99
+
100
+ Source: src/shared/schemas/index.ts