@sustaina/shared-ui 1.30.2 → 1.31.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/dist/index.d.mts CHANGED
@@ -48,7 +48,9 @@ interface FieldSchemaBase<T extends FieldType> {
48
48
  interface DropdownFieldSchema extends FieldSchemaBase<"dropdown"> {
49
49
  options: Option[];
50
50
  }
51
- type TextFieldSchema = FieldSchemaBase<"text">;
51
+ interface TextFieldSchema extends FieldSchemaBase<"text"> {
52
+ allowRegex?: RegExp;
53
+ }
52
54
  type NumberFieldSchema = FieldSchemaBase<"number">;
53
55
  type DateFieldSchema = FieldSchemaBase<"date">;
54
56
  type DateTimeFieldSchema = FieldSchemaBase<"datetime">;
@@ -84,6 +86,7 @@ type RowState = {
84
86
  multiTableSearch?: boolean;
85
87
  jsonPath?: string[];
86
88
  lookupFieldName?: string;
89
+ allowRegex?: RegExp;
87
90
  } | {
88
91
  id: string;
89
92
  fieldName: string;
@@ -94,6 +97,7 @@ type RowState = {
94
97
  multiTableSearch?: boolean;
95
98
  jsonPath?: string[];
96
99
  lookupFieldName?: string;
100
+ allowRegex?: RegExp;
97
101
  };
98
102
  interface Params {
99
103
  AND: Record<string, unknown>[];
package/dist/index.d.ts CHANGED
@@ -48,7 +48,9 @@ interface FieldSchemaBase<T extends FieldType> {
48
48
  interface DropdownFieldSchema extends FieldSchemaBase<"dropdown"> {
49
49
  options: Option[];
50
50
  }
51
- type TextFieldSchema = FieldSchemaBase<"text">;
51
+ interface TextFieldSchema extends FieldSchemaBase<"text"> {
52
+ allowRegex?: RegExp;
53
+ }
52
54
  type NumberFieldSchema = FieldSchemaBase<"number">;
53
55
  type DateFieldSchema = FieldSchemaBase<"date">;
54
56
  type DateTimeFieldSchema = FieldSchemaBase<"datetime">;
@@ -84,6 +86,7 @@ type RowState = {
84
86
  multiTableSearch?: boolean;
85
87
  jsonPath?: string[];
86
88
  lookupFieldName?: string;
89
+ allowRegex?: RegExp;
87
90
  } | {
88
91
  id: string;
89
92
  fieldName: string;
@@ -94,6 +97,7 @@ type RowState = {
94
97
  multiTableSearch?: boolean;
95
98
  jsonPath?: string[];
96
99
  lookupFieldName?: string;
100
+ allowRegex?: RegExp;
97
101
  };
98
102
  interface Params {
99
103
  AND: Record<string, unknown>[];
package/dist/index.js CHANGED
@@ -692,7 +692,8 @@ var OPERATOR_MAP = {
692
692
  dropdown: ["is", "isNot"],
693
693
  lookup: ["containsAny", "containsOnly", "containsAll", "notContains"],
694
694
  uuid: ["equals", "notEquals", "gt", "gte", "lt", "lte"],
695
- json: ["equals", "notEquals", "containsAny"]
695
+ json: ["equals", "notEquals"]
696
+ // removed containsAny from json
696
697
  };
697
698
 
698
699
  // src/components/advanceSearch/hooks/useAdvanceSearch.ts
@@ -739,7 +740,8 @@ function makeNewRow(field) {
739
740
  operator: op,
740
741
  value: "",
741
742
  multiTableSearch: field.multiTableSearch,
742
- lookupFieldName: field.lookupFieldName
743
+ lookupFieldName: field.lookupFieldName,
744
+ allowRegex: field.type === "text" ? field.allowRegex : void 0
743
745
  };
744
746
  }
745
747
  function useAdvanceSearch({ fields, limitRows }) {
@@ -782,7 +784,8 @@ function useAdvanceSearch({ fields, limitRows }) {
782
784
  value2: "",
783
785
  multiTableSearch: r.multiTableSearch,
784
786
  jsonPath: r.jsonPath,
785
- lookupFieldName: r.lookupFieldName
787
+ lookupFieldName: r.lookupFieldName,
788
+ allowRegex: r.allowRegex
786
789
  } : {
787
790
  id: r.id,
788
791
  fieldName: r.fieldName,
@@ -791,7 +794,8 @@ function useAdvanceSearch({ fields, limitRows }) {
791
794
  value: "",
792
795
  multiTableSearch: r.multiTableSearch,
793
796
  jsonPath: r.jsonPath,
794
- lookupFieldName: r.lookupFieldName
797
+ lookupFieldName: r.lookupFieldName,
798
+ allowRegex: r.allowRegex
795
799
  };
796
800
  })
797
801
  );
@@ -839,7 +843,8 @@ function useAdvanceSearch({ fields, limitRows }) {
839
843
  lookupFieldName: r.lookupFieldName,
840
844
  jsonPath: r.jsonPath,
841
845
  operator,
842
- value: ""
846
+ value: "",
847
+ allowRegex: r.allowRegex
843
848
  };
844
849
  })
845
850
  );
@@ -1429,11 +1434,19 @@ var ConditionTextInput = ({ row, control, onClear }) => /* @__PURE__ */ jsxRunti
1429
1434
  field.onChange("");
1430
1435
  onClear("value");
1431
1436
  };
1437
+ const handleChange = (e) => {
1438
+ const val = e.target.value;
1439
+ if (val !== "" && row.allowRegex && !row.allowRegex.test(val)) {
1440
+ return;
1441
+ }
1442
+ field.onChange(val);
1443
+ };
1432
1444
  return /* @__PURE__ */ jsxRuntime.jsxs(FormItem, { className: "relative", children: [
1433
1445
  /* @__PURE__ */ jsxRuntime.jsx(FormControl, { children: /* @__PURE__ */ jsxRuntime.jsx(
1434
1446
  Input,
1435
1447
  {
1436
1448
  ...field,
1449
+ onChange: handleChange,
1437
1450
  value: field.value ?? "",
1438
1451
  autoComplete: "off",
1439
1452
  inputMode: "text",
@@ -2640,12 +2653,16 @@ var LookupSelect = ({
2640
2653
  (option) => {
2641
2654
  upsertOptionLabels([option]);
2642
2655
  addTag(option.value);
2643
- inputRef.current?.focus();
2644
- setTimeout(() => {
2645
- inputRef.current?.scrollIntoView({ behavior: "smooth" });
2646
- }, 100);
2656
+ if (multiple) {
2657
+ inputRef.current?.focus();
2658
+ setTimeout(() => {
2659
+ inputRef.current?.scrollIntoView({ behavior: "smooth" });
2660
+ }, 100);
2661
+ } else {
2662
+ inputRef.current?.blur();
2663
+ }
2647
2664
  },
2648
- [addTag, upsertOptionLabels]
2665
+ [addTag, multiple, upsertOptionLabels]
2649
2666
  );
2650
2667
  const handleKeyDown = React4.useCallback(
2651
2668
  (e) => {
@@ -2805,7 +2822,7 @@ var LookupSelect = ({
2805
2822
  }
2806
2823
  return /* @__PURE__ */ jsxRuntime.jsx("div", { ref: assignDropdownContentRef, className: "absolute left-0 right-0 top-full z-10 mt-1", children: dropdownContent });
2807
2824
  };
2808
- return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative w-full", ref: containerRef, children: [
2825
+ return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative w-full truncate", ref: containerRef, children: [
2809
2826
  /* @__PURE__ */ jsxRuntime.jsxs(
2810
2827
  "div",
2811
2828
  {
@@ -2836,7 +2853,7 @@ var LookupSelect = ({
2836
2853
  `${tag}-${i}`
2837
2854
  );
2838
2855
  }),
2839
- !multiple && selectedLabel && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate text-sm text-gray-700", children: selectedLabel }),
2856
+ !multiple && selectedLabel && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate text-sm text-gray-700 max-w-full", children: selectedLabel }),
2840
2857
  /* @__PURE__ */ jsxRuntime.jsx(
2841
2858
  "input",
2842
2859
  {
@@ -2850,6 +2867,7 @@ var LookupSelect = ({
2850
2867
  setIsDropdownOpen(true);
2851
2868
  }
2852
2869
  },
2870
+ hidden: !multiple && selectedLabel !== void 0,
2853
2871
  placeholder: value.length === 0 && resolvedPlaceholder || "",
2854
2872
  className: "min-w-[120px] flex-1 border-none bg-transparent py-1 text-sm text-gray-600 placeholder:text-gray-400 outline-none",
2855
2873
  disabled: multiple && limitReached
@@ -2951,7 +2969,6 @@ var ConditionJSONInput = ({
2951
2969
  onClear: handleClear,
2952
2970
  error: Boolean(fieldState.error),
2953
2971
  placeholder: fieldSchema?.placeholder,
2954
- maxTags: row.operator === "containsAny" ? fieldSchema?.maxTags : 1,
2955
2972
  fetchSuggestions: fieldSchema?.fetchSuggestions,
2956
2973
  suggestionDebounce: fieldSchema?.suggestionDebounce,
2957
2974
  noOptionsMessage: fieldSchema?.noOptionsMessage,
@@ -3164,7 +3181,8 @@ var DatetimeBuilder = class {
3164
3181
  case "after":
3165
3182
  return {
3166
3183
  [row.fieldName]: helper(
3167
- { gte: dayStart.toISOString() },
3184
+ { gte: dayEnd.toISOString() },
3185
+ // use end of the day time
3168
3186
  { multiTableSearch: row.multiTableSearch }
3169
3187
  )
3170
3188
  };
@@ -3267,12 +3285,12 @@ var JSONBuilder = class {
3267
3285
  return {
3268
3286
  NOT: { [row.fieldName]: { path: row.jsonPath, equals: isArray ? row.value[0] : row.value } }
3269
3287
  };
3270
- case "containsAny":
3271
- if (!isArray)
3272
- return { [row.fieldName]: { path: row.jsonPath, equals: isArray ? row.value[0] : row.value } };
3273
- return {
3274
- OR: row.value.map((v) => ({ [row.fieldName]: { path: row.jsonPath, equals: v } }))
3275
- };
3288
+ // case "containsAny":
3289
+ // if (!isArray)
3290
+ // return { [row.fieldName]: { path: row.jsonPath, equals: isArray ? row.value[0] : row.value } };
3291
+ // return {
3292
+ // OR: (row.value as any[]).map((v) => ({ [row.fieldName]: { path: row.jsonPath, equals: v } }))
3293
+ // };
3276
3294
  default:
3277
3295
  return {};
3278
3296
  }
@@ -3545,7 +3563,9 @@ function transformFilterKeys(obj, fieldMap = FILTER_FIELD_MAP) {
3545
3563
  }
3546
3564
  var sanitizeInput = (val) => {
3547
3565
  if (!val) return val;
3548
- if (typeof val !== "string") return "__INVALID_TYPE__";
3566
+ if (Array.isArray(val)) {
3567
+ return val.map((v) => sanitizeInput(v));
3568
+ }
3549
3569
  if (val.includes("\n") || val.includes("\r") || /[\u2028\u2029]/u.test(val))
3550
3570
  return "__INVALID_NEWLINE__";
3551
3571
  if (/\\\\/.test(val)) return "__INVALID_ESCAPE__";
@@ -3564,6 +3584,9 @@ var numericTypes = ["number", "integer", "decimal"];
3564
3584
  var dateTypes = ["date", "datemonth"];
3565
3585
  var validateByFieldType = (value, fieldType) => {
3566
3586
  if (!value) return { valid: true };
3587
+ if (Array.isArray(value)) {
3588
+ return { valid: true };
3589
+ }
3567
3590
  if (numericTypes.includes(fieldType)) {
3568
3591
  if (!/^\d+(\.\d+)?$/.test(value)) {
3569
3592
  return { valid: false, message: "Please enter a valid number." };
@@ -3636,6 +3659,7 @@ var AdvanceSearch = ({
3636
3659
  );
3637
3660
  const parseRangeValue = React4.useCallback((raw, fieldType) => {
3638
3661
  if (!raw) return void 0;
3662
+ if (Array.isArray(raw)) return void 0;
3639
3663
  const normalized = fieldType === "datemonth" ? `${raw}-01` : raw;
3640
3664
  const parsed = dateFns.parseISO(normalized);
3641
3665
  return dateFns.isValid(parsed) ? parsed : void 0;
@@ -3654,10 +3678,10 @@ var AdvanceSearch = ({
3654
3678
  const processedRows = rows.map((r) => {
3655
3679
  const startField = `value_${r.id}`;
3656
3680
  const endField = `value2_${r.id}`;
3657
- let v1 = currentValues[startField] ?? "";
3658
- let v2 = currentValues[endField] ?? "";
3681
+ let v1 = currentValues[startField];
3682
+ let v2 = currentValues[endField];
3659
3683
  const s1 = sanitizeInput(v1);
3660
- if (s1?.startsWith("__INVALID")) {
3684
+ if (Array.isArray(s1) && s1.some((v) => v?.startsWith("__INVALID")) || typeof s1 === "string" && s1?.startsWith("__INVALID")) {
3661
3685
  hasError = true;
3662
3686
  setError(startField, { type: "validate", message: "Invalid input." });
3663
3687
  return null;
@@ -3671,7 +3695,7 @@ var AdvanceSearch = ({
3671
3695
  }
3672
3696
  if (r.operator === "between") {
3673
3697
  const s2 = sanitizeInput(v2);
3674
- if (s2?.startsWith("__INVALID")) {
3698
+ if (Array.isArray(s2) && s2.some((v) => v?.startsWith("__INVALID")) || typeof s2 === "string" && s2?.startsWith("__INVALID")) {
3675
3699
  hasError = true;
3676
3700
  setError(endField, { type: "validate", message: "Invalid input." });
3677
3701
  return null;