pejay-ui 1.4.3 → 1.5.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/README.md +26 -0
- package/bin/cli.js +45 -15
- package/package.json +2 -1
- package/registry/buttons.json +3 -2
- package/registry/dropdowns.json +3 -1
- package/registry/forms.json +51 -23
- package/registry/hotkeys.json +12 -0
- package/registry/overlays.json +18 -2
- package/registry/panels.json +21 -0
- package/registry/skeleton.json +20 -0
- package/registry/spinner.json +13 -0
- package/templates/button/Button.tsx +8 -7
- package/templates/button/README.md +81 -0
- package/templates/button/index.ts +1 -2
- package/templates/form/{checkbox-group.tsx → choices/checkbox-group.tsx} +1 -1
- package/templates/form/{checkbox.tsx → choices/checkbox.tsx} +1 -1
- package/templates/form/{radio-group.tsx → choices/radio-group.tsx} +1 -1
- package/templates/form/{radio.tsx → choices/radio.tsx} +1 -1
- package/templates/form/choices/readme.checkbox-group.md +27 -0
- package/templates/form/choices/readme.checkbox.md +26 -0
- package/templates/form/choices/readme.radio-group.md +26 -0
- package/templates/form/choices/readme.radio.md +24 -0
- package/templates/form/choices/readme.switch.md +26 -0
- package/templates/form/{switch.tsx → choices/switch.tsx} +1 -1
- package/templates/form/{file-input.tsx → file/file-input.tsx} +2 -2
- package/templates/form/file/readme.file-input.md +26 -0
- package/templates/form/index.ts +19 -22
- package/templates/form/{amount-input.tsx → numeric/amount-input.tsx} +2 -2
- package/templates/form/{number-input.tsx → numeric/number-input.tsx} +2 -2
- package/templates/form/{range-slider.tsx → numeric/range-slider.tsx} +1 -1
- package/templates/form/numeric/readme.amount-input.md +27 -0
- package/templates/form/numeric/readme.number-input.md +26 -0
- package/templates/form/numeric/readme.range-slider.md +27 -0
- package/templates/form/{date-picker.tsx → pickers/date-picker.tsx} +2 -2
- package/templates/form/{date-range-picker.tsx → pickers/date-range-picker.tsx} +2 -2
- package/templates/form/pickers/readme.date-picker.md +26 -0
- package/templates/form/pickers/readme.date-range-picker.md +25 -0
- package/templates/form/pickers/readme.time-picker.md +25 -0
- package/templates/form/pickers/readme.time-range-picker.md +25 -0
- package/templates/form/{time-picker.tsx → pickers/time-picker.tsx} +1 -1
- package/templates/form/{time-range-picker.tsx → pickers/time-range-picker.tsx} +1 -1
- package/templates/form/{input.tsx → text-inputs/input.tsx} +1 -1
- package/templates/form/{password-input.tsx → text-inputs/password-input.tsx} +1 -1
- package/templates/form/text-inputs/readme.email-input.md +24 -0
- package/templates/form/text-inputs/readme.input.md +28 -0
- package/templates/form/text-inputs/readme.password-input.md +24 -0
- package/templates/form/text-inputs/readme.phone-input.md +24 -0
- package/templates/form/text-inputs/readme.textarea.md +24 -0
- package/templates/form/text-inputs/readme.url-input.md +23 -0
- package/templates/form/{textarea.tsx → text-inputs/textarea.tsx} +1 -1
- package/templates/hotkeys/README.md +134 -0
- package/templates/hotkeys/components/HotkeyProvider.tsx +78 -0
- package/templates/hotkeys/components/HotkeysHelpModal.tsx +102 -0
- package/templates/hotkeys/core/key-matcher.ts +106 -0
- package/templates/hotkeys/core/registry.ts +39 -0
- package/templates/hotkeys/core/types.ts +15 -0
- package/templates/hotkeys/hooks/useHotkey.ts +43 -0
- package/templates/hotkeys/index.ts +6 -0
- package/templates/layouts/lv1/app-layout.tsx +1 -1
- package/templates/layouts/lv1/sidebar-menu.tsx +1 -1
- package/templates/notes/app-provider/app-provider-side-panel-modals-roadmap.md +606 -0
- package/templates/notes/app-provider/manual-open-close-side-panel-and-modal.md +913 -0
- package/templates/notes/app-provider/side-panel-card-hooks-and-complexity.md +578 -0
- package/templates/notes/under-dev/AppProvider.tsx +92 -0
- package/templates/notes/under-dev/app-context.ts +14 -0
- package/templates/notes/under-dev/card/base-card.tsx +35 -0
- package/templates/notes/under-dev/card/index.ts +4 -0
- package/templates/notes/under-dev/card/modal-card.tsx +88 -0
- package/templates/notes/under-dev/card/side-panel-card.tsx +127 -0
- package/templates/notes/under-dev/form-overlay-registry.ts +42 -0
- package/templates/notes/under-dev/keyboard-shortcuts-help.tsx +79 -0
- package/templates/notes/under-dev/keyboard-utils.ts +22 -0
- package/templates/notes/under-dev/overlay/backdrop.tsx +95 -0
- package/templates/notes/under-dev/overlay/index.ts +4 -0
- package/templates/notes/under-dev/overlay/modal.tsx +43 -0
- package/templates/notes/under-dev/overlay/side-panel.tsx +126 -0
- package/templates/notes/under-dev/overlay-close.ts +50 -0
- package/templates/notes/under-dev/page-shortcut-registry.ts +9 -0
- package/templates/notes/under-dev/unsaved-changes-notify.ts +11 -0
- package/templates/notes/under-dev/use-keyboard-shortcuts.tsx +110 -0
- package/templates/notes/under-dev/useFormDirty.ts +6 -0
- package/templates/notes/under-dev/useFormOverlayRegistration.ts +47 -0
- package/templates/notes/under-dev/useFormPanel.tsx +18 -0
- package/templates/notes/under-dev/useFormTabHandler.ts +22 -0
- package/templates/notes/under-dev/useHorizontalWheelScroll.ts +27 -0
- package/templates/notes/under-dev/useOverlay.ts +41 -0
- package/templates/overlays/index.ts +2 -1
- package/templates/overlays/portal/portal.tsx +26 -0
- package/templates/overlays/tooltip/readme.tooltip.md +26 -0
- package/templates/{button → overlays/tooltip}/tooltip.tsx +1 -1
- package/templates/panels/COMPONENTS.md +103 -0
- package/templates/panels/README.md +702 -0
- package/templates/panels/components/base-card.tsx +33 -0
- package/templates/panels/components/index.ts +8 -0
- package/templates/panels/components/modal/backdrop.tsx +88 -0
- package/templates/panels/components/modal/modal-card.tsx +139 -0
- package/templates/panels/components/modal/modal-raw.tsx +36 -0
- package/templates/panels/components/modal/modal.tsx +49 -0
- package/templates/panels/components/side-panel/side-panel-card.tsx +123 -0
- package/templates/panels/components/side-panel/side-panel-raw.tsx +25 -0
- package/templates/panels/components/side-panel/side-panel.tsx +135 -0
- package/templates/panels/core/PanelProvider.tsx +145 -0
- package/templates/panels/core/constants.ts +9 -0
- package/templates/panels/core/form-overlay-registry.ts +35 -0
- package/templates/panels/core/index.ts +6 -0
- package/templates/panels/core/overlay-close.ts +11 -0
- package/templates/panels/core/panel-context.ts +41 -0
- package/templates/panels/core/types.ts +41 -0
- package/templates/panels/hooks/index.ts +7 -0
- package/templates/panels/hooks/useFormDirty.ts +6 -0
- package/templates/panels/hooks/useFormOverlayRegistration.ts +92 -0
- package/templates/panels/hooks/useFormPanel.tsx +18 -0
- package/templates/panels/hooks/useFormTabHandler.ts +25 -0
- package/templates/panels/hooks/useHorizontalWheelScroll.ts +31 -0
- package/templates/panels/hooks/useModalForm.tsx +22 -0
- package/templates/panels/hooks/useOverlay.ts +65 -0
- package/templates/panels/index.ts +3 -0
- package/templates/panels/vendor-example/by-using-modal/VendorModalPage.tsx +47 -0
- package/templates/panels/vendor-example/by-using-modal/useVendorModalForm.tsx +19 -0
- package/templates/panels/vendor-example/by-using-modal/vendor-modal-form.tsx +112 -0
- package/templates/panels/vendor-example/by-using-modal/vendor-types.ts +29 -0
- package/templates/panels/vendor-example/by-using-sidepanel/VendorsPage.tsx +47 -0
- package/templates/panels/vendor-example/by-using-sidepanel/useVendorFormPanel.tsx +15 -0
- package/templates/panels/vendor-example/by-using-sidepanel/vendor-form.tsx +108 -0
- package/templates/panels/vendor-example/by-using-sidepanel/vendor-types.ts +29 -0
- package/templates/select-dropdown/README.md +62 -0
- package/templates/select-dropdown/multiselect-input.tsx +2 -2
- package/templates/select-dropdown/select-input.tsx +2 -2
- package/templates/skeleton/README.md +53 -0
- package/templates/skeleton/index.ts +2 -0
- package/templates/skeleton/skeleton.css +36 -0
- package/templates/skeleton/skeleton.tsx +40 -0
- package/templates/skeleton/types.ts +12 -0
- package/templates/spinner/README.md +51 -0
- package/templates/spinner/index.ts +1 -0
- package/templates/spinner/spinner.css +58 -0
- package/templates/spinner/spinner.tsx +263 -0
- package/templates/toast/container.tsx +2 -2
- package/templates/utilities/formater.dateTime.md +74 -0
- package/templates/utilities/formater.dateTime.ts +310 -0
- package/templates/utilities/formater.phoneNumber.md +32 -0
- package/templates/utilities/formater.phoneNumber.ts +143 -0
- package/templates/utilities/sanitize.md +23 -0
- package/templates/utilities/sanitize.ts +148 -0
- /package/templates/form/{email-input.tsx → text-inputs/email-input.tsx} +0 -0
- /package/templates/form/{phone-input.tsx → text-inputs/phone-input.tsx} +0 -0
- /package/templates/form/{url-input.tsx → text-inputs/url-input.tsx} +0 -0
- /package/templates/{overlays → notes/under-dev/overlay}/portal.tsx +0 -0
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
|
|
2
|
+
### Phone Number Formatter (`phone-number-formatter`)
|
|
3
|
+
|
|
4
|
+
- **Description**: Parses, validates, and formats phone numbers using `libphonenumber-js`. Supports national and international numbers, country-based parsing, country calling code prefixes, and graceful handling of invalid or placeholder values.
|
|
5
|
+
|
|
6
|
+
- **Exported Functions**:
|
|
7
|
+
- `setPhoneNumberFormat({ number, country, countryCode })`
|
|
8
|
+
- Formats valid phone numbers to their national format.
|
|
9
|
+
- Supports parsing using:
|
|
10
|
+
- Existing international numbers (`+1234567890`)
|
|
11
|
+
- Country calling codes (`+1`, `+91`, etc.)
|
|
12
|
+
- ISO country codes (`US`, `IN`, etc.)
|
|
13
|
+
- Returns `null` for:
|
|
14
|
+
- `null`
|
|
15
|
+
- `undefined`
|
|
16
|
+
- Empty strings
|
|
17
|
+
- Placeholder values such as `"null"`, `"undefined"`, and `"-"`
|
|
18
|
+
- Returns the original value when:
|
|
19
|
+
- The phone number is invalid
|
|
20
|
+
- Parsing fails
|
|
21
|
+
- Prioritizes parsing in the following order:
|
|
22
|
+
1. Number already contains `+`
|
|
23
|
+
2. `countryCode`
|
|
24
|
+
3. `country`
|
|
25
|
+
|
|
26
|
+
- **Features**
|
|
27
|
+
- Supports both string and numeric inputs.
|
|
28
|
+
- Handles national and international phone numbers.
|
|
29
|
+
- Supports ISO country codes and country calling codes.
|
|
30
|
+
- Safely handles null, undefined, and placeholder values.
|
|
31
|
+
- Returns original input for invalid or unparsable numbers.
|
|
32
|
+
- Formats valid numbers using `formatNational()`.
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
import { parsePhoneNumberWithError, type CountryCode } from "libphonenumber-js";
|
|
2
|
+
|
|
3
|
+
/* ------------------------------------------------
|
|
4
|
+
? Types & Interfaces
|
|
5
|
+
------------------------------------------------*/
|
|
6
|
+
type PhoneFormatterArgs = {
|
|
7
|
+
number: string | number | null | undefined;
|
|
8
|
+
country?: CountryCode;
|
|
9
|
+
countryCode?: string; // +1, +91, etc.
|
|
10
|
+
};
|
|
11
|
+
|
|
12
|
+
/* ------------------------------------------------
|
|
13
|
+
? Main function
|
|
14
|
+
@param- number: Phone number to be formatted
|
|
15
|
+
@param- country: Country code
|
|
16
|
+
@param- countryCode: Country calling code
|
|
17
|
+
@returns - Formatted phone number
|
|
18
|
+
|
|
19
|
+
*usage Type 1 (Use country code)
|
|
20
|
+
|
|
21
|
+
setPhoneNumberFormat({
|
|
22
|
+
number: "4165551234",
|
|
23
|
+
country: "US",
|
|
24
|
+
countryCode: "+1",
|
|
25
|
+
});
|
|
26
|
+
|
|
27
|
+
*useage Type 2 (Country code is provided)
|
|
28
|
+
|
|
29
|
+
setPhoneNumberFormat({
|
|
30
|
+
number: "4165551234",
|
|
31
|
+
countryCode: "+1",
|
|
32
|
+
});
|
|
33
|
+
|
|
34
|
+
*useage Type 3 (only country is provided)
|
|
35
|
+
|
|
36
|
+
setPhoneNumberFormat({
|
|
37
|
+
number: "4165551234",
|
|
38
|
+
country: "IN",
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
*useage Type 4 (Number already contains + ignore country code)
|
|
42
|
+
|
|
43
|
+
setPhoneNumberFormat({
|
|
44
|
+
number: "+14165551234",
|
|
45
|
+
country: "IN",
|
|
46
|
+
});
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
*useage Type 5 (Number already contains + so no need to provide country code)
|
|
51
|
+
|
|
52
|
+
setPhoneNumberFormat({
|
|
53
|
+
number: "+14165551234",
|
|
54
|
+
});
|
|
55
|
+
|
|
56
|
+
*usage Type 6 (null is provided)
|
|
57
|
+
|
|
58
|
+
setPhoneNumberFormat({
|
|
59
|
+
number: null,
|
|
60
|
+
});
|
|
61
|
+
|
|
62
|
+
*usage Type 7 (undefined is provided)
|
|
63
|
+
|
|
64
|
+
setPhoneNumberFormat({
|
|
65
|
+
number: undefined,
|
|
66
|
+
});
|
|
67
|
+
|
|
68
|
+
|
|
69
|
+
*usage Type 8 (placeholder value is provided)
|
|
70
|
+
|
|
71
|
+
setPhoneNumberFormat({
|
|
72
|
+
number: "-",
|
|
73
|
+
});
|
|
74
|
+
|
|
75
|
+
*usage Type 9 (invalid number)
|
|
76
|
+
|
|
77
|
+
setPhoneNumberFormat({
|
|
78
|
+
number: "abc",
|
|
79
|
+
});
|
|
80
|
+
|
|
81
|
+
*usage Type 10 (unformatted number)
|
|
82
|
+
|
|
83
|
+
setPhoneNumberFormat({
|
|
84
|
+
number: "1234",
|
|
85
|
+
});
|
|
86
|
+
|
|
87
|
+
------------------------------------------------*/
|
|
88
|
+
export function setPhoneNumberFormat({
|
|
89
|
+
number,
|
|
90
|
+
country,
|
|
91
|
+
countryCode,
|
|
92
|
+
}: PhoneFormatterArgs): string | null {
|
|
93
|
+
// Handle nullish values
|
|
94
|
+
if (number == null) return null;
|
|
95
|
+
const strNum = String(number).trim();
|
|
96
|
+
|
|
97
|
+
// Handle common placeholder values
|
|
98
|
+
if (!strNum || ["null", "undefined", "-"].includes(strNum.toLowerCase())) {
|
|
99
|
+
return null;
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
try {
|
|
103
|
+
let phoneInput = strNum;
|
|
104
|
+
|
|
105
|
+
/**
|
|
106
|
+
* NOTE : Priority:
|
|
107
|
+
* 1. Number already contains '+'
|
|
108
|
+
* 2. countryCode
|
|
109
|
+
* 3. country
|
|
110
|
+
*/
|
|
111
|
+
|
|
112
|
+
if (!phoneInput.startsWith("+") && countryCode) {
|
|
113
|
+
phoneInput = `${countryCode}${phoneInput}`;
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
const phone = phoneInput.startsWith("+")
|
|
117
|
+
? parsePhoneNumberWithError(phoneInput)
|
|
118
|
+
: parsePhoneNumberWithError(phoneInput, country);
|
|
119
|
+
|
|
120
|
+
if (!phone.isValid()) {
|
|
121
|
+
return strNum;
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
return phone.formatNational();
|
|
125
|
+
} catch {
|
|
126
|
+
return strNum;
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
/*
|
|
131
|
+
|
|
132
|
+
*what number can handel as input
|
|
133
|
+
|
|
134
|
+
1. null/undefined -> null
|
|
135
|
+
2. "", "null", "-" -> null
|
|
136
|
+
3. Number starts "+" -> parse as international
|
|
137
|
+
4. countryCode -> prepend and parse
|
|
138
|
+
5. country -> parse as national
|
|
139
|
+
6. Valid number -> formatNational()
|
|
140
|
+
7. Invalid number -> return original value
|
|
141
|
+
8. Parse error -> return original value
|
|
142
|
+
|
|
143
|
+
*/
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
### Sanitize Data (`sanitize-fn`)
|
|
2
|
+
|
|
3
|
+
- **Description**: Recursively trims string values, nullifies empty strings, and checks for empty payloads in form data.
|
|
4
|
+
|
|
5
|
+
- **Exported Functions**:
|
|
6
|
+
- `sanitizeFormData({ data, skip, nullifyEmptyStrings })`
|
|
7
|
+
- Sanitizes an entire object and returns:
|
|
8
|
+
```ts
|
|
9
|
+
{
|
|
10
|
+
isEmpty: boolean;
|
|
11
|
+
data: T;
|
|
12
|
+
}
|
|
13
|
+
```
|
|
14
|
+
- Supports nested field exclusion using dot notation (e.g. `"user.email"`).
|
|
15
|
+
- Optionally preserves empty strings by setting `nullifyEmptyStrings` to `false`.
|
|
16
|
+
|
|
17
|
+
- **Features**
|
|
18
|
+
- Trims leading and trailing whitespace from strings.
|
|
19
|
+
- Converts empty strings to `null` (configurable).
|
|
20
|
+
- Supports nested objects and arrays.
|
|
21
|
+
- Supports skipping specific fields using dot notation.
|
|
22
|
+
- Preserves `Date` and `File` instances.
|
|
23
|
+
- Returns an `isEmpty` flag for quick form validation.
|
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
/* ------------------------------------------------
|
|
2
|
+
? Types & Interfaces
|
|
3
|
+
------------------------------------------------*/
|
|
4
|
+
type SanitizeFormDataOptions<T> = {
|
|
5
|
+
data: T;
|
|
6
|
+
skip?: string[];
|
|
7
|
+
nullifyEmptyStrings?: boolean;
|
|
8
|
+
};
|
|
9
|
+
|
|
10
|
+
type SanitizeFormDataResult<T> = {
|
|
11
|
+
isEmpty: boolean;
|
|
12
|
+
data: T;
|
|
13
|
+
};
|
|
14
|
+
|
|
15
|
+
/* ------------------------------------------------
|
|
16
|
+
? Main function
|
|
17
|
+
@param - data: Object to be sanitized
|
|
18
|
+
@param - skip: Array of keys to skip
|
|
19
|
+
@param - nullifyEmptyStrings: Whether to nullify empty strings
|
|
20
|
+
@returns - Sanitized object
|
|
21
|
+
|
|
22
|
+
*usage Type 1
|
|
23
|
+
|
|
24
|
+
const {isEmpty,data:sanitizedData} = sanitizeFormData({data});
|
|
25
|
+
|
|
26
|
+
if(isEmpty){
|
|
27
|
+
return;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
*usage Type 2
|
|
31
|
+
const {isEmpty,data:sanitizedData} = sanitizeFormData({data, skip:["password","user.email",]});
|
|
32
|
+
|
|
33
|
+
if(isEmpty){
|
|
34
|
+
return;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
# NOTE : skip contains dot notation for nested objects and key names whose value will skip from sanitizing
|
|
38
|
+
|
|
39
|
+
*usage Type 3
|
|
40
|
+
const {isEmpty,data:sanitizedData} = sanitizeFormData({data, skip:["password","user.email",], nullifyEmptyStrings:false});
|
|
41
|
+
|
|
42
|
+
if(isEmpty){
|
|
43
|
+
return;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
|
|
47
|
+
------------------------------------------------*/
|
|
48
|
+
export const sanitizeFormData = <T>({
|
|
49
|
+
data,
|
|
50
|
+
skip = [],
|
|
51
|
+
nullifyEmptyStrings = true,
|
|
52
|
+
}: SanitizeFormDataOptions<T>): SanitizeFormDataResult<T> => {
|
|
53
|
+
const skipSet = new Set(skip);
|
|
54
|
+
const sanitizedData = sanitize(data, "", skipSet, nullifyEmptyStrings) as T;
|
|
55
|
+
return {
|
|
56
|
+
isEmpty: isEmptyValue(sanitizedData),
|
|
57
|
+
data: sanitizedData,
|
|
58
|
+
};
|
|
59
|
+
};
|
|
60
|
+
|
|
61
|
+
/* ------------------------------------------------
|
|
62
|
+
# ANCHOR : Helper Functions
|
|
63
|
+
------------------------------------------------*/
|
|
64
|
+
|
|
65
|
+
/* ------------------------------------------------
|
|
66
|
+
? Recursive Function
|
|
67
|
+
@param - value: Value to be sanitized
|
|
68
|
+
@param - path: Path of the value
|
|
69
|
+
@param - skipSet: Set of keys to skip
|
|
70
|
+
@param - nullifyEmptyStrings: Whether to nullify empty strings
|
|
71
|
+
@returns - Sanitized value
|
|
72
|
+
------------------------------------------------*/
|
|
73
|
+
export function sanitize(
|
|
74
|
+
value: unknown,
|
|
75
|
+
path = "",
|
|
76
|
+
skipSet: Set<string>,
|
|
77
|
+
nullifyEmptyStrings: boolean,
|
|
78
|
+
): unknown {
|
|
79
|
+
// Strings
|
|
80
|
+
if (typeof value === "string") {
|
|
81
|
+
if (skipSet.has(path)) {
|
|
82
|
+
return value;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
const trimmed = value.trim();
|
|
86
|
+
|
|
87
|
+
return nullifyEmptyStrings && trimmed === "" ? null : trimmed;
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
// Arrays
|
|
91
|
+
if (Array.isArray(value)) {
|
|
92
|
+
return value.map((item, index) =>
|
|
93
|
+
sanitize(item, `${path}[${index}]`, skipSet, nullifyEmptyStrings),
|
|
94
|
+
);
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
// Plain Objects
|
|
98
|
+
if (
|
|
99
|
+
value &&
|
|
100
|
+
typeof value === "object" &&
|
|
101
|
+
!(value instanceof Date) &&
|
|
102
|
+
!(value instanceof File)
|
|
103
|
+
) {
|
|
104
|
+
return Object.fromEntries(
|
|
105
|
+
Object.entries(value).map(([key, val]) => [
|
|
106
|
+
key,
|
|
107
|
+
sanitize(
|
|
108
|
+
val,
|
|
109
|
+
path ? `${path}.${key}` : key,
|
|
110
|
+
skipSet,
|
|
111
|
+
nullifyEmptyStrings,
|
|
112
|
+
),
|
|
113
|
+
]),
|
|
114
|
+
);
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
return value;
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
/* ------------------------------------------------
|
|
121
|
+
? Check if value is empty
|
|
122
|
+
@param - value: Value to be checked
|
|
123
|
+
@returns - boolean
|
|
124
|
+
------------------------------------------------*/
|
|
125
|
+
export function isEmptyValue(value: unknown): boolean {
|
|
126
|
+
if (value === null) return true;
|
|
127
|
+
|
|
128
|
+
if (typeof value === "string") {
|
|
129
|
+
return value.trim() === "";
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
if (Array.isArray(value)) {
|
|
133
|
+
return value.length === 0 || value.every(isEmptyValue);
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
if (
|
|
137
|
+
value &&
|
|
138
|
+
typeof value === "object" &&
|
|
139
|
+
!(value instanceof Date) &&
|
|
140
|
+
!(value instanceof File)
|
|
141
|
+
) {
|
|
142
|
+
const values = Object.values(value);
|
|
143
|
+
|
|
144
|
+
return values.length === 0 || values.every(isEmptyValue);
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
return false;
|
|
148
|
+
}
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|