@donotdev/crud 0.0.6 → 0.0.7
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 +18 -2
- package/dist/CrudService.d.ts +91 -8
- package/dist/CrudService.d.ts.map +1 -1
- package/dist/CrudService.js +1 -1
- package/dist/CrudStore.d.ts +45 -2
- package/dist/CrudStore.d.ts.map +1 -1
- package/dist/CrudStore.js +1 -1
- package/dist/FieldRegistry.d.ts +56 -20
- package/dist/FieldRegistry.d.ts.map +1 -1
- package/dist/FieldRegistry.js +1 -1
- package/dist/adapters/FirestoreAdapter.d.ts +4 -4
- package/dist/adapters/FirestoreAdapter.d.ts.map +1 -1
- package/dist/adapters/FirestoreAdapter.js +1 -1
- package/dist/adapters/FunctionsAdapter.d.ts +3 -2
- package/dist/adapters/FunctionsAdapter.d.ts.map +1 -1
- package/dist/adapters/FunctionsAdapter.js +1 -1
- package/dist/builtinFieldTypes.d.ts +4 -0
- package/dist/builtinFieldTypes.d.ts.map +1 -1
- package/dist/builtinFieldTypes.js +1 -1
- package/dist/components/CrudButton.d.ts +1 -1
- package/dist/components/CrudButton.d.ts.map +1 -1
- package/dist/components/CrudButton.js +1 -1
- package/dist/components/DisplayFieldRenderer.d.ts +15 -11
- package/dist/components/DisplayFieldRenderer.d.ts.map +1 -1
- package/dist/components/DisplayFieldRenderer.js +1 -1
- package/dist/components/EntityCardList.d.ts +27 -0
- package/dist/components/EntityCardList.d.ts.map +1 -0
- package/dist/components/EntityCardList.js +1 -0
- package/dist/components/EntityDisplayRenderer.d.ts +43 -0
- package/dist/components/EntityDisplayRenderer.d.ts.map +1 -0
- package/dist/components/EntityDisplayRenderer.js +1 -0
- package/dist/components/EntityFormRenderer.d.ts +21 -26
- package/dist/components/EntityFormRenderer.d.ts.map +1 -1
- package/dist/components/EntityFormRenderer.js +1 -5
- package/dist/components/EntityList.d.ts +24 -0
- package/dist/components/EntityList.d.ts.map +1 -0
- package/dist/components/EntityList.js +1 -0
- package/dist/components/FormFieldRenderer.d.ts +3 -10
- package/dist/components/FormFieldRenderer.d.ts.map +1 -1
- package/dist/components/FormFieldRenderer.js +1 -1
- package/dist/components/FormLayout.d.ts +1 -9
- package/dist/components/FormLayout.d.ts.map +1 -1
- package/dist/components/controlled/complex/ControlledAddressField.d.ts +8 -0
- package/dist/components/controlled/complex/ControlledAddressField.d.ts.map +1 -0
- package/dist/components/controlled/complex/ControlledAddressField.js +1 -0
- package/dist/components/controlled/complex/ControlledDateField.d.ts +8 -0
- package/dist/components/controlled/complex/ControlledDateField.d.ts.map +1 -0
- package/dist/components/controlled/complex/ControlledDateField.js +1 -0
- package/dist/components/controlled/complex/ControlledGeoPointField.d.ts +8 -0
- package/dist/components/controlled/complex/ControlledGeoPointField.d.ts.map +1 -0
- package/dist/components/controlled/complex/ControlledGeoPointField.js +1 -0
- package/dist/components/controlled/complex/ControlledMapField.d.ts +8 -0
- package/dist/components/controlled/complex/ControlledMapField.d.ts.map +1 -0
- package/dist/components/controlled/complex/ControlledMapField.js +1 -0
- package/dist/components/controlled/complex/ControlledMultiInputField.d.ts +8 -0
- package/dist/components/controlled/complex/ControlledMultiInputField.d.ts.map +1 -0
- package/dist/components/controlled/complex/ControlledMultiInputField.js +1 -0
- package/dist/components/controlled/complex/ControlledRichTextField.d.ts +8 -0
- package/dist/components/controlled/complex/ControlledRichTextField.d.ts.map +1 -0
- package/dist/components/controlled/complex/ControlledRichTextField.js +1 -0
- package/dist/components/controlled/complex/ControlledTimestampField.d.ts +8 -0
- package/dist/components/controlled/complex/ControlledTimestampField.d.ts.map +1 -0
- package/dist/components/controlled/complex/ControlledTimestampField.js +1 -0
- package/dist/components/controlled/complex/index.d.ts +8 -0
- package/dist/components/controlled/complex/index.d.ts.map +1 -0
- package/dist/components/controlled/complex/index.js +1 -0
- package/dist/components/controlled/file/ControlledDocumentField.d.ts +8 -0
- package/dist/components/controlled/file/ControlledDocumentField.d.ts.map +1 -0
- package/dist/components/controlled/file/ControlledDocumentField.js +1 -0
- package/dist/components/controlled/file/ControlledFileField.d.ts +8 -0
- package/dist/components/controlled/file/ControlledFileField.d.ts.map +1 -0
- package/dist/components/controlled/file/ControlledFileField.js +1 -0
- package/dist/components/controlled/file/ControlledImageField.d.ts +8 -0
- package/dist/components/controlled/file/ControlledImageField.d.ts.map +1 -0
- package/dist/components/controlled/file/ControlledImageField.js +1 -0
- package/dist/components/controlled/file/ControlledMultiDocumentField.d.ts +8 -0
- package/dist/components/controlled/file/ControlledMultiDocumentField.d.ts.map +1 -0
- package/dist/components/controlled/file/ControlledMultiDocumentField.js +1 -0
- package/dist/components/controlled/file/ControlledMultiFileField.d.ts +8 -0
- package/dist/components/controlled/file/ControlledMultiFileField.d.ts.map +1 -0
- package/dist/components/controlled/file/ControlledMultiFileField.js +1 -0
- package/dist/components/controlled/file/ControlledMultiImageField.d.ts +8 -0
- package/dist/components/controlled/file/ControlledMultiImageField.d.ts.map +1 -0
- package/dist/components/controlled/file/ControlledMultiImageField.js +1 -0
- package/dist/components/controlled/file/index.d.ts +7 -0
- package/dist/components/controlled/file/index.d.ts.map +1 -0
- package/dist/components/controlled/file/index.js +1 -0
- package/dist/components/controlled/index.d.ts +12 -0
- package/dist/components/controlled/index.d.ts.map +1 -0
- package/dist/components/controlled/index.js +1 -0
- package/dist/components/controlled/input/ControlledCheckboxField.d.ts +8 -0
- package/dist/components/controlled/input/ControlledCheckboxField.d.ts.map +1 -0
- package/dist/components/controlled/input/ControlledCheckboxField.js +1 -0
- package/dist/components/controlled/input/ControlledNumberField.d.ts +8 -0
- package/dist/components/controlled/input/ControlledNumberField.d.ts.map +1 -0
- package/dist/components/controlled/input/ControlledNumberField.js +1 -0
- package/dist/components/controlled/input/ControlledPasswordField.d.ts +8 -0
- package/dist/components/controlled/input/ControlledPasswordField.d.ts.map +1 -0
- package/dist/components/controlled/input/ControlledPasswordField.js +1 -0
- package/dist/components/controlled/input/ControlledPhoneField.d.ts +8 -0
- package/dist/components/controlled/input/ControlledPhoneField.d.ts.map +1 -0
- package/dist/components/controlled/input/ControlledPhoneField.js +1 -0
- package/dist/components/controlled/input/ControlledRangeField.d.ts +8 -0
- package/dist/components/controlled/input/ControlledRangeField.d.ts.map +1 -0
- package/dist/components/controlled/input/ControlledRangeField.js +1 -0
- package/dist/components/controlled/input/ControlledSwitchField.d.ts +8 -0
- package/dist/components/controlled/input/ControlledSwitchField.d.ts.map +1 -0
- package/dist/components/controlled/input/ControlledSwitchField.js +1 -0
- package/dist/components/controlled/input/ControlledTextField.d.ts +8 -0
- package/dist/components/controlled/input/ControlledTextField.d.ts.map +1 -0
- package/dist/components/controlled/input/ControlledTextField.js +1 -0
- package/dist/components/controlled/input/ControlledTextareaField.d.ts +8 -0
- package/dist/components/controlled/input/ControlledTextareaField.d.ts.map +1 -0
- package/dist/components/controlled/input/ControlledTextareaField.js +1 -0
- package/dist/components/controlled/input/index.d.ts +9 -0
- package/dist/components/controlled/input/index.d.ts.map +1 -0
- package/dist/components/controlled/input/index.js +1 -0
- package/dist/components/controlled/select/ControlledComboboxField.d.ts +9 -0
- package/dist/components/controlled/select/ControlledComboboxField.d.ts.map +1 -0
- package/dist/components/controlled/select/ControlledComboboxField.js +1 -0
- package/dist/components/controlled/select/ControlledDropdownField.d.ts +9 -0
- package/dist/components/controlled/select/ControlledDropdownField.d.ts.map +1 -0
- package/dist/components/controlled/select/ControlledDropdownField.js +1 -0
- package/dist/components/controlled/select/ControlledMultiDropdownField.d.ts +9 -0
- package/dist/components/controlled/select/ControlledMultiDropdownField.d.ts.map +1 -0
- package/dist/components/controlled/select/ControlledMultiDropdownField.js +1 -0
- package/dist/components/controlled/select/ControlledRadioField.d.ts +9 -0
- package/dist/components/controlled/select/ControlledRadioField.d.ts.map +1 -0
- package/dist/components/controlled/select/ControlledRadioField.js +1 -0
- package/dist/components/controlled/select/index.d.ts +5 -0
- package/dist/components/controlled/select/index.d.ts.map +1 -0
- package/dist/components/controlled/select/index.js +1 -0
- package/dist/components/controlled/types.d.ts +23 -0
- package/dist/components/controlled/types.d.ts.map +1 -0
- package/dist/components/controlled/types.js +1 -0
- package/dist/components/form/fields/AddressFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/AddressFieldComponent.js +1 -1
- package/dist/components/form/fields/AvatarFieldComponent.d.ts +2 -2
- package/dist/components/form/fields/BadgeFieldComponent.d.ts +2 -2
- package/dist/components/form/fields/ButtonFieldComponent.d.ts +1 -9
- package/dist/components/form/fields/ButtonFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/ButtonFieldComponent.js +1 -1
- package/dist/components/form/fields/ComboboxComponent.d.ts.map +1 -1
- package/dist/components/form/fields/CurrencyFieldComponent.d.ts +1 -9
- package/dist/components/form/fields/CurrencyFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/CurrencyFieldComponent.js +1 -1
- package/dist/components/form/fields/DateFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/DateFieldComponent.js +1 -1
- package/dist/components/form/fields/DocumentFieldComponent.d.ts +47 -0
- package/dist/components/form/fields/DocumentFieldComponent.d.ts.map +1 -0
- package/dist/components/form/fields/DocumentFieldComponent.js +1 -0
- package/dist/components/form/fields/DropdownComponent.d.ts.map +1 -1
- package/dist/components/form/fields/DropdownComponent.js +1 -1
- package/dist/components/form/fields/FileFieldComponent.d.ts +31 -15
- package/dist/components/form/fields/FileFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/FileFieldComponent.js +1 -1
- package/dist/components/form/fields/GeoPointFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/GeoPointFieldComponent.js +1 -1
- package/dist/components/form/fields/HiddenFieldComponent.d.ts +1 -1
- package/dist/components/form/fields/HiddenFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/HiddenFieldComponent.js +1 -1
- package/dist/components/form/fields/ImageFieldComponent.d.ts +8 -14
- package/dist/components/form/fields/ImageFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/ImageFieldComponent.js +1 -1
- package/dist/components/form/fields/MapFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/MapFieldComponent.js +1 -1
- package/dist/components/form/fields/MultiDropdownComponent.js +1 -1
- package/dist/components/form/fields/MultiInputTextFieldComponent.d.ts +1 -9
- package/dist/components/form/fields/MultiInputTextFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/MultiInputTextFieldComponent.js +1 -1
- package/dist/components/form/fields/NumberFieldComponent.d.ts +2 -0
- package/dist/components/form/fields/NumberFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/NumberFieldComponent.js +1 -1
- package/dist/components/form/fields/PasswordFieldComponent.d.ts +1 -9
- package/dist/components/form/fields/PasswordFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/PhoneNumberComponent.d.ts +1 -9
- package/dist/components/form/fields/PhoneNumberComponent.d.ts.map +1 -1
- package/dist/components/form/fields/PhoneNumberComponent.js +1 -1
- package/dist/components/form/fields/RadioFieldComponent.d.ts +1 -9
- package/dist/components/form/fields/RadioFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/ReferenceFieldComponent.d.ts +33 -12
- package/dist/components/form/fields/ReferenceFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/ReferenceFieldComponent.js +1 -1
- package/dist/components/form/fields/RichTextComponent.d.ts +32 -0
- package/dist/components/form/fields/RichTextComponent.d.ts.map +1 -0
- package/dist/components/form/fields/RichTextComponent.js +1 -0
- package/dist/components/form/fields/SwitchFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/TextAreaComponent.d.ts +1 -9
- package/dist/components/form/fields/TextAreaComponent.d.ts.map +1 -1
- package/dist/components/form/fields/TextAreaComponent.js +1 -1
- package/dist/components/form/fields/TextFieldComponent.d.ts +1 -9
- package/dist/components/form/fields/TextFieldComponent.d.ts.map +1 -1
- package/dist/components/form/fields/index.d.ts +4 -2
- package/dist/components/form/fields/index.d.ts.map +1 -1
- package/dist/components/form/fields/index.js +1 -1
- package/dist/components/form/fields/internal/TiptapEditor.d.ts +13 -0
- package/dist/components/form/fields/internal/TiptapEditor.d.ts.map +1 -0
- package/dist/components/form/fields/internal/TiptapEditor.js +52 -0
- package/dist/components/form/index.d.ts +10 -0
- package/dist/components/form/index.d.ts.map +1 -0
- package/dist/components/form/index.js +1 -0
- package/dist/components/form/internal/ImageViewerDialog.d.ts +1 -1
- package/dist/components/form/internal/ImageViewerDialog.d.ts.map +1 -1
- package/dist/components/index.d.ts +8 -2
- package/dist/components/index.d.ts.map +1 -1
- package/dist/components/index.js +1 -1
- package/dist/contexts/UploadContext.d.ts +16 -0
- package/dist/contexts/UploadContext.d.ts.map +1 -0
- package/dist/contexts/UploadContext.js +1 -0
- package/dist/contexts/index.d.ts +3 -0
- package/dist/contexts/index.d.ts.map +1 -0
- package/dist/contexts/index.js +1 -0
- package/dist/forms/hooks/index.d.ts +2 -0
- package/dist/forms/hooks/index.d.ts.map +1 -1
- package/dist/forms/hooks/index.js +1 -1
- package/dist/forms/hooks/useController.d.ts +29 -0
- package/dist/forms/hooks/useController.d.ts.map +1 -0
- package/dist/forms/hooks/useController.js +1 -0
- package/dist/forms/hooks/useEntityField.d.ts.map +1 -1
- package/dist/forms/hooks/useEntityField.js +1 -1
- package/dist/forms/hooks/useEntityForm.d.ts +8 -76
- package/dist/forms/hooks/useEntityForm.d.ts.map +1 -1
- package/dist/forms/hooks/useEntityForm.js +1 -1
- package/dist/forms/index.d.ts +6 -4
- package/dist/forms/index.d.ts.map +1 -1
- package/dist/forms/index.js +1 -1
- package/dist/forms/types.d.ts +31 -5
- package/dist/forms/types.d.ts.map +1 -1
- package/dist/forms/utils/getFieldsForOperation.d.ts +5 -5
- package/dist/forms/utils/getFieldsForOperation.d.ts.map +1 -1
- package/dist/forms/utils/getFieldsForOperation.js +1 -1
- package/dist/forms/utils/index.d.ts +9 -5
- package/dist/forms/utils/index.d.ts.map +1 -1
- package/dist/forms/utils/index.js +1 -1
- package/dist/forms/utils/isFieldEditable.d.ts +0 -8
- package/dist/forms/utils/isFieldEditable.d.ts.map +1 -1
- package/dist/forms/utils/optionHelpers.d.ts +54 -0
- package/dist/forms/utils/optionHelpers.d.ts.map +1 -0
- package/dist/forms/utils/optionHelpers.js +1 -0
- package/dist/forms/utils/translateFieldLabel.d.ts +70 -0
- package/dist/forms/utils/translateFieldLabel.d.ts.map +1 -0
- package/dist/forms/utils/translateFieldLabel.js +1 -0
- package/dist/forms/utils/validateEntity.d.ts +5 -2
- package/dist/forms/utils/validateEntity.d.ts.map +1 -1
- package/dist/forms/utils/validateEntity.js +1 -1
- package/dist/hooks/index.d.ts +3 -0
- package/dist/hooks/index.d.ts.map +1 -0
- package/dist/hooks/index.js +1 -0
- package/dist/hooks/useFileUpload.d.ts +67 -0
- package/dist/hooks/useFileUpload.d.ts.map +1 -0
- package/dist/hooks/useFileUpload.js +1 -0
- package/dist/index.d.ts +15 -5
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -1
- package/dist/stores/FormStore.d.ts +78 -0
- package/dist/stores/FormStore.d.ts.map +1 -0
- package/dist/stores/FormStore.js +1 -0
- package/dist/stores/UploadStore.d.ts +105 -0
- package/dist/stores/UploadStore.d.ts.map +1 -0
- package/dist/stores/UploadStore.js +1 -0
- package/dist/stores/index.d.ts +11 -0
- package/dist/stores/index.d.ts.map +1 -0
- package/dist/stores/index.js +1 -0
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/dist/useCrud.d.ts +32 -74
- package/dist/useCrud.d.ts.map +1 -1
- package/dist/useCrud.js +1 -1
- package/dist/useCrudCardList.d.ts +62 -0
- package/dist/useCrudCardList.d.ts.map +1 -0
- package/dist/useCrudCardList.js +1 -0
- package/dist/useCrudList.d.ts +61 -0
- package/dist/useCrudList.d.ts.map +1 -0
- package/dist/useCrudList.js +1 -0
- package/dist/utils/fileStorage.d.ts +58 -0
- package/dist/utils/fileStorage.d.ts.map +1 -0
- package/dist/utils/fileStorage.js +1 -0
- package/dist/utils/imageProcessing.d.ts +1 -1
- package/dist/utils/imageProcessing.d.ts.map +1 -1
- package/dist/utils/imageProcessing.js +1 -1
- package/dist/utils/imageStorage.d.ts +1 -10
- package/dist/utils/imageStorage.d.ts.map +1 -1
- package/dist/utils/imageStorage.js +1 -1
- package/dist/utils/mergeWithOptimistic.d.ts +27 -0
- package/dist/utils/mergeWithOptimistic.d.ts.map +1 -0
- package/dist/utils/mergeWithOptimistic.js +1 -0
- package/dist/utils/uploadValidation.d.ts +37 -0
- package/dist/utils/uploadValidation.d.ts.map +1 -0
- package/dist/utils/uploadValidation.js +1 -0
- package/package.json +22 -5
- package/dist/components/ControlledFields.d.ts +0 -49
- package/dist/components/ControlledFields.d.ts.map +0 -1
- package/dist/components/ControlledFields.js +0 -1
- package/dist/context/FormUploadContext.d.ts +0 -36
- package/dist/context/FormUploadContext.d.ts.map +0 -1
- package/dist/context/FormUploadContext.js +0 -1
- package/dist/context/index.d.ts +0 -2
- package/dist/context/index.d.ts.map +0 -1
- package/dist/context/index.js +0 -1
- package/dist/forms/utils/createEntitySchema.d.ts +0 -53
- package/dist/forms/utils/createEntitySchema.d.ts.map +0 -1
- package/dist/forms/utils/createEntitySchema.js +0 -1
- package/dist/forms/utils/normalizeToFieldConfig.d.ts +0 -47
- package/dist/forms/utils/normalizeToFieldConfig.d.ts.map +0 -1
- package/dist/forms/utils/normalizeToFieldConfig.js +0 -1
package/dist/useCrud.d.ts
CHANGED
|
@@ -1,94 +1,52 @@
|
|
|
1
|
-
import type { dndevSchema, Entity, FeatureStatus } from '@donotdev/core';
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
1
|
+
import type { dndevSchema, Entity, FeatureStatus, OperationSchemas, CrudAPI } from '@donotdev/core';
|
|
2
|
+
import type { CrudServiceInterface, CacheOptions } from './CrudService';
|
|
3
|
+
import type { BackendType } from './CrudStore';
|
|
4
|
+
export declare const EMPTY_DATA: Record<string, unknown>;
|
|
5
|
+
export declare const EMPTY_OPTIMISTIC: Record<string, unknown>;
|
|
6
|
+
/**
|
|
7
|
+
* Get the current CrudService instance (for use in callbacks)
|
|
8
|
+
*/
|
|
9
|
+
export declare function getCrudServiceInstance(): CrudServiceInterface | null;
|
|
4
10
|
export interface UseCrudOptions<T> {
|
|
5
11
|
backend?: BackendType;
|
|
6
12
|
schema?: dndevSchema<T>;
|
|
7
13
|
/** Entity definition - auto-generates schema if schema not provided */
|
|
8
14
|
entity?: Entity;
|
|
9
|
-
/** TanStack Query stale time in ms (default:
|
|
15
|
+
/** TanStack Query stale time in ms (default: Infinity) */
|
|
10
16
|
staleTime?: number;
|
|
11
17
|
/** Disable caching (bypass TanStack Query) */
|
|
12
18
|
noCache?: boolean;
|
|
13
19
|
}
|
|
14
20
|
/**
|
|
15
|
-
* CRUD API return type -
|
|
16
|
-
|
|
21
|
+
* CRUD API return type - Single Document & Actions
|
|
22
|
+
*/
|
|
23
|
+
/**
|
|
24
|
+
* CRUD API return type - Single Document & Actions
|
|
17
25
|
*/
|
|
18
|
-
export interface UseCrudReturn<T> {
|
|
19
|
-
/**
|
|
20
|
-
|
|
21
|
-
/**
|
|
22
|
-
|
|
23
|
-
/**
|
|
24
|
-
|
|
25
|
-
/**
|
|
26
|
-
|
|
27
|
-
/** Fetch single document by ID */
|
|
28
|
-
get: (id: string) => Promise<T | null>;
|
|
29
|
-
/** Set/replace document by ID */
|
|
30
|
-
set: (id: string, data: T) => Promise<void>;
|
|
31
|
-
/** Partial update document by ID */
|
|
32
|
-
update: (id: string, data: Partial<T>) => Promise<void>;
|
|
33
|
-
/** Delete document by ID */
|
|
34
|
-
delete: (id: string) => Promise<void>;
|
|
35
|
-
/** Add new document (auto-generated ID) */
|
|
36
|
-
add: (data: T) => Promise<string>;
|
|
37
|
-
/** Query collection with filters */
|
|
38
|
-
query: (options: QueryOptions) => Promise<T[]>;
|
|
39
|
-
/** Subscribe to document changes */
|
|
40
|
-
subscribe: (id: string, callback: (data: T | null, error?: Error) => void) => () => void;
|
|
41
|
-
/** Subscribe to collection changes */
|
|
42
|
-
subscribeToCollection: (options: QueryOptions, callback: (data: T[], error?: Error) => void) => () => void;
|
|
43
|
-
/** Invalidate cache for this collection (TanStack Query) */
|
|
44
|
-
invalidate: () => Promise<void>;
|
|
45
|
-
/** Whether CRUD is available and operational (status === 'ready') */
|
|
46
|
-
isAvailable: boolean;
|
|
26
|
+
export interface UseCrudReturn<T> extends CrudAPI<T> {
|
|
27
|
+
/** @internal Collection name */
|
|
28
|
+
_collection: string;
|
|
29
|
+
/** @internal Generated schemas */
|
|
30
|
+
_schemas: OperationSchemas | undefined;
|
|
31
|
+
/** @internal Cache options */
|
|
32
|
+
_cacheOptions: CacheOptions;
|
|
33
|
+
/** @internal Store data for collection */
|
|
34
|
+
_storeData: Record<string, unknown>;
|
|
47
35
|
}
|
|
48
36
|
/**
|
|
49
|
-
* React hook for CRUD
|
|
50
|
-
*
|
|
51
|
-
* Collection-scoped hook that returns full CRUD API for a specific collection.
|
|
52
|
-
* Uses unified FeatureStatus enum for lifecycle management.
|
|
53
|
-
*
|
|
54
|
-
* **Usage:**
|
|
55
|
-
* ```typescript
|
|
56
|
-
* // With entity (auto-generates schema, derives collection, defaults to 'firestore' backend)
|
|
57
|
-
* const { status, data, get, set, query } = useCrud(carEntity);
|
|
37
|
+
* React hook for CRUD Actions & Single Documents
|
|
58
38
|
*
|
|
59
|
-
*
|
|
60
|
-
*
|
|
61
|
-
*
|
|
62
|
-
*
|
|
63
|
-
* const { status, data, get, set, query } = useCrud('cars', { entity: carEntity });
|
|
64
|
-
*
|
|
65
|
-
* // With explicit schema
|
|
66
|
-
* const { status, data, get, set, query } = useCrud('cars', { schema: CarSchema });
|
|
67
|
-
*
|
|
68
|
-
* // Check availability
|
|
69
|
-
* if (!isAvailable) return <Degraded />;
|
|
70
|
-
* if (status === 'initializing') return <Loader />;
|
|
71
|
-
*
|
|
72
|
-
* // Use CRUD operations
|
|
73
|
-
* const car = await get('car-123');
|
|
74
|
-
* await set('car-123', { make: 'Toyota', model: 'Camry' });
|
|
75
|
-
* ```
|
|
76
|
-
*
|
|
77
|
-
* **Status values:**
|
|
78
|
-
* - `initializing`: CRUD service loading
|
|
79
|
-
* - `ready`: Fully operational
|
|
80
|
-
* - `degraded`: Feature unavailable (no schema, no consent)
|
|
81
|
-
* - `error`: Error occurred
|
|
39
|
+
* Use this hook for:
|
|
40
|
+
* - Checking feature status: `const status = useCrud('status');`
|
|
41
|
+
* - Adding, Updating, Deleting items
|
|
42
|
+
* - Fetching a single document
|
|
82
43
|
*
|
|
83
44
|
* @template T - Document type for this collection
|
|
84
|
-
* @param entityOrCollection - Entity definition
|
|
85
|
-
* @param options - Configuration options
|
|
86
|
-
* @returns
|
|
87
|
-
*
|
|
88
|
-
* @version 0.0.5
|
|
89
|
-
* @since 0.0.1
|
|
90
|
-
* @author AMBROISE PARK Consulting
|
|
45
|
+
* @param entityOrCollection - Entity definition or collection name
|
|
46
|
+
* @param options - Configuration options
|
|
47
|
+
* @returns CRUD Actions API
|
|
91
48
|
*/
|
|
49
|
+
export declare function useCrud(key: 'status'): FeatureStatus;
|
|
92
50
|
export declare function useCrud<T = unknown>(entity: Entity, options?: UseCrudOptions<T>): UseCrudReturn<T>;
|
|
93
51
|
export declare function useCrud<T = unknown>(collection: string, options?: UseCrudOptions<T>): UseCrudReturn<T>;
|
|
94
52
|
//# sourceMappingURL=useCrud.d.ts.map
|
package/dist/useCrud.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useCrud.d.ts","sourceRoot":"","sources":["../src/useCrud.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"useCrud.d.ts","sourceRoot":"","sources":["../src/useCrud.ts"],"names":[],"mappings":"AAwBA,OAAO,KAAK,EACV,WAAW,EACX,MAAM,EACN,aAAa,EACb,gBAAgB,EAChB,OAAO,EACR,MAAM,gBAAgB,CAAC;AAKxB,OAAO,KAAK,EAAE,oBAAoB,EAAgB,YAAY,EAAE,MAAM,eAAe,CAAC;AACtF,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAK/C,eAAO,MAAM,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAM,CAAC;AACtD,eAAO,MAAM,gBAAgB,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAM,CAAC;AAM5D;;GAEG;AACH,wBAAgB,sBAAsB,IAAI,oBAAoB,GAAG,IAAI,CAEpE;AAMD,MAAM,WAAW,cAAc,CAAC,CAAC;IAC/B,OAAO,CAAC,EAAE,WAAW,CAAC;IACtB,MAAM,CAAC,EAAE,WAAW,CAAC,CAAC,CAAC,CAAC;IACxB,uEAAuE;IACvE,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,0DAA0D;IAC1D,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,8CAA8C;IAC9C,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED;;GAEG;AACH;;GAEG;AACH,MAAM,WAAW,aAAa,CAAC,CAAC,CAAE,SAAQ,OAAO,CAAC,CAAC,CAAC;IAElD,gCAAgC;IAChC,WAAW,EAAE,MAAM,CAAC;IACpB,kCAAkC;IAClC,QAAQ,EAAE,gBAAgB,GAAG,SAAS,CAAC;IACvC,8BAA8B;IAC9B,aAAa,EAAE,YAAY,CAAC;IAC5B,0CAA0C;IAC1C,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACrC;AAMD;;;;;;;;;;;;GAYG;AACH,wBAAgB,OAAO,CAAC,GAAG,EAAE,QAAQ,GAAG,aAAa,CAAC;AACtD,wBAAgB,OAAO,CAAC,CAAC,GAAG,OAAO,EACjC,MAAM,EAAE,MAAM,EACd,OAAO,CAAC,EAAE,cAAc,CAAC,CAAC,CAAC,GAC1B,aAAa,CAAC,CAAC,CAAC,CAAC;AACpB,wBAAgB,OAAO,CAAC,CAAC,GAAG,OAAO,EACjC,UAAU,EAAE,MAAM,EAClB,OAAO,CAAC,EAAE,cAAc,CAAC,CAAC,CAAC,GAC1B,aAAa,CAAC,CAAC,CAAC,CAAC"}
|
package/dist/useCrud.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use client";import{useEffect as
|
|
1
|
+
"use client";import{useEffect as B,useMemo as y,useCallback as n}from"react";import{useFeatureConsent as L,FRAMEWORK_FEATURES as j,FEATURE_STATUS as f,handleError as V,isClient as W,createSchemas as Z,DEGRADED_CRUD_API as $}from"@donotdev/core";import{getCrudService as H}from"./CrudService";import{useCrudStore as a}from"./CrudStore";const J={},ee={};let U=null,v=null,D=!1;function o(){return U}function te(u,i={}){const m=L(j.CRUD),P=a(e=>e.crudService),E=m&&!P,h=m?E?f.INITIALIZING:f.READY:f.DEGRADED;if(u==="status")return h;const S=typeof u=="object"?u:i.entity,t=typeof u=="string"?u:u.collection,d=i.backend||"functions",g=i.noCache??!1,T=i.staleTime,l=y(()=>({noCache:g,staleTime:T}),[g,T]),s=y(()=>{if(i.schema){const e=i.schema;return{create:e,draft:e,update:e,get:e,list:e,listCard:e,delete:e}}if(S)return Z(S)},[i.schema?"custom":S?.name,t]),b=a(e=>e.collections[t]?.data||J),w=a(e=>e.collections[t]?.loading||!1),A=a(e=>e.collections[t]?.error||null),F=a(e=>e.collections[t]?.data.current||null);B(()=>{if(!W()||!m||!s)return;const{crudService:e,backend:c}=a.getState();e&&c===d||v||(v=(async()=>{try{const r=H();U=r,r.setStore(a),await r.initialize(d),D=!1,a.getState().setBackend(d),a.getState().setCrudService(r)}catch(r){D||(V(r,{userMessage:"Failed to initialize CRUD service.",context:{backend:d,collection:t},severity:"error"}),D=!0)}finally{v=null}})())},[m,d,t,s?"hasSchema":"noSchema"]);const C=E||w,k=h===f.READY,x=n(async e=>{const c=o();return!c||!s?null:c.get(t,e,s.get,l)},[t,s?"hasSchema":"noSchema",l]),M=n(async(e,c)=>{const r=o();if(!r||!s)return;const G=c?.status==="draft"?s.draft:s.create;await r.set(t,e,c,G)},[t,s?"hasSchema":"noSchema"]),N=n(async(e,c)=>{const r=o();r&&await r.update(t,e,c)},[t]),z=n(async e=>{const c=o();c&&await c.delete(t,e)},[t]),Y=n(async e=>{const c=o();if(!c||!s)return"";const R=e?.status==="draft"?s.draft:s.create;return c.add(t,e,R)},[t,s?"hasSchema":"noSchema"]),q=n(async e=>{const c=o();return!c||!s?[]:c.query(t,e,s.list,l)},[t,s?"hasSchema":"noSchema",l]),p=n((e,c)=>{const r=o();return!r||!s?()=>{}:r.subscribe(t,e,c,s.get)},[t,s?"hasSchema":"noSchema"]),_=n((e,c)=>{const r=o();return!r||!s?()=>{}:r.subscribeToCollection(t,e,c,s.list)},[t,s?"hasSchema":"noSchema"]),I=n(async()=>{const e=o();e&&await e.invalidateCollection(t)},[t]);return k?{status:f.READY,data:F,loading:C,error:A,get:x,set:M,update:N,delete:z,add:Y,query:q,subscribe:p,subscribeToCollection:_,invalidate:I,isAvailable:!0,_collection:t,_schemas:s,_cacheOptions:l,_storeData:b}:{...$,status:h,loading:C,error:A,subscribe:p,subscribeToCollection:_,invalidate:I,_collection:t,_schemas:s,_cacheOptions:l,_storeData:b}}export{J as EMPTY_DATA,ee as EMPTY_OPTIMISTIC,o as getCrudServiceInstance,te as useCrud};
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview useCrudCardList Hook - Optimized Card List Management
|
|
3
|
+
* @description Specialized hook for fetching lists of entities optimized for card views.
|
|
4
|
+
* Uses TanStack Query for reactive loading states.
|
|
5
|
+
* Fetches only the fields defined in `listCardFields` (or `listFields`) to reduce payload size.
|
|
6
|
+
*
|
|
7
|
+
* @version 0.1.0
|
|
8
|
+
* @since 0.0.1
|
|
9
|
+
* @author AMBROISE PARK Consulting
|
|
10
|
+
*/
|
|
11
|
+
import type { Entity, FeatureStatus } from '@donotdev/core';
|
|
12
|
+
import type { UseCrudOptions } from './useCrud';
|
|
13
|
+
export interface UseCrudCardListOptions<T> extends UseCrudOptions<T> {
|
|
14
|
+
/** Automatically fetch data on mount (default: true) */
|
|
15
|
+
enabled?: boolean;
|
|
16
|
+
}
|
|
17
|
+
export interface UseCrudCardListReturn<T> {
|
|
18
|
+
status: FeatureStatus;
|
|
19
|
+
data: {
|
|
20
|
+
items: T[];
|
|
21
|
+
} | null;
|
|
22
|
+
/** True during initial fetch (show skeletons) */
|
|
23
|
+
loading: boolean;
|
|
24
|
+
/** True during background refetch (show subtle indicator) */
|
|
25
|
+
fetching: boolean;
|
|
26
|
+
error: Error | null;
|
|
27
|
+
/** Manual refresh function */
|
|
28
|
+
mutate: () => Promise<void>;
|
|
29
|
+
isAvailable: boolean;
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* React hook for fetching a list of entities optimized for Card views
|
|
33
|
+
*
|
|
34
|
+
* Use this hook for:
|
|
35
|
+
* - Public-facing grids
|
|
36
|
+
* - Dashboard widgets
|
|
37
|
+
* - Summary lists
|
|
38
|
+
*
|
|
39
|
+
* @template T - Document type
|
|
40
|
+
* @param entityOrCollection - Entity definition or collection name
|
|
41
|
+
* @param options - Configuration options
|
|
42
|
+
* @returns List data and control methods
|
|
43
|
+
*
|
|
44
|
+
* @example
|
|
45
|
+
* ```typescript
|
|
46
|
+
* const { data, loading, fetching } = useCrudCardList(carEntity);
|
|
47
|
+
*
|
|
48
|
+
* if (loading) return <Skeletons />;
|
|
49
|
+
*
|
|
50
|
+
* return (
|
|
51
|
+
* <Grid>
|
|
52
|
+
* {data?.items.map(car => <Card key={car.id} title={car.make} />)}
|
|
53
|
+
* </Grid>
|
|
54
|
+
* );
|
|
55
|
+
* ```
|
|
56
|
+
*/
|
|
57
|
+
export declare function useCrudCardList<T extends {
|
|
58
|
+
id: string;
|
|
59
|
+
} = {
|
|
60
|
+
id: string;
|
|
61
|
+
}>(entityOrCollection: Entity | string, options?: UseCrudCardListOptions<T>): UseCrudCardListReturn<T>;
|
|
62
|
+
//# sourceMappingURL=useCrudCardList.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useCrudCardList.d.ts","sourceRoot":"","sources":["../src/useCrudCardList.ts"],"names":[],"mappings":"AACA;;;;;;;;;GASG;AAKH,OAAO,KAAK,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,gBAAgB,CAAC;AAO5D,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAEhD,MAAM,WAAW,sBAAsB,CAAC,CAAC,CAAE,SAAQ,cAAc,CAAC,CAAC,CAAC;IAClE,wDAAwD;IACxD,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED,MAAM,WAAW,qBAAqB,CAAC,CAAC;IACtC,MAAM,EAAE,aAAa,CAAC;IACtB,IAAI,EAAE;QAAE,KAAK,EAAE,CAAC,EAAE,CAAA;KAAE,GAAG,IAAI,CAAC;IAC5B,iDAAiD;IACjD,OAAO,EAAE,OAAO,CAAC;IACjB,6DAA6D;IAC7D,QAAQ,EAAE,OAAO,CAAC;IAClB,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IACpB,8BAA8B;IAC9B,MAAM,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5B,WAAW,EAAE,OAAO,CAAC;CACtB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AACH,wBAAgB,eAAe,CAAC,CAAC,SAAS;IAAE,EAAE,EAAE,MAAM,CAAA;CAAE,GAAG;IAAE,EAAE,EAAE,MAAM,CAAA;CAAE,EACvE,kBAAkB,EAAE,MAAM,GAAG,MAAM,EACnC,OAAO,GAAE,sBAAsB,CAAC,CAAC,CAAM,GACtC,qBAAqB,CAAC,CAAC,CAAC,CAsF1B"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{useMemo as y,useCallback as T}from"react";import{useQuery as _}from"@donotdev/core";import{useCrudStore as I}from"./CrudStore";import{useCrud as h,getCrudServiceInstance as L,EMPTY_OPTIMISTIC as A}from"./useCrud";import{mergeWithOptimistic as D}from"./utils/mergeWithOptimistic";function K(p,n={}){const C=n.enabled??!0,i=h("status"),e=i==="ready",g=h(p,n),{error:c,invalidate:u,_collection:r,_schemas:a,_cacheOptions:l,_storeData:m}=g,d=I(s=>s.collections[r]?.optimistic||A),t=y(()=>{if(!e||!a)return null;const s=L();return s?s.getListQueryOptions(r,{},a.listCard,l,"listCard"):null},[e,r,l,a?"hasSchema":"noSchema"]),{data:o,isLoading:b,isFetching:q,error:v,refetch:f}=_({queryKey:t?.queryKey??["crud",r,"disabled"],queryFn:t?.queryFn??(()=>Promise.resolve([])),staleTime:t?.staleTime,enabled:C&&!!t}),O=y(()=>!o||!e?[]:D(o,d,m),[o,d,m,e]),S=T(async()=>{e&&(await u(),await f())},[u,f,e]);return e?{status:i,data:{items:O},loading:b,fetching:q,error:v??c,mutate:S,isAvailable:!0}:{status:i,data:{items:[]},loading:!1,fetching:!1,error:c,mutate:async()=>{},isAvailable:!1}}export{K as useCrudCardList};
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview useCrudList Hook - Collection Management
|
|
3
|
+
* @description Specialized hook for fetching and managing lists of entities.
|
|
4
|
+
* Uses TanStack Query for reactive loading states.
|
|
5
|
+
*
|
|
6
|
+
* @version 0.2.0
|
|
7
|
+
* @since 0.0.1
|
|
8
|
+
* @author AMBROISE PARK Consulting
|
|
9
|
+
*/
|
|
10
|
+
import type { Entity, FeatureStatus } from '@donotdev/core';
|
|
11
|
+
import type { UseCrudOptions } from './useCrud';
|
|
12
|
+
export interface UseCrudListOptions<T> extends UseCrudOptions<T> {
|
|
13
|
+
/** Automatically fetch data on mount (default: true) */
|
|
14
|
+
enabled?: boolean;
|
|
15
|
+
}
|
|
16
|
+
export interface UseCrudListReturn<T> {
|
|
17
|
+
status: FeatureStatus;
|
|
18
|
+
data: {
|
|
19
|
+
items: T[];
|
|
20
|
+
} | null;
|
|
21
|
+
/** True during initial fetch (show skeletons) */
|
|
22
|
+
loading: boolean;
|
|
23
|
+
/** True during background refetch (show subtle indicator) */
|
|
24
|
+
fetching: boolean;
|
|
25
|
+
error: Error | null;
|
|
26
|
+
/** Manual refresh function */
|
|
27
|
+
mutate: () => Promise<void>;
|
|
28
|
+
isAvailable: boolean;
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* React hook for fetching and managing a list of entities
|
|
32
|
+
*
|
|
33
|
+
* Use this hook for:
|
|
34
|
+
* - Admin tables
|
|
35
|
+
* - Data grids
|
|
36
|
+
* - Lists of items
|
|
37
|
+
*
|
|
38
|
+
* @template T - Document type
|
|
39
|
+
* @param entityOrCollection - Entity definition or collection name
|
|
40
|
+
* @param options - Configuration options
|
|
41
|
+
* @returns List data and control methods
|
|
42
|
+
*
|
|
43
|
+
* @example
|
|
44
|
+
* ```typescript
|
|
45
|
+
* const { data, loading, mutate } = useCrudList(carEntity);
|
|
46
|
+
*
|
|
47
|
+
* if (loading) return <Loader />;
|
|
48
|
+
*
|
|
49
|
+
* return (
|
|
50
|
+
* <ul>
|
|
51
|
+
* {data?.items.map(car => <li key={car.id}>{car.make}</li>)}
|
|
52
|
+
* </ul>
|
|
53
|
+
* );
|
|
54
|
+
* ```
|
|
55
|
+
*/
|
|
56
|
+
export declare function useCrudList<T extends {
|
|
57
|
+
id: string;
|
|
58
|
+
} = {
|
|
59
|
+
id: string;
|
|
60
|
+
}>(entityOrCollection: Entity | string, options?: UseCrudListOptions<T>): UseCrudListReturn<T>;
|
|
61
|
+
//# sourceMappingURL=useCrudList.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useCrudList.d.ts","sourceRoot":"","sources":["../src/useCrudList.ts"],"names":[],"mappings":"AACA;;;;;;;;GAQG;AAKH,OAAO,KAAK,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,gBAAgB,CAAC;AAO5D,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAEhD,MAAM,WAAW,kBAAkB,CAAC,CAAC,CAAE,SAAQ,cAAc,CAAC,CAAC,CAAC;IAC9D,wDAAwD;IACxD,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED,MAAM,WAAW,iBAAiB,CAAC,CAAC;IAClC,MAAM,EAAE,aAAa,CAAC;IACtB,IAAI,EAAE;QAAE,KAAK,EAAE,CAAC,EAAE,CAAA;KAAE,GAAG,IAAI,CAAC;IAC5B,iDAAiD;IACjD,OAAO,EAAE,OAAO,CAAC;IACjB,6DAA6D;IAC7D,QAAQ,EAAE,OAAO,CAAC;IAClB,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IACpB,8BAA8B;IAC9B,MAAM,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5B,WAAW,EAAE,OAAO,CAAC;CACtB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AACH,wBAAgB,WAAW,CAAC,CAAC,SAAS;IAAE,EAAE,EAAE,MAAM,CAAA;CAAE,GAAG;IAAE,EAAE,EAAE,MAAM,CAAA;CAAE,EACnE,kBAAkB,EAAE,MAAM,GAAG,MAAM,EACnC,OAAO,GAAE,kBAAkB,CAAC,CAAC,CAAM,GAClC,iBAAiB,CAAC,CAAC,CAAC,CAsFtB"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{useMemo as y,useCallback as T}from"react";import{useQuery as _}from"@donotdev/core";import{useCrudStore as I}from"./CrudStore";import{useCrud as h,getCrudServiceInstance as L,EMPTY_OPTIMISTIC as A}from"./useCrud";import{mergeWithOptimistic as D}from"./utils/mergeWithOptimistic";function K(p,n={}){const g=n.enabled??!0,i=h("status"),e=i==="ready",b=h(p,n),{error:c,invalidate:u,_collection:t,_schemas:a,_cacheOptions:l,_storeData:m}=b,d=I(s=>s.collections[t]?.optimistic||A),r=y(()=>{if(!e||!a)return null;const s=L();return s?s.getListQueryOptions(t,{},a.list,l,"list"):null},[e,t,l,a?"hasSchema":"noSchema"]),{data:o,isLoading:q,isFetching:v,error:C,refetch:f}=_({queryKey:r?.queryKey??["crud",t,"disabled"],queryFn:r?.queryFn??(()=>Promise.resolve([])),staleTime:r?.staleTime,enabled:g&&!!r}),O=y(()=>!o||!e?[]:D(o,d,m),[o,d,m,e]),S=T(async()=>{e&&(await u(),await f())},[u,f,e]);return e?{status:i,data:{items:O},loading:q,fetching:v,error:C??c,mutate:S,isAvailable:!0}:{status:i,data:{items:[]},loading:!1,fetching:!1,error:c,mutate:async()=>{},isAvailable:!1}}export{K as useCrudList};
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import type { UploadProgressCallback } from '@donotdev/firebase';
|
|
2
|
+
import type { FileAsset } from '@donotdev/types';
|
|
3
|
+
export type { FileAsset };
|
|
4
|
+
export interface UploadProgress {
|
|
5
|
+
bytesTransferred: number;
|
|
6
|
+
totalBytes: number;
|
|
7
|
+
progress: number;
|
|
8
|
+
}
|
|
9
|
+
export interface UploadFileOptions {
|
|
10
|
+
/** Storage path (default: 'uploads/files') */
|
|
11
|
+
storagePath?: string;
|
|
12
|
+
/** Custom filename (default: timestamp_originalname) */
|
|
13
|
+
filename?: string;
|
|
14
|
+
/** Progress callback */
|
|
15
|
+
onProgress?: UploadProgressCallback;
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Upload a file to Firebase Storage with progress tracking
|
|
19
|
+
* Generic version for any file type (documents, PDFs, etc.)
|
|
20
|
+
*/
|
|
21
|
+
export declare function uploadFile(file: File, options?: UploadFileOptions): Promise<FileAsset>;
|
|
22
|
+
/**
|
|
23
|
+
* Upload multiple files to Firebase Storage
|
|
24
|
+
*/
|
|
25
|
+
export declare function uploadFiles(files: File[], options?: UploadFileOptions): Promise<FileAsset[]>;
|
|
26
|
+
/**
|
|
27
|
+
* Delete a file from Firebase Storage
|
|
28
|
+
*/
|
|
29
|
+
export declare function deleteFile(asset: FileAsset): Promise<void>;
|
|
30
|
+
/**
|
|
31
|
+
* Generate a unique file ID
|
|
32
|
+
*/
|
|
33
|
+
export declare function generateFileId(): string;
|
|
34
|
+
/**
|
|
35
|
+
* Get file extension from filename
|
|
36
|
+
*/
|
|
37
|
+
export declare function getFileExtension(filename: string): string;
|
|
38
|
+
/**
|
|
39
|
+
* Get file icon based on MIME type or extension
|
|
40
|
+
*/
|
|
41
|
+
export declare function getFileIcon(mimeType?: string, filename?: string): string;
|
|
42
|
+
/**
|
|
43
|
+
* Format file size for display
|
|
44
|
+
*/
|
|
45
|
+
export declare function formatFileSize(bytes: number): string;
|
|
46
|
+
/**
|
|
47
|
+
* Document MIME types
|
|
48
|
+
*/
|
|
49
|
+
export declare const DOCUMENT_MIME_TYPES: string[];
|
|
50
|
+
/**
|
|
51
|
+
* Document file extensions
|
|
52
|
+
*/
|
|
53
|
+
export declare const DOCUMENT_EXTENSIONS: string[];
|
|
54
|
+
/**
|
|
55
|
+
* Get accept string for document inputs
|
|
56
|
+
*/
|
|
57
|
+
export declare function getDocumentAcceptString(): string;
|
|
58
|
+
//# sourceMappingURL=fileStorage.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"fileStorage.d.ts","sourceRoot":"","sources":["../../src/utils/fileStorage.ts"],"names":[],"mappings":"AAeA,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,oBAAoB,CAAC;AACjE,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,iBAAiB,CAAC;AAEjD,YAAY,EAAE,SAAS,EAAE,CAAC;AAE1B,MAAM,WAAW,cAAc;IAC7B,gBAAgB,EAAE,MAAM,CAAC;IACzB,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,iBAAiB;IAChC,8CAA8C;IAC9C,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,wDAAwD;IACxD,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,wBAAwB;IACxB,UAAU,CAAC,EAAE,sBAAsB,CAAC;CACrC;AAYD;;;GAGG;AACH,wBAAsB,UAAU,CAC9B,IAAI,EAAE,IAAI,EACV,OAAO,GAAE,iBAAsB,GAC9B,OAAO,CAAC,SAAS,CAAC,CAkCpB;AAED;;GAEG;AACH,wBAAsB,WAAW,CAC/B,KAAK,EAAE,IAAI,EAAE,EACb,OAAO,GAAE,iBAAsB,GAC9B,OAAO,CAAC,SAAS,EAAE,CAAC,CA4BtB;AAED;;GAEG;AACH,wBAAsB,UAAU,CAAC,KAAK,EAAE,SAAS,GAAG,OAAO,CAAC,IAAI,CAAC,CAWhE;AAED;;GAEG;AACH,wBAAgB,cAAc,IAAI,MAAM,CAEvC;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAGzD;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,QAAQ,CAAC,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,GAAG,MAAM,CA4CxE;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAMpD;AAED;;GAEG;AACH,eAAO,MAAM,mBAAmB,UAY/B,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,mBAAmB,UAY/B,CAAC;AAEF;;GAEG;AACH,wBAAgB,uBAAuB,IAAI,MAAM,CAEhD"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use client";import{handleError as p}from"@donotdev/core";import{uploadFileResumable as u,deleteFileByUrl as d}from"@donotdev/firebase";function f(e){return e.replace(/[^a-zA-Z0-9.-]/g,"_").replace(/_{2,}/g,"_").toLowerCase()}async function x(e,t={}){const{storagePath:r="uploads/files",filename:n,onProgress:a}=t,o=Date.now(),i=f(e.name),c=n||`${o}_${i}`,l=`${r}/${c}`;try{const{promise:s}=u(e,{basePath:r,filename:c,onProgress:a,metadata:{contentType:e.type}});return{url:(await s).url,filename:e.name,size:e.size,mimeType:e.type,uploadedAt:new Date().toISOString()}}catch(s){throw p(s,{userMessage:"Failed to upload file",severity:"error",context:{filename:e.name,fileSize:e.size}})}}async function v(e,t={}){const r=[],n=e.reduce((o,i)=>o+i.size,0);let a=0;for(const o of e){const i=t.onProgress?l=>{const s=l.bytesTransferred/l.totalBytes*o.size;t.onProgress({bytesTransferred:a+s,totalBytes:n,progress:(a+s)/n*100})}:void 0,c=await x(o,{...t,onProgress:i});r.push(c),a+=o.size}return r}async function M(e){try{await d(e.url)}catch(t){throw p(t,{userMessage:"Failed to delete file",severity:"error",context:{url:e.url,filename:e.filename}}),t}}function S(){return`${Date.now()}-${Math.random().toString(36).slice(2,9)}`}function m(e){const t=e.split(".");return t.length>1?t.pop().toLowerCase():""}function P(e,t){const r=t?m(t):"";if(e){if(e.startsWith("image/"))return"image";if(e.startsWith("video/"))return"video";if(e.startsWith("audio/"))return"audio";if(e==="application/pdf")return"pdf";if(e.includes("word")||e.includes("document"))return"doc";if(e.includes("excel")||e.includes("spreadsheet"))return"xls";if(e.includes("powerpoint")||e.includes("presentation"))return"ppt"}switch(r){case"pdf":return"pdf";case"doc":case"docx":return"doc";case"xls":case"xlsx":case"csv":return"xls";case"ppt":case"pptx":return"ppt";case"md":case"txt":return"text";case"html":case"htm":return"html";case"zip":case"rar":case"7z":return"archive";default:return"file"}}function B(e){if(e===0)return"0 B";const t=1024,r=["B","KB","MB","GB"],n=Math.floor(Math.log(e)/Math.log(t));return`${parseFloat((e/Math.pow(t,n)).toFixed(1))} ${r[n]}`}const h=["application/pdf","application/msword","application/vnd.openxmlformats-officedocument.wordprocessingml.document","application/vnd.ms-excel","application/vnd.openxmlformats-officedocument.spreadsheetml.sheet","application/vnd.ms-powerpoint","application/vnd.openxmlformats-officedocument.presentationml.presentation","text/plain","text/markdown","text/html","text/csv"],g=[".pdf",".doc",".docx",".xls",".xlsx",".ppt",".pptx",".txt",".md",".html",".csv"];function E(){return[...h,...g].join(",")}export{g as DOCUMENT_EXTENSIONS,h as DOCUMENT_MIME_TYPES,M as deleteFile,B as formatFileSize,S as generateFileId,E as getDocumentAcceptString,m as getFileExtension,P as getFileIcon,x as uploadFile,v as uploadFiles};
|
|
@@ -23,7 +23,7 @@ export interface ProcessImageOptions {
|
|
|
23
23
|
thumbHeight?: number;
|
|
24
24
|
/** Target aspect ratio (default: 4/3) */
|
|
25
25
|
aspectRatio?: number;
|
|
26
|
-
/** WebP quality (0-1, default: 0.
|
|
26
|
+
/** WebP quality (0-1, default: 0.85 for full, 0.65 for thumb) */
|
|
27
27
|
quality?: number;
|
|
28
28
|
/** Add transparent background for non-matching aspect ratios */
|
|
29
29
|
transparentBackground?: boolean;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"imageProcessing.d.ts","sourceRoot":"","sources":["../../src/utils/imageProcessing.ts"],"names":[],"mappings":"AAEA;;;;;;;GAOG;AAEH,MAAM,WAAW,cAAc;IAC7B,QAAQ,EAAE,IAAI,CAAC;IACf,SAAS,EAAE,IAAI,CAAC;IAChB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,mBAAmB;IAClC,wDAAwD;IACxD,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,yDAAyD;IACzD,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,qCAAqC;IACrC,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,sCAAsC;IACtC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,yCAAyC;IACzC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB
|
|
1
|
+
{"version":3,"file":"imageProcessing.d.ts","sourceRoot":"","sources":["../../src/utils/imageProcessing.ts"],"names":[],"mappings":"AAEA;;;;;;;GAOG;AAEH,MAAM,WAAW,cAAc;IAC7B,QAAQ,EAAE,IAAI,CAAC;IACf,SAAS,EAAE,IAAI,CAAC;IAChB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,mBAAmB;IAClC,wDAAwD;IACxD,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,yDAAyD;IACzD,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,qCAAqC;IACrC,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,sCAAsC;IACtC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,yCAAyC;IACzC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,iEAAiE;IACjE,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,gEAAgE;IAChE,qBAAqB,CAAC,EAAE,OAAO,CAAC;IAChC,iEAAiE;IACjE,IAAI,CAAC,EAAE;QAAE,CAAC,EAAE,MAAM,CAAC;QAAC,CAAC,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,CAAA;KAAE,CAAC;CAChE;AAED;;GAEG;AACH,wBAAsB,YAAY,CAChC,IAAI,EAAE,IAAI,EACV,OAAO,GAAE,mBAAwB,GAChC,OAAO,CAAC,cAAc,CAAC,CAuEzB;AAwHD;;GAEG;AACH,wBAAgB,iBAAiB,CAC/B,IAAI,EAAE,IAAI,EACV,YAAY,CAAC,EAAE,MAAM,GACpB;IAAE,KAAK,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAgBpC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
async function x(t,r={}){const{maxWidth:o=1920,maxHeight:a=1440,thumbWidth:d=300,thumbHeight:i=225,aspectRatio:e=4/3,quality:h=.
|
|
1
|
+
async function x(t,r={}){const{maxWidth:o=1920,maxHeight:a=1440,thumbWidth:d=300,thumbHeight:i=225,aspectRatio:e=4/3,quality:h=.85,transparentBackground:c=!0,crop:l}=r;return new Promise((f,s)=>{const n=new Image,u=new FileReader;u.onload=w=>{n.src=w.target?.result},u.onerror=()=>s(new Error("Failed to read file")),n.onload=async()=>{try{const{width:w,height:F}=g(l?l.width:n.width,l?l.height:n.height,o,a,e),m=await b(n,w,F,e,h,c,l),v=await b(n,d,i,e,.65,c,l);f({fullBlob:m,thumbBlob:v,width:w,height:F})}catch(w){s(w)}},n.onerror=()=>s(new Error("Failed to load image")),u.readAsDataURL(t)})}function g(t,r,o,a,d){let i=t,e=r;i>o&&(e=o/i*e,i=o),e>a&&(i=a/e*i,e=a);const h=i/e;return Math.abs(h-d)>.01&&(h>d?e=i/d:i=e*d),{width:Math.round(i),height:Math.round(e)}}async function b(t,r,o,a,d,i,e){const h=document.createElement("canvas"),c=h.getContext("2d");if(!c)throw new Error("Failed to get canvas context");h.width=r,h.height=o,i?c.clearRect(0,0,r,o):(c.fillStyle="#FFFFFF",c.fillRect(0,0,r,o));let l,f,s,n;if(e)l=e.x,f=e.y,s=e.width,n=e.height;else{const u=t.width/t.height;s=t.width,n=t.height,l=0,f=0,u>a?(s=t.height*a,l=(t.width-s)/2):u<a&&(n=t.width/a,f=(t.height-n)/2)}return c.drawImage(t,l,f,s,n,0,0,r,o),new Promise((u,w)=>{h.toBlob(F=>{F?u(F):w(new Error("Failed to convert canvas to blob"))},"image/webp",d)})}function y(t,r){return t.type.startsWith("image/")?r&&t.size>r?{valid:!1,error:`File size exceeds ${(r/1048576).toFixed(1)}MB limit`}:{valid:!0}:{valid:!1,error:"File must be an image"}}export{x as processImage,y as validateImageFile};
|
|
@@ -1,13 +1,4 @@
|
|
|
1
|
-
|
|
2
|
-
* @fileoverview Image Storage Utilities
|
|
3
|
-
* @description Handle image uploads to Firebase Storage with progress tracking, WebP conversion, and thumbnails
|
|
4
|
-
* Uses @donotdev/firebase for storage operations
|
|
5
|
-
*
|
|
6
|
-
* @version 0.0.2
|
|
7
|
-
* @since 0.0.1
|
|
8
|
-
* @author AMBROISE PARK Consulting
|
|
9
|
-
*/
|
|
10
|
-
import { type UploadProgressCallback } from '@donotdev/firebase';
|
|
1
|
+
import type { UploadProgressCallback } from '@donotdev/firebase';
|
|
11
2
|
import type { Picture } from '@donotdev/types';
|
|
12
3
|
export type { Picture };
|
|
13
4
|
export interface UploadProgress {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"imageStorage.d.ts","sourceRoot":"","sources":["../../src/utils/imageStorage.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"imageStorage.d.ts","sourceRoot":"","sources":["../../src/utils/imageStorage.ts"],"names":[],"mappings":"AAkBA,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,oBAAoB,CAAC;AACjE,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAC;AAE/C,YAAY,EAAE,OAAO,EAAE,CAAC;AAExB,MAAM,WAAW,cAAc;IAC7B,gBAAgB,EAAE,MAAM,CAAC;IACzB,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,kBAAkB;IACjC,+CAA+C;IAC/C,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,wDAAwD;IACxD,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,wBAAwB;IACxB,UAAU,CAAC,EAAE,sBAAsB,CAAC;CACrC;AAYD;;;GAGG;AACH,wBAAsB,WAAW,CAC/B,QAAQ,EAAE,IAAI,EACd,SAAS,EAAE,IAAI,EACf,gBAAgB,EAAE,MAAM,EACxB,OAAO,GAAE,kBAAuB,GAC/B,OAAO,CAAC,OAAO,CAAC,CAmFlB;AAED;;GAEG;AACH,wBAAsB,WAAW,CAAC,OAAO,EAAE,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAcjE"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{uploadFileResumable as c,deleteFileByUrl as i,getFileUrl as m}from"@donotdev/firebase";
|
|
1
|
+
import{handleError as _}from"@donotdev/core";import{uploadFileResumable as c,deleteFileByUrl as i,getFileUrl as m}from"@donotdev/firebase";function F(e){return e.replace(/[^a-zA-Z0-9.-]/g,"_").replace(/_{2,}/g,"_").toLowerCase()}async function N(e,l,b,h={}){const{storagePath:r="uploads/images",filename:f,onProgress:s}=h,p=Date.now(),t=(f||`${p}_${F(b)}`).replace(/\.[^/.]+$/,""),w=`${r}/${t}_full.webp`,g=`${r}/${t}_thumb.webp`;try{const u=s?a=>{s({bytesTransferred:a.bytesTransferred,totalBytes:a.totalBytes*2,progress:a.progress*.5})}:void 0,o=new File([e],`${t}_full.webp`,{type:"image/webp"}),{promise:n}=c(o,{basePath:r,filename:`${t}_full.webp`,onProgress:u,metadata:{contentType:"image/webp"}}),d=(await n).url,y=s?a=>{s({bytesTransferred:a.bytesTransferred+e.size,totalBytes:e.size+l.size,progress:50+a.progress*.5})}:void 0,P=new File([l],`${t}_thumb.webp`,{type:"image/webp"}),{promise:U}=c(P,{basePath:r,filename:`${t}_thumb.webp`,onProgress:y,metadata:{contentType:"image/webp"}}),$=(await U).url;return{fullUrl:d,thumbUrl:$}}catch(u){try{const o=await m(w).catch(()=>null),n=await m(g).catch(()=>null);o&&await i(o).catch(()=>{}),n&&await i(n).catch(()=>{})}catch{}throw u}}async function k(e){try{await Promise.all([i(e.fullUrl),i(e.thumbUrl)])}catch(l){throw _(l,{userMessage:"Failed to delete image",severity:"error",context:{fullUrl:e.fullUrl,thumbUrl:e.thumbUrl}}),l}}export{k as deleteImage,N as uploadImage};
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview Optimistic merge utility
|
|
3
|
+
* @description Merges TanStack Query results with optimistic operations from store
|
|
4
|
+
*
|
|
5
|
+
* @version 0.0.1
|
|
6
|
+
* @since 0.0.1
|
|
7
|
+
* @author AMBROISE PARK Consulting
|
|
8
|
+
*/
|
|
9
|
+
import type { OptimisticMeta } from '../CrudStore';
|
|
10
|
+
interface WithId {
|
|
11
|
+
id: string;
|
|
12
|
+
[key: string]: unknown;
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Merge query results with optimistic operations.
|
|
16
|
+
* - Filter out items marked for deletion
|
|
17
|
+
* - Apply optimistic updates
|
|
18
|
+
* - Append optimistic adds (temp IDs)
|
|
19
|
+
*
|
|
20
|
+
* @param queryData - Data from TanStack Query cache
|
|
21
|
+
* @param optimistic - Optimistic operation metadata from store
|
|
22
|
+
* @param storeData - Current store data (for optimistic values)
|
|
23
|
+
* @returns Merged array with optimistic changes applied
|
|
24
|
+
*/
|
|
25
|
+
export declare function mergeWithOptimistic<T extends WithId>(queryData: T[], optimistic: Record<string, OptimisticMeta>, storeData?: Record<string, unknown>): T[];
|
|
26
|
+
export {};
|
|
27
|
+
//# sourceMappingURL=mergeWithOptimistic.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mergeWithOptimistic.d.ts","sourceRoot":"","sources":["../../src/utils/mergeWithOptimistic.ts"],"names":[],"mappings":"AAEA;;;;;;;GAOG;AAEH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,cAAc,CAAC;AAEnD,UAAU,MAAM;IACd,EAAE,EAAE,MAAM,CAAC;IACX,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACxB;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,mBAAmB,CAAC,CAAC,SAAS,MAAM,EAClD,SAAS,EAAE,CAAC,EAAE,EACd,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,cAAc,CAAC,EAC1C,SAAS,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAClC,CAAC,EAAE,CA4BL"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
function p(s,t,i){const n=[],d=new Set;for(const e of s){const o=t[e.id];o?.operation!=="delete"&&(o?.operation==="update"&&i?.[e.id]?n.push(i[e.id]):n.push(e),d.add(e.id))}for(const[e,o]of Object.entries(t))o.operation==="add"&&!d.has(e)&&i?.[e]&&n.push(i[e]);return n}export{p as mergeWithOptimistic};
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview Upload Validation Utilities
|
|
3
|
+
* @description Type-safe validation utilities to ensure no blob URLs reach the database.
|
|
4
|
+
* Provides security checks for Picture objects and form data validation.
|
|
5
|
+
*
|
|
6
|
+
* @version 0.0.1
|
|
7
|
+
* @since 0.0.1
|
|
8
|
+
* @author AMBROISE PARK Consulting
|
|
9
|
+
*/
|
|
10
|
+
import type { Picture } from '@donotdev/types';
|
|
11
|
+
/**
|
|
12
|
+
* Check if a URL is a valid storage URL (not a blob URL)
|
|
13
|
+
* @param url - URL to check
|
|
14
|
+
* @returns true if URL is a storage URL (https://), false if blob URL or invalid
|
|
15
|
+
*/
|
|
16
|
+
export declare function isStorageUrl(url: string): boolean;
|
|
17
|
+
/**
|
|
18
|
+
* Validate that a Picture object has valid storage URLs
|
|
19
|
+
* @param picture - Picture object to validate
|
|
20
|
+
* @returns true if both fullUrl and thumbUrl are valid storage URLs
|
|
21
|
+
*/
|
|
22
|
+
export declare function validatePicture(picture: Picture): boolean;
|
|
23
|
+
/**
|
|
24
|
+
* Recursively check for blob URLs in form data
|
|
25
|
+
* Returns array of paths where blob URLs were found
|
|
26
|
+
* @param data - Data to check (can be nested object/array)
|
|
27
|
+
* @param path - Current path in the data structure (for error messages)
|
|
28
|
+
* @returns Array of paths where blob URLs were found
|
|
29
|
+
*/
|
|
30
|
+
export declare function checkForBlobUrls(data: any, path?: string): string[];
|
|
31
|
+
/**
|
|
32
|
+
* Check if form data contains any blob URLs
|
|
33
|
+
* @param data - Form data to check
|
|
34
|
+
* @returns true if any blob URLs found, false otherwise
|
|
35
|
+
*/
|
|
36
|
+
export declare function hasBlobUrls(data: any): boolean;
|
|
37
|
+
//# sourceMappingURL=uploadValidation.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"uploadValidation.d.ts","sourceRoot":"","sources":["../../src/utils/uploadValidation.ts"],"names":[],"mappings":"AAGA;;;;;;;;GAQG;AAEH,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAC;AAE/C;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAGjD;AAED;;;;GAIG;AACH,wBAAgB,eAAe,CAAC,OAAO,EAAE,OAAO,GAAG,OAAO,CAKzD;AAED;;;;;;GAMG;AACH,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,GAAG,EAAE,IAAI,SAAK,GAAG,MAAM,EAAE,CA2C/D;AAED;;;;GAIG;AACH,wBAAgB,WAAW,CAAC,IAAI,EAAE,GAAG,GAAG,OAAO,CAE9C"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use client";function l(r){return!r||typeof r!="string"?!1:r.startsWith("https://")&&!r.startsWith("blob:")}function i(r){return!r||typeof r!="object"?!1:l(r.fullUrl)&&l(r.thumbUrl)}function f(r,n=""){const e=[];if(r==null)return e;if(typeof r=="string")return r.startsWith("blob:")&&e.push(n||"root"),e;if(typeof r!="object")return e;if(Array.isArray(r))r.forEach((t,o)=>{const s=n?`${n}[${o}]`:`[${o}]`;e.push(...f(t,s))});else if(r.fullUrl!==void 0&&r.thumbUrl!==void 0){if(!l(r.fullUrl)||!l(r.thumbUrl)){const t=n||"root";e.push(`${t}.fullUrl or ${t}.thumbUrl contains blob URL`)}}else Object.entries(r).forEach(([t,o])=>{const s=n?`${n}.${t}`:t;e.push(...f(o,s))});return e}function u(r){return f(r).length>0}export{f as checkForBlobUrls,u as hasBlobUrls,l as isStorageUrl,i as validatePicture};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@donotdev/crud",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.7",
|
|
4
4
|
"private": false,
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "SEE LICENSE IN LICENSE.md",
|
|
@@ -49,8 +49,8 @@
|
|
|
49
49
|
"type-check": "tsc --noEmit"
|
|
50
50
|
},
|
|
51
51
|
"dependencies": {
|
|
52
|
-
"@donotdev/components": "^0.0.
|
|
53
|
-
"@donotdev/core": "^0.0.
|
|
52
|
+
"@donotdev/components": "^0.0.13",
|
|
53
|
+
"@donotdev/core": "^0.0.14",
|
|
54
54
|
"@hookform/resolvers": "^5.2.2",
|
|
55
55
|
"react-easy-crop": "^5.5.6"
|
|
56
56
|
},
|
|
@@ -61,7 +61,24 @@
|
|
|
61
61
|
"react": "^19.2.3",
|
|
62
62
|
"react-dom": "^19.2.3",
|
|
63
63
|
"react-hook-form": "^7.71.0",
|
|
64
|
-
"valibot": "^1.2.0"
|
|
64
|
+
"valibot": "^1.2.0",
|
|
65
|
+
"@tiptap/react": "^3.16.0",
|
|
66
|
+
"@tiptap/pm": "^3.16.0",
|
|
67
|
+
"@tiptap/starter-kit": "^3.16.0",
|
|
68
|
+
"@tiptap/extension-placeholder": "^3.16.0"
|
|
65
69
|
},
|
|
66
|
-
"peerDependenciesMeta": {
|
|
70
|
+
"peerDependenciesMeta": {
|
|
71
|
+
"@tiptap/react": {
|
|
72
|
+
"optional": true
|
|
73
|
+
},
|
|
74
|
+
"@tiptap/pm": {
|
|
75
|
+
"optional": true
|
|
76
|
+
},
|
|
77
|
+
"@tiptap/starter-kit": {
|
|
78
|
+
"optional": true
|
|
79
|
+
},
|
|
80
|
+
"@tiptap/extension-placeholder": {
|
|
81
|
+
"optional": true
|
|
82
|
+
}
|
|
83
|
+
}
|
|
67
84
|
}
|