@scality/data-browser-library 1.0.0-preview.13 → 1.0.0-preview.15
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/components/DataBrowserUI.d.ts +15 -8
- package/dist/components/DataBrowserUI.js +79 -55
- package/dist/components/Editor.d.ts +1 -1
- package/dist/components/Editor.js +3 -3
- package/dist/components/__tests__/BucketCreate.test.js +102 -102
- package/dist/components/__tests__/BucketDetails.test.js +121 -122
- package/dist/components/__tests__/BucketLifecycleFormPage.test.js +177 -177
- package/dist/components/__tests__/BucketLifecycleList.test.js +85 -85
- package/dist/components/__tests__/BucketList.test.js +175 -176
- package/dist/components/__tests__/BucketNotificationCreatePage.test.js +84 -84
- package/dist/components/__tests__/BucketOverview.test.js +256 -200
- package/dist/components/__tests__/BucketPolicyPage.test.js +62 -62
- package/dist/components/__tests__/BucketReplicationFormPage.test.js +542 -542
- package/dist/components/__tests__/BucketReplicationList.test.js +106 -106
- package/dist/components/__tests__/CreateFolderButton.test.js +56 -56
- package/dist/components/__tests__/DeleteBucketButton.test.js +62 -62
- package/dist/components/__tests__/DeleteBucketConfigRuleButton.test.js +47 -47
- package/dist/components/__tests__/DeleteObjectButton.test.js +63 -63
- package/dist/components/__tests__/EmptyBucketButton.test.js +56 -56
- package/dist/components/__tests__/MetadataSearch.test.js +65 -65
- package/dist/components/__tests__/ObjectList.test.js +251 -250
- package/dist/components/__tests__/UploadButton.test.js +45 -45
- package/dist/components/buckets/BucketCreate.d.ts +2 -2
- package/dist/components/buckets/BucketCreate.js +41 -41
- package/dist/components/buckets/BucketDetails.d.ts +2 -2
- package/dist/components/buckets/BucketDetails.js +48 -36
- package/dist/components/buckets/BucketLifecycleFormPage.js +161 -160
- package/dist/components/buckets/BucketLifecycleList.d.ts +2 -2
- package/dist/components/buckets/BucketLifecycleList.js +46 -46
- package/dist/components/buckets/BucketList.d.ts +2 -2
- package/dist/components/buckets/BucketList.js +28 -27
- package/dist/components/buckets/BucketLocation.js +3 -3
- package/dist/components/buckets/BucketOverview.d.ts +1 -1
- package/dist/components/buckets/BucketOverview.js +62 -62
- package/dist/components/buckets/BucketPage.js +19 -11
- package/dist/components/buckets/BucketPolicyButton.js +2 -2
- package/dist/components/buckets/BucketPolicyPage.js +27 -25
- package/dist/components/buckets/BucketReplicationFormPage.js +133 -132
- package/dist/components/buckets/BucketReplicationList.d.ts +2 -2
- package/dist/components/buckets/BucketReplicationList.js +41 -41
- package/dist/components/buckets/BucketVersioning.js +11 -11
- package/dist/components/buckets/DeleteBucketButton.js +5 -5
- package/dist/components/buckets/DeleteBucketConfigRuleButton.d.ts +2 -2
- package/dist/components/buckets/DeleteBucketConfigRuleButton.js +1 -1
- package/dist/components/buckets/EmptyBucketButton.js +19 -19
- package/dist/components/buckets/EmptyBucketSummary.d.ts +1 -1
- package/dist/components/buckets/EmptyBucketSummary.js +1 -1
- package/dist/components/buckets/EmptyBucketSummaryList.js +22 -22
- package/dist/components/buckets/__tests__/BucketVersioning.test.js +45 -45
- package/dist/components/buckets/notifications/BucketNotificationCreatePage.js +34 -33
- package/dist/components/buckets/notifications/EventsSection.js +144 -28
- package/dist/components/buckets/notifications/__tests__/events.test.d.ts +1 -0
- package/dist/components/buckets/notifications/__tests__/events.test.js +56 -0
- package/dist/components/buckets/notifications/events.d.ts +71 -7
- package/dist/components/buckets/notifications/events.js +98 -16
- package/dist/components/index.d.ts +23 -22
- package/dist/components/index.js +3 -2
- package/dist/components/layouts/ArrowNavigation.d.ts +1 -2
- package/dist/components/layouts/ArrowNavigation.js +3 -3
- package/dist/components/layouts/BrowserPageLayout.d.ts +2 -3
- package/dist/components/layouts/BrowserPageLayout.js +1 -1
- package/dist/components/objects/CreateFolderButton.d.ts +2 -2
- package/dist/components/objects/CreateFolderButton.js +9 -9
- package/dist/components/objects/DeleteObjectButton.d.ts +1 -1
- package/dist/components/objects/DeleteObjectButton.js +20 -20
- package/dist/components/objects/ObjectDetails/ObjectMetadata.d.ts +1 -1
- package/dist/components/objects/ObjectDetails/ObjectMetadata.js +56 -56
- package/dist/components/objects/ObjectDetails/ObjectSummary.d.ts +1 -1
- package/dist/components/objects/ObjectDetails/ObjectSummary.js +39 -39
- package/dist/components/objects/ObjectDetails/ObjectTags.d.ts +1 -1
- package/dist/components/objects/ObjectDetails/ObjectTags.js +25 -25
- package/dist/components/objects/ObjectDetails/__tests__/ObjectDetails.test.js +119 -119
- package/dist/components/objects/ObjectDetails/__tests__/ObjectSummary.test.js +211 -211
- package/dist/components/objects/ObjectDetails/index.d.ts +1 -1
- package/dist/components/objects/ObjectDetails/index.js +30 -30
- package/dist/components/objects/ObjectList.d.ts +5 -5
- package/dist/components/objects/ObjectList.js +112 -111
- package/dist/components/objects/ObjectLock/EditRetentionButton.js +3 -3
- package/dist/components/objects/ObjectLock/ObjectLockRetentionSettings.js +14 -14
- package/dist/components/objects/ObjectLock/ObjectLockSettings.d.ts +1 -1
- package/dist/components/objects/ObjectLock/ObjectLockSettings.js +29 -28
- package/dist/components/objects/ObjectLock/ObjectLockSettingsUtils.d.ts +1 -1
- package/dist/components/objects/ObjectLock/ObjectLockSettingsUtils.js +6 -6
- package/dist/components/objects/ObjectLock/__tests__/EditRetentionButton.test.js +50 -50
- package/dist/components/objects/ObjectLock/__tests__/ObjectLockSettings.test.js +77 -77
- package/dist/components/objects/ObjectPage.js +5 -4
- package/dist/components/objects/UploadButton.d.ts +3 -3
- package/dist/components/objects/UploadButton.js +5 -5
- package/dist/components/providers/DataBrowserProvider.d.ts +15 -4
- package/dist/components/providers/DataBrowserProvider.js +33 -11
- package/dist/components/search/MetadataSearch.js +26 -25
- package/dist/components/search/SearchHints.js +1 -1
- package/dist/components/ui/ArrayFieldActions.js +4 -4
- package/dist/components/ui/ConfirmDeleteRuleModal.d.ts +1 -1
- package/dist/components/ui/ConfirmDeleteRuleModal.js +1 -1
- package/dist/components/ui/DeleteObjectModalContent.d.ts +1 -1
- package/dist/components/ui/DeleteObjectModalContent.js +12 -12
- package/dist/components/ui/FilterFormSection.d.ts +2 -2
- package/dist/components/ui/FilterFormSection.js +29 -29
- package/dist/components/ui/Search.elements.d.ts +1 -1
- package/dist/components/ui/Search.elements.js +7 -7
- package/dist/components/ui/Table.elements.js +5 -5
- package/dist/config/factory.d.ts +23 -10
- package/dist/config/factory.js +22 -7
- package/dist/config/types.d.ts +20 -3
- package/dist/contexts/DataBrowserUICustomizationContext.d.ts +2 -2
- package/dist/hooks/__tests__/useISVBucketDetection.test.js +41 -41
- package/dist/hooks/__tests__/useIsBucketEmpty.test.js +25 -25
- package/dist/hooks/bucketConfiguration.d.ts +1 -1
- package/dist/hooks/bucketConfiguration.js +48 -48
- package/dist/hooks/bucketOperations.d.ts +1 -1
- package/dist/hooks/bucketOperations.js +6 -6
- package/dist/hooks/factories/__tests__/useCreateS3FunctionMutationHook.test.js +78 -78
- package/dist/hooks/factories/__tests__/useCreateS3InfiniteQueryHook.test.js +78 -78
- package/dist/hooks/factories/__tests__/useCreateS3LoginHook.test.js +42 -42
- package/dist/hooks/factories/__tests__/useCreateS3MutationHook.test.js +61 -61
- package/dist/hooks/factories/__tests__/useCreateS3QueryHook.test.js +63 -63
- package/dist/hooks/factories/index.d.ts +4 -4
- package/dist/hooks/factories/useCreateS3InfiniteQueryHook.d.ts +2 -2
- package/dist/hooks/factories/useCreateS3InfiniteQueryHook.js +15 -12
- package/dist/hooks/factories/useCreateS3LoginHook.d.ts +2 -2
- package/dist/hooks/factories/useCreateS3MutationHook.d.ts +3 -3
- package/dist/hooks/factories/useCreateS3MutationHook.js +6 -1
- package/dist/hooks/factories/useCreateS3QueryHook.d.ts +2 -2
- package/dist/hooks/factories/useCreateS3QueryHook.js +8 -5
- package/dist/hooks/index.d.ts +14 -13
- package/dist/hooks/index.js +2 -1
- package/dist/hooks/loginOperations.d.ts +1 -1
- package/dist/hooks/loginOperations.js +1 -1
- package/dist/hooks/objectOperations.d.ts +2 -2
- package/dist/hooks/objectOperations.js +49 -49
- package/dist/hooks/presignedOperations.d.ts +2 -2
- package/dist/hooks/presignedOperations.js +3 -3
- package/dist/hooks/useBatchObjectLegalHold.js +7 -4
- package/dist/hooks/useDataBrowserNavigate.d.ts +14 -0
- package/dist/hooks/useDataBrowserNavigate.js +24 -0
- package/dist/hooks/useDeleteBucketConfigRule.d.ts +2 -2
- package/dist/hooks/useDeleteBucketConfigRule.js +4 -4
- package/dist/hooks/useEmptyBucket.js +10 -10
- package/dist/hooks/useISVBucketDetection.js +3 -3
- package/dist/hooks/useIsBucketEmpty.js +4 -4
- package/dist/hooks/useLoginMutation.d.ts +1 -1
- package/dist/hooks/useLoginMutation.js +1 -1
- package/dist/hooks/useS3Client.d.ts +5 -0
- package/dist/hooks/useS3Client.js +3 -2
- package/dist/hooks/useS3ConfigSwitch.d.ts +11 -0
- package/dist/hooks/useS3ConfigSwitch.js +37 -0
- package/dist/index.d.ts +6 -6
- package/dist/test/msw/handlers/deleteBucket.d.ts +1 -1
- package/dist/test/msw/handlers/deleteBucket.js +20 -10
- package/dist/test/msw/handlers/getBucketAcl.d.ts +1 -1
- package/dist/test/msw/handlers/getBucketAcl.js +29 -17
- package/dist/test/msw/handlers/getBucketLocation.d.ts +1 -1
- package/dist/test/msw/handlers/getBucketLocation.js +29 -15
- package/dist/test/msw/handlers/getBucketPolicy.d.ts +1 -1
- package/dist/test/msw/handlers/getBucketPolicy.js +52 -32
- package/dist/test/msw/handlers/headObject.d.ts +1 -1
- package/dist/test/msw/handlers/headObject.js +31 -13
- package/dist/test/msw/handlers/listBuckets.d.ts +1 -1
- package/dist/test/msw/handlers/listBuckets.js +5 -3
- package/dist/test/msw/handlers/listObjectVersions.d.ts +1 -1
- package/dist/test/msw/handlers/listObjectVersions.js +38 -26
- package/dist/test/msw/handlers/listObjects.d.ts +1 -1
- package/dist/test/msw/handlers/listObjects.js +35 -23
- package/dist/test/msw/handlers/objectLegalHold.d.ts +1 -1
- package/dist/test/msw/handlers/objectLegalHold.js +31 -16
- package/dist/test/msw/handlers/objectRetention.d.ts +1 -1
- package/dist/test/msw/handlers/objectRetention.js +31 -17
- package/dist/test/msw/handlers/putBucketAcl.d.ts +1 -1
- package/dist/test/msw/handlers/putBucketAcl.js +29 -14
- package/dist/test/msw/handlers/putObject.d.ts +1 -1
- package/dist/test/msw/handlers/putObject.js +27 -12
- package/dist/test/msw/handlers.d.ts +3 -3
- package/dist/test/msw/handlers.js +72 -49
- package/dist/test/msw/index.d.ts +2 -2
- package/dist/test/msw/server.d.ts +1 -1
- package/dist/test/msw/server.js +1 -1
- package/dist/test/msw/utils.js +2 -2
- package/dist/test/setup.d.ts +1 -1
- package/dist/test/setup.js +19 -19
- package/dist/test/testUtils.d.ts +9 -15
- package/dist/test/testUtils.js +78 -92
- package/dist/test/utils/errorHandling.test.js +119 -119
- package/dist/types/index.d.ts +6 -31
- package/dist/utils/__tests__/s3ConfigIdentifier.test.d.ts +1 -0
- package/dist/utils/__tests__/s3ConfigIdentifier.test.js +429 -0
- package/dist/utils/constants.js +8 -8
- package/dist/utils/deletion/index.d.ts +2 -2
- package/dist/utils/deletion/messages.d.ts +1 -1
- package/dist/utils/deletion/messages.js +4 -4
- package/dist/utils/errorHandling.d.ts +3 -3
- package/dist/utils/errorHandling.js +6 -6
- package/dist/utils/hooks.js +8 -8
- package/dist/utils/index.d.ts +5 -4
- package/dist/utils/index.js +2 -0
- package/dist/utils/proxyMiddleware.d.ts +1 -1
- package/dist/utils/proxyMiddleware.js +6 -11
- package/dist/utils/s3Client.d.ts +2 -2
- package/dist/utils/s3Client.js +1 -1
- package/dist/utils/s3ConfigIdentifier.d.ts +68 -0
- package/dist/utils/s3ConfigIdentifier.js +55 -0
- package/dist/utils/s3RuleUtils.d.ts +5 -5
- package/dist/utils/s3RuleUtils.js +17 -17
- package/dist/utils/useSupportedNotificationEvents.d.ts +6 -0
- package/dist/utils/useSupportedNotificationEvents.js +7 -0
- package/package.json +2 -2
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
2
2
|
import { usePrefixWithSlash, useQueryParams } from "../../utils/hooks.js";
|
|
3
3
|
import { useCallback, useEffect, useRef, useState } from "react";
|
|
4
|
-
import { useLocation
|
|
4
|
+
import { useLocation } from "react-router";
|
|
5
|
+
import { useDataBrowserNavigate } from "../../hooks/useDataBrowserNavigate.js";
|
|
5
6
|
import { SearchContainer, SearchInputContainer, searchIcon } from "../ui/Search.elements.js";
|
|
6
7
|
import { Box, Button, Input } from "@scality/core-ui/dist/next";
|
|
7
8
|
import { Icon } from "@scality/core-ui";
|
|
@@ -9,43 +10,43 @@ import { SearchHints } from "./SearchHints.js";
|
|
|
9
10
|
const METADATA_SEARCH_HINT_ITEMS = [
|
|
10
11
|
{
|
|
11
12
|
label: 'files with extension ".pdf"',
|
|
12
|
-
query:
|
|
13
|
+
query: 'key like /pdf$/'
|
|
13
14
|
},
|
|
14
15
|
{
|
|
15
|
-
label:
|
|
16
|
-
query:
|
|
16
|
+
label: 'files bigger than 1MB',
|
|
17
|
+
query: 'content-length > 1000000'
|
|
17
18
|
},
|
|
18
19
|
{
|
|
19
|
-
label:
|
|
20
|
-
query:
|
|
20
|
+
label: 'file names that contain scality (case insensitive)',
|
|
21
|
+
query: 'key like /scality/i'
|
|
21
22
|
},
|
|
22
23
|
{
|
|
23
|
-
label:
|
|
24
|
+
label: 'files with metadata field color set to green',
|
|
24
25
|
query: 'x-amz-meta-color="green"'
|
|
25
26
|
},
|
|
26
27
|
{
|
|
27
|
-
label:
|
|
28
|
-
query:
|
|
28
|
+
label: 'files tagged with color blue',
|
|
29
|
+
query: 'tags.color=blue'
|
|
29
30
|
},
|
|
30
31
|
{
|
|
31
|
-
label:
|
|
32
|
-
query:
|
|
32
|
+
label: 'PDF files (from content-type)',
|
|
33
|
+
query: 'content-type=application/pdf'
|
|
33
34
|
},
|
|
34
35
|
{
|
|
35
|
-
label:
|
|
36
|
-
query:
|
|
36
|
+
label: 'file names that contain the word Report (case sensitive)',
|
|
37
|
+
query: 'key like Report'
|
|
37
38
|
},
|
|
38
39
|
{
|
|
39
|
-
label:
|
|
40
|
+
label: 'files waiting to be replicated',
|
|
40
41
|
query: 'replication-status="PENDING"'
|
|
41
42
|
}
|
|
42
43
|
];
|
|
43
44
|
const MetadataSearch = ({ isError })=>{
|
|
44
|
-
const navigate =
|
|
45
|
+
const navigate = useDataBrowserNavigate();
|
|
45
46
|
const location = useLocation();
|
|
46
47
|
const query = useQueryParams();
|
|
47
|
-
const searchInput = query.get(
|
|
48
|
-
const [inputText, setInputText] = useState(searchInput ||
|
|
48
|
+
const searchInput = query.get('metadatasearch');
|
|
49
|
+
const [inputText, setInputText] = useState(searchInput || '');
|
|
49
50
|
const [hintsShown, setHintsShown] = useState(false);
|
|
50
51
|
const prefixWithSlash = usePrefixWithSlash();
|
|
51
52
|
const inputRef = useRef(null);
|
|
@@ -54,8 +55,8 @@ const MetadataSearch = ({ isError })=>{
|
|
|
54
55
|
e.preventDefault();
|
|
55
56
|
if (!inputText || prefixWithSlash) return;
|
|
56
57
|
const newQuery = new URLSearchParams(location.search);
|
|
57
|
-
newQuery.set(
|
|
58
|
-
navigate(
|
|
58
|
+
newQuery.set('metadatasearch', inputText);
|
|
59
|
+
navigate(`?${newQuery.toString()}`);
|
|
59
60
|
}, [
|
|
60
61
|
inputText,
|
|
61
62
|
prefixWithSlash,
|
|
@@ -80,19 +81,19 @@ const MetadataSearch = ({ isError })=>{
|
|
|
80
81
|
const handleClickOutside = (event)=>{
|
|
81
82
|
if (hintsShown && inputRef.current && hintsRef.current && !inputRef.current.contains(event.target) && !hintsRef.current.contains(event.target)) setHintsShown(false);
|
|
82
83
|
};
|
|
83
|
-
document.addEventListener(
|
|
84
|
+
document.addEventListener('mousedown', handleClickOutside);
|
|
84
85
|
return ()=>{
|
|
85
|
-
document.removeEventListener(
|
|
86
|
+
document.removeEventListener('mousedown', handleClickOutside);
|
|
86
87
|
};
|
|
87
88
|
}, [
|
|
88
89
|
hintsShown
|
|
89
90
|
]);
|
|
90
91
|
const reset = useCallback(()=>{
|
|
91
92
|
setHintsShown(false);
|
|
92
|
-
setInputText(
|
|
93
|
+
setInputText('');
|
|
93
94
|
const newQuery = new URLSearchParams(location.search);
|
|
94
|
-
newQuery.delete(
|
|
95
|
-
navigate(
|
|
95
|
+
newQuery.delete('metadatasearch');
|
|
96
|
+
navigate(`?${newQuery.toString()}`);
|
|
96
97
|
}, [
|
|
97
98
|
location,
|
|
98
99
|
navigate
|
|
@@ -135,7 +136,7 @@ const MetadataSearch = ({ isError })=>{
|
|
|
135
136
|
name: "Close"
|
|
136
137
|
}),
|
|
137
138
|
tooltip: {
|
|
138
|
-
overlay:
|
|
139
|
+
overlay: 'Reset search'
|
|
139
140
|
},
|
|
140
141
|
onClick: reset,
|
|
141
142
|
"aria-label": "Clear search input"
|
|
@@ -2,10 +2,10 @@ import { jsx, jsxs } from "react/jsx-runtime";
|
|
|
2
2
|
import { Box, Button } from "@scality/core-ui/dist/next";
|
|
3
3
|
import { Icon, spacing } from "@scality/core-ui";
|
|
4
4
|
import { convertSizeToRem } from "@scality/core-ui/dist/components/inputv2/inputv2";
|
|
5
|
-
function ArrayFieldActions({ onRemove, onAdd, canRemove, canAdd = true, showAdd, removeLabel =
|
|
5
|
+
function ArrayFieldActions({ onRemove, onAdd, canRemove, canAdd = true, showAdd, removeLabel = 'Remove', addLabel = 'Add' }) {
|
|
6
6
|
return /*#__PURE__*/ jsxs(Box, {
|
|
7
7
|
display: "flex",
|
|
8
|
-
width: convertSizeToRem(
|
|
8
|
+
width: convertSizeToRem('1/2'),
|
|
9
9
|
gap: spacing.r8,
|
|
10
10
|
justifyContent: "flex-start",
|
|
11
11
|
children: [
|
|
@@ -20,7 +20,7 @@ function ArrayFieldActions({ onRemove, onAdd, canRemove, canAdd = true, showAdd,
|
|
|
20
20
|
disabled: !canRemove,
|
|
21
21
|
tooltip: {
|
|
22
22
|
overlay: removeLabel,
|
|
23
|
-
placement:
|
|
23
|
+
placement: 'top'
|
|
24
24
|
}
|
|
25
25
|
}),
|
|
26
26
|
showAdd && /*#__PURE__*/ jsx(Button, {
|
|
@@ -33,7 +33,7 @@ function ArrayFieldActions({ onRemove, onAdd, canRemove, canAdd = true, showAdd,
|
|
|
33
33
|
"aria-label": addLabel,
|
|
34
34
|
tooltip: {
|
|
35
35
|
overlay: addLabel,
|
|
36
|
-
placement:
|
|
36
|
+
placement: 'top'
|
|
37
37
|
},
|
|
38
38
|
disabled: !canAdd
|
|
39
39
|
})
|
|
@@ -4,7 +4,7 @@ interface ConfirmDeleteRuleModalProps {
|
|
|
4
4
|
/** Rule ID to display in confirmation message */
|
|
5
5
|
ruleId: string;
|
|
6
6
|
/** Type of rule (e.g., "lifecycle", "replication") */
|
|
7
|
-
ruleType:
|
|
7
|
+
ruleType: 'lifecycle' | 'replication';
|
|
8
8
|
/** Whether deletion is in progress */
|
|
9
9
|
isDeleting: boolean;
|
|
10
10
|
/** Callback when user confirms deletion */
|
|
@@ -2,7 +2,7 @@ import { jsx, jsxs } from "react/jsx-runtime";
|
|
|
2
2
|
import { Loader, Modal, Stack, Wrap } from "@scality/core-ui";
|
|
3
3
|
import { Button } from "@scality/core-ui/dist/next";
|
|
4
4
|
function ConfirmDeleteRuleModal({ isOpen, ruleId, ruleType, isDeleting, onConfirm, onCancel }) {
|
|
5
|
-
const ruleTypeLabel =
|
|
5
|
+
const ruleTypeLabel = 'lifecycle' === ruleType ? 'Lifecycle' : 'Replication';
|
|
6
6
|
return /*#__PURE__*/ jsxs(Modal, {
|
|
7
7
|
close: onCancel,
|
|
8
8
|
isOpen: isOpen,
|
|
@@ -12,30 +12,30 @@ const Container = styled_components(Box)`
|
|
|
12
12
|
const DeleteObjectModalContent = ({ objects, onRemove })=>{
|
|
13
13
|
const columns = useMemo(()=>[
|
|
14
14
|
{
|
|
15
|
-
Header:
|
|
16
|
-
accessor:
|
|
15
|
+
Header: 'Name',
|
|
16
|
+
accessor: 'Key',
|
|
17
17
|
Cell: ({ value })=>/*#__PURE__*/ jsx(ConstrainedText, {
|
|
18
18
|
text: value,
|
|
19
19
|
lineClamp: 1
|
|
20
20
|
}),
|
|
21
|
-
id:
|
|
21
|
+
id: 'name'
|
|
22
22
|
},
|
|
23
23
|
{
|
|
24
|
-
Header:
|
|
25
|
-
accessor:
|
|
24
|
+
Header: 'Size',
|
|
25
|
+
accessor: 'Size',
|
|
26
26
|
cellStyle: {
|
|
27
|
-
textAlign:
|
|
27
|
+
textAlign: 'right'
|
|
28
28
|
},
|
|
29
29
|
Cell: ({ value })=>/*#__PURE__*/ jsx(PrettyBytes, {
|
|
30
30
|
bytes: Number(value)
|
|
31
31
|
}),
|
|
32
|
-
id:
|
|
32
|
+
id: 'size'
|
|
33
33
|
},
|
|
34
34
|
{
|
|
35
|
-
Header:
|
|
36
|
-
accessor:
|
|
35
|
+
Header: '',
|
|
36
|
+
accessor: 'type',
|
|
37
37
|
cellStyle: {
|
|
38
|
-
width:
|
|
38
|
+
width: '0.625rem'
|
|
39
39
|
},
|
|
40
40
|
Cell: (row)=>{
|
|
41
41
|
const objectKey = row.row.original.Key;
|
|
@@ -52,7 +52,7 @@ const DeleteObjectModalContent = ({ objects, onRemove })=>{
|
|
|
52
52
|
onRemove
|
|
53
53
|
]);
|
|
54
54
|
const HEADER_AND_SPACING_ROWS = 3;
|
|
55
|
-
const rowHeight =
|
|
55
|
+
const rowHeight = 'h40';
|
|
56
56
|
const tableRowHeightInRem = tableRowHeight[rowHeight];
|
|
57
57
|
return /*#__PURE__*/ jsx(Container, {
|
|
58
58
|
height: `calc(${objects.length + HEADER_AND_SPACING_ROWS} * (${tableRowHeightInRem}rem + 1px))`,
|
|
@@ -62,7 +62,7 @@ const DeleteObjectModalContent = ({ objects, onRemove })=>{
|
|
|
62
62
|
children: /*#__PURE__*/ jsx(Table.SingleSelectableContent, {
|
|
63
63
|
rowHeight: "h40",
|
|
64
64
|
separationLineVariant: "backgroundLevel3",
|
|
65
|
-
selectedId:
|
|
65
|
+
selectedId: 'Name',
|
|
66
66
|
onRowSelected: ()=>{}
|
|
67
67
|
})
|
|
68
68
|
})
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { UseFormRegisterReturn } from
|
|
1
|
+
import { UseFormRegisterReturn } from 'react-hook-form';
|
|
2
2
|
export interface FilterFormValues {
|
|
3
|
-
filterType:
|
|
3
|
+
filterType: 'none' | 'prefix' | 'tags' | 'and';
|
|
4
4
|
prefix: string;
|
|
5
5
|
tags: Array<{
|
|
6
6
|
key: string;
|
|
@@ -5,28 +5,28 @@ import { Box, Input, Select } from "@scality/core-ui/dist/next";
|
|
|
5
5
|
import { ArrayFieldActions } from "./ArrayFieldActions.js";
|
|
6
6
|
const filterTypeOptions = [
|
|
7
7
|
{
|
|
8
|
-
value:
|
|
9
|
-
label:
|
|
8
|
+
value: 'none',
|
|
9
|
+
label: 'All objects'
|
|
10
10
|
},
|
|
11
11
|
{
|
|
12
|
-
value:
|
|
13
|
-
label:
|
|
12
|
+
value: 'prefix',
|
|
13
|
+
label: 'Prefix filter'
|
|
14
14
|
},
|
|
15
15
|
{
|
|
16
|
-
value:
|
|
17
|
-
label:
|
|
16
|
+
value: 'tags',
|
|
17
|
+
label: 'Tags filter'
|
|
18
18
|
},
|
|
19
19
|
{
|
|
20
|
-
value:
|
|
21
|
-
label:
|
|
20
|
+
value: 'and',
|
|
21
|
+
label: 'Prefix and tags filter'
|
|
22
22
|
}
|
|
23
23
|
];
|
|
24
|
-
const shouldShowPrefix = (filterType)=>
|
|
25
|
-
const shouldShowTags = (filterType)=>
|
|
24
|
+
const shouldShowPrefix = (filterType)=>'prefix' === filterType || 'and' === filterType;
|
|
25
|
+
const shouldShowTags = (filterType)=>'tags' === filterType || 'and' === filterType;
|
|
26
26
|
function FilterFormSection({ filterType, onFilterTypeChange, prefixRegister, tagFields, tagKeyRegister, tagValueRegister, getTagKeyValue, getTagValueValue, appendTag, removeTag, errors, forceLabelWidth = convertRemToPixels(15) }) {
|
|
27
27
|
return /*#__PURE__*/ jsxs(FormSection, {
|
|
28
28
|
title: {
|
|
29
|
-
name:
|
|
29
|
+
name: 'Filter'
|
|
30
30
|
},
|
|
31
31
|
forceLabelWidth: forceLabelWidth,
|
|
32
32
|
children: [
|
|
@@ -50,7 +50,7 @@ function FilterFormSection({ filterType, onFilterTypeChange, prefixRegister, tag
|
|
|
50
50
|
direction: "horizontal",
|
|
51
51
|
error: errors?.prefix?.message,
|
|
52
52
|
helpErrorPosition: "bottom",
|
|
53
|
-
required:
|
|
53
|
+
required: 'prefix' === filterType,
|
|
54
54
|
content: /*#__PURE__*/ jsx(Input, {
|
|
55
55
|
id: "prefix",
|
|
56
56
|
placeholder: "folder/",
|
|
@@ -109,8 +109,8 @@ function FilterFormSection({ filterType, onFilterTypeChange, prefixRegister, tag
|
|
|
109
109
|
showAdd: index === tagFields.length - 1,
|
|
110
110
|
onRemove: ()=>removeTag(index),
|
|
111
111
|
onAdd: ()=>appendTag({
|
|
112
|
-
key:
|
|
113
|
-
value:
|
|
112
|
+
key: '',
|
|
113
|
+
value: ''
|
|
114
114
|
}),
|
|
115
115
|
canRemove: tagFields.length > 1,
|
|
116
116
|
canAdd: !!getTagKeyValue(index) && !!getTagValueValue(index),
|
|
@@ -126,32 +126,32 @@ function FilterFormSection({ filterType, onFilterTypeChange, prefixRegister, tag
|
|
|
126
126
|
});
|
|
127
127
|
}
|
|
128
128
|
const createFilterValidationSchema = (Joi)=>({
|
|
129
|
-
filterType: Joi.string().valid(
|
|
130
|
-
prefix: Joi.when(
|
|
131
|
-
is:
|
|
129
|
+
filterType: Joi.string().valid('none', 'prefix', 'tags', 'and').required(),
|
|
130
|
+
prefix: Joi.when('filterType', {
|
|
131
|
+
is: 'prefix',
|
|
132
132
|
then: Joi.string().required().min(1).messages({
|
|
133
|
-
|
|
134
|
-
|
|
133
|
+
'string.empty': 'Prefix is required when using prefix filter',
|
|
134
|
+
'string.min': 'Prefix is required when using prefix filter'
|
|
135
135
|
}),
|
|
136
|
-
otherwise: Joi.when(
|
|
137
|
-
is:
|
|
138
|
-
then: Joi.string().allow(
|
|
136
|
+
otherwise: Joi.when('filterType', {
|
|
137
|
+
is: 'and',
|
|
138
|
+
then: Joi.string().allow('').optional(),
|
|
139
139
|
otherwise: Joi.any()
|
|
140
140
|
})
|
|
141
141
|
}),
|
|
142
|
-
tags: Joi.when(
|
|
143
|
-
is: Joi.valid(
|
|
142
|
+
tags: Joi.when('filterType', {
|
|
143
|
+
is: Joi.valid('tags', 'and'),
|
|
144
144
|
then: Joi.array().items(Joi.object({
|
|
145
145
|
key: Joi.string().required().max(128).messages({
|
|
146
|
-
|
|
147
|
-
|
|
146
|
+
'string.empty': 'Tag key is required',
|
|
147
|
+
'string.max': 'Tag key must not exceed 128 characters'
|
|
148
148
|
}),
|
|
149
149
|
value: Joi.string().required().max(256).messages({
|
|
150
|
-
|
|
151
|
-
|
|
150
|
+
'string.empty': 'Tag value is required',
|
|
151
|
+
'string.max': 'Tag value must not exceed 256 characters'
|
|
152
152
|
})
|
|
153
153
|
})).min(1).messages({
|
|
154
|
-
|
|
154
|
+
'array.min': 'At least one tag is required when using tag filter'
|
|
155
155
|
}),
|
|
156
156
|
otherwise: Joi.array().optional()
|
|
157
157
|
})
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { IconColor, IconName } from
|
|
1
|
+
import { IconColor, IconName } from '@scality/core-ui/dist/components/icon/Icon.component';
|
|
2
2
|
export declare const SearchContainer: import("styled-components").StyledComponent<"form", any, {
|
|
3
3
|
isHidden?: boolean;
|
|
4
4
|
}, never>;
|
|
@@ -5,7 +5,7 @@ const SearchContainer = styled_components.form`
|
|
|
5
5
|
display: flex;
|
|
6
6
|
max-width: 600px;
|
|
7
7
|
margin-right: ${spacing.r20};
|
|
8
|
-
visibility: ${(props)=>props.isHidden ?
|
|
8
|
+
visibility: ${(props)=>props.isHidden ? 'hidden' : 'visible'};
|
|
9
9
|
gap: ${spacing.r8};
|
|
10
10
|
`;
|
|
11
11
|
const SearchInputContainer = styled_components.div`
|
|
@@ -44,16 +44,16 @@ const HintsTitle = styled_components.div`
|
|
|
44
44
|
`;
|
|
45
45
|
const searchIcon = ({ isMetadata, isError })=>{
|
|
46
46
|
if (isError) return {
|
|
47
|
-
name:
|
|
48
|
-
color:
|
|
47
|
+
name: 'Close',
|
|
48
|
+
color: 'statusCritical'
|
|
49
49
|
};
|
|
50
50
|
if (isMetadata) return {
|
|
51
|
-
name:
|
|
52
|
-
color:
|
|
51
|
+
name: 'Check',
|
|
52
|
+
color: 'statusHealthy'
|
|
53
53
|
};
|
|
54
54
|
return {
|
|
55
|
-
name:
|
|
56
|
-
color:
|
|
55
|
+
name: 'Search',
|
|
56
|
+
color: 'textSecondary'
|
|
57
57
|
};
|
|
58
58
|
};
|
|
59
59
|
export { HintItem, HintsContainer, HintsTitle, SearchContainer, SearchInputContainer, searchIcon };
|
|
@@ -47,16 +47,16 @@ const Row = ({ children, ...props })=>/*#__PURE__*/ jsx(Box, {
|
|
|
47
47
|
});
|
|
48
48
|
const RawKey = styled_components.div`
|
|
49
49
|
color: ${(props)=>props.principal ? props.theme.textPrimary : props.theme?.textSecondary};
|
|
50
|
-
font-weight: ${(props)=>props.principal ?
|
|
50
|
+
font-weight: ${(props)=>props.principal ? 'bold' : 'normal'};
|
|
51
51
|
${(props)=>props.required ? `
|
|
52
52
|
&:after {
|
|
53
53
|
content: '*';
|
|
54
54
|
}
|
|
55
|
-
` :
|
|
55
|
+
` : ''}
|
|
56
56
|
`;
|
|
57
57
|
const Key = styled_components(RawKey)`
|
|
58
58
|
&& {
|
|
59
|
-
flex: ${(props)=>props.size ||
|
|
59
|
+
flex: ${(props)=>props.size || '0.35'};
|
|
60
60
|
min-width: 0;
|
|
61
61
|
}
|
|
62
62
|
`;
|
|
@@ -76,12 +76,12 @@ const TableContainer = ({ children, ...props })=>/*#__PURE__*/ jsx(Box, {
|
|
|
76
76
|
});
|
|
77
77
|
const GroupValues = styled_components.div`
|
|
78
78
|
display: flex;
|
|
79
|
-
flex: ${(props)=>props.size ||
|
|
79
|
+
flex: ${(props)=>props.size || '0.65'};
|
|
80
80
|
justify-content: space-between;
|
|
81
81
|
align-items: center;
|
|
82
82
|
min-width: 0;
|
|
83
83
|
`;
|
|
84
84
|
const ExtraCell = styled_components.div`
|
|
85
|
-
margin-left: ${(props)=>props.marginLeft ||
|
|
85
|
+
margin-left: ${(props)=>props.marginLeft || '1.429rem'};
|
|
86
86
|
`;
|
|
87
87
|
export { Body, ExtraCell, Group, GroupContent, GroupName, GroupValues, Key, Row, Table, TableContainer, Value };
|
package/dist/config/factory.d.ts
CHANGED
|
@@ -1,15 +1,14 @@
|
|
|
1
|
-
import
|
|
2
|
-
import type { S3BrowserConfig, S3Credentials } from
|
|
3
|
-
import {
|
|
4
|
-
|
|
1
|
+
import Joi from 'joi';
|
|
2
|
+
import type { S3BrowserConfig, S3Credentials } from '../types';
|
|
3
|
+
import type { S3ClientConfiguration } from './types';
|
|
4
|
+
export type S3RuntimeConfig = {
|
|
5
5
|
s3: {
|
|
6
6
|
endpoint?: string;
|
|
7
7
|
region: string;
|
|
8
8
|
forcePathStyle?: boolean;
|
|
9
9
|
};
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
}
|
|
10
|
+
};
|
|
11
|
+
export declare const s3RuntimeConfigSchema: Joi.ObjectSchema<any>;
|
|
13
12
|
/**
|
|
14
13
|
* Configuration factory that uses build-time constants
|
|
15
14
|
* No runtime environment detection or hardcoded values
|
|
@@ -18,8 +17,23 @@ export declare class S3ConfigurationFactory {
|
|
|
18
17
|
/**
|
|
19
18
|
* Load runtime configuration from config.json
|
|
20
19
|
* Should be called at app startup
|
|
20
|
+
*
|
|
21
|
+
* @template T - Extended runtime config type that must include S3RuntimeConfig
|
|
22
|
+
* @param configUrl - URL to fetch the config.json from
|
|
23
|
+
* @returns Promise resolving to the loaded config or null if loading failed
|
|
24
|
+
*
|
|
25
|
+
* @example
|
|
26
|
+
* ```typescript
|
|
27
|
+
* type MyConfig = S3RuntimeConfig & {
|
|
28
|
+
* theme?: string;
|
|
29
|
+
* basePath?: string;
|
|
30
|
+
* more: "type";
|
|
31
|
+
* };
|
|
32
|
+
*
|
|
33
|
+
* const config = await loadRuntimeConfig<MyConfig>("/config.json");
|
|
34
|
+
* ```
|
|
21
35
|
*/
|
|
22
|
-
static loadRuntimeConfig(configUrl: string): Promise<
|
|
36
|
+
static loadRuntimeConfig<T extends S3RuntimeConfig = S3RuntimeConfig>(configUrl: string): Promise<T>;
|
|
23
37
|
private static getBuildTimeConfig;
|
|
24
38
|
/**
|
|
25
39
|
* Create S3 client configuration based on build-time settings
|
|
@@ -59,5 +73,4 @@ export declare const getBuildInfo: () => {
|
|
|
59
73
|
s3Endpoint: string;
|
|
60
74
|
proxyEndpoint: string | undefined;
|
|
61
75
|
};
|
|
62
|
-
export declare const loadRuntimeConfig: (configUrl: string) => Promise<
|
|
63
|
-
export {};
|
|
76
|
+
export declare const loadRuntimeConfig: <T extends S3RuntimeConfig = S3RuntimeConfig>(configUrl: string) => Promise<T>;
|
package/dist/config/factory.js
CHANGED
|
@@ -1,3 +1,11 @@
|
|
|
1
|
+
import joi from "joi";
|
|
2
|
+
const s3RuntimeConfigSchema = joi.object({
|
|
3
|
+
s3: joi.object({
|
|
4
|
+
endpoint: joi.string().optional(),
|
|
5
|
+
region: joi.string().required(),
|
|
6
|
+
forcePathStyle: joi.boolean().optional()
|
|
7
|
+
})
|
|
8
|
+
});
|
|
1
9
|
let runtimeConfig = null;
|
|
2
10
|
class S3ConfigurationFactory {
|
|
3
11
|
static async loadRuntimeConfig(configUrl) {
|
|
@@ -6,14 +14,21 @@ class S3ConfigurationFactory {
|
|
|
6
14
|
if (response.ok) {
|
|
7
15
|
const data = await response.json();
|
|
8
16
|
runtimeConfig = data;
|
|
9
|
-
|
|
10
|
-
|
|
17
|
+
const { error } = s3RuntimeConfigSchema.validate(data, {
|
|
18
|
+
allowUnknown: true,
|
|
19
|
+
stripUnknown: false,
|
|
20
|
+
abortEarly: false
|
|
21
|
+
});
|
|
22
|
+
if (error) {
|
|
23
|
+
const errorMessages = error.details.map((detail)=>detail.message).join(`\n`);
|
|
24
|
+
throw new Error(`Invalid runtime configuration, please check your config.json: \n${errorMessages}`);
|
|
25
|
+
}
|
|
26
|
+
if (runtimeConfig?.s3?.endpoint === 'origin') runtimeConfig.s3.endpoint = window.location.origin;
|
|
11
27
|
return data;
|
|
12
28
|
}
|
|
13
|
-
|
|
29
|
+
throw new Error('Failed to load runtime configuration');
|
|
14
30
|
} catch (error) {
|
|
15
|
-
|
|
16
|
-
return null;
|
|
31
|
+
throw error;
|
|
17
32
|
}
|
|
18
33
|
}
|
|
19
34
|
static getBuildTimeConfig() {
|
|
@@ -59,7 +74,7 @@ class S3ConfigurationFactory {
|
|
|
59
74
|
static getBuildInfo() {
|
|
60
75
|
const buildConfig = this.getBuildTimeConfig();
|
|
61
76
|
return {
|
|
62
|
-
environment: buildConfig.isDevelopment ?
|
|
77
|
+
environment: buildConfig.isDevelopment ? 'development' : 'production',
|
|
63
78
|
useProxy: buildConfig.dev.useProxy,
|
|
64
79
|
s3Endpoint: buildConfig.s3.endpoint,
|
|
65
80
|
proxyEndpoint: buildConfig.dev.proxyEndpoint
|
|
@@ -71,4 +86,4 @@ const shouldUseProxy = ()=>S3ConfigurationFactory.shouldUseProxyMiddleware();
|
|
|
71
86
|
const getProxyConfig = ()=>S3ConfigurationFactory.createProxyConfiguration();
|
|
72
87
|
const getBuildInfo = ()=>S3ConfigurationFactory.getBuildInfo();
|
|
73
88
|
const loadRuntimeConfig = (configUrl)=>S3ConfigurationFactory.loadRuntimeConfig(configUrl);
|
|
74
|
-
export { S3ConfigurationFactory, createS3Config, getBuildInfo, getProxyConfig, loadRuntimeConfig, shouldUseProxy };
|
|
89
|
+
export { S3ConfigurationFactory, createS3Config, getBuildInfo, getProxyConfig, loadRuntimeConfig, s3RuntimeConfigSchema, shouldUseProxy };
|
package/dist/config/types.d.ts
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Build-time configuration types injected by RSBuild
|
|
3
3
|
*/
|
|
4
|
-
import type { Bucket } from
|
|
5
|
-
import type { TableItem } from
|
|
4
|
+
import type { Bucket } from '@aws-sdk/client-s3';
|
|
5
|
+
import type { TableItem } from '../components/objects/ObjectList';
|
|
6
6
|
export interface S3Configuration {
|
|
7
7
|
endpoint: string;
|
|
8
8
|
region: string;
|
|
@@ -56,6 +56,7 @@ export interface ColumnConfig<T = unknown> {
|
|
|
56
56
|
render: React.ComponentType<{
|
|
57
57
|
data: T;
|
|
58
58
|
}>;
|
|
59
|
+
cellStyle?: React.CSSProperties;
|
|
59
60
|
}
|
|
60
61
|
/**
|
|
61
62
|
* Action configuration for list-level actions (buttons at top of list)
|
|
@@ -90,6 +91,14 @@ export interface FieldConfig {
|
|
|
90
91
|
entityName: string;
|
|
91
92
|
}>;
|
|
92
93
|
}
|
|
94
|
+
/**
|
|
95
|
+
* Section configuration for overview pages
|
|
96
|
+
*/
|
|
97
|
+
export interface SectionConfig {
|
|
98
|
+
id: string;
|
|
99
|
+
title: string;
|
|
100
|
+
render: () => React.ReactNode;
|
|
101
|
+
}
|
|
93
102
|
/**
|
|
94
103
|
* Storage class selector props
|
|
95
104
|
*/
|
|
@@ -101,6 +110,12 @@ export interface StorageClassSelectorProps {
|
|
|
101
110
|
* Main DataBrowserUI component props
|
|
102
111
|
*/
|
|
103
112
|
export interface DataBrowserUIProps {
|
|
113
|
+
basePath?: string;
|
|
114
|
+
/**
|
|
115
|
+
* Custom header component to render above the main content.
|
|
116
|
+
* Typically used for breadcrumbs or navigation.
|
|
117
|
+
*/
|
|
118
|
+
header?: React.ReactNode;
|
|
104
119
|
storageClassSelector?: React.ComponentType<StorageClassSelectorProps>;
|
|
105
120
|
extraBucketListColumns?: ColumnConfig<Bucket>[];
|
|
106
121
|
extraBucketListActions?: ActionConfig[];
|
|
@@ -108,6 +123,7 @@ export interface DataBrowserUIProps {
|
|
|
108
123
|
extraBucketOverviewGeneral?: FieldConfig[];
|
|
109
124
|
extraBucketOverviewDataProtection?: FieldConfig[];
|
|
110
125
|
extraBucketOverviewPermissions?: FieldConfig[];
|
|
126
|
+
extraBucketOverviewSections?: SectionConfig[];
|
|
111
127
|
/**
|
|
112
128
|
* Extra columns for object list.
|
|
113
129
|
*
|
|
@@ -160,4 +176,5 @@ export interface DataBrowserUIProps {
|
|
|
160
176
|
*/
|
|
161
177
|
extraObjectSummaryDataProtection?: FieldConfig[];
|
|
162
178
|
}
|
|
163
|
-
export type S3EventType =
|
|
179
|
+
export type S3EventType = 's3:ObjectCreated:*' | 's3:ObjectCreated:Put' | 's3:ObjectCreated:Post' | 's3:ObjectCreated:Copy' | 's3:ObjectCreated:CompleteMultipartUpload' | 's3:ObjectRemoved:*' | 's3:ObjectRemoved:Delete' | 's3:ObjectRemoved:DeleteMarkerCreated' | 's3:ObjectRestore:*' | 's3:ObjectRestore:Post' | 's3:ObjectRestore:Completed' | 's3:ObjectRestore:Delete' | 's3:LifecycleExpiration:*' | 's3:LifecycleExpiration:Delete' | 's3:LifecycleExpiration:DeleteMarkerCreated' | 's3:LifecycleTransition' | 's3:Replication:*' | 's3:Replication:OperationFailedReplication' | 's3:Replication:OperationMissedThreshold' | 's3:Replication:OperationReplicatedAfterThreshold' | 's3:Replication:OperationNotTracked' | 's3:ObjectTagging:*' | 's3:ObjectTagging:Put' | 's3:ObjectTagging:Delete' | 's3:ReducedRedundancyLostObject' | 's3:IntelligentTiering' | 's3:ObjectAcl:Put' | 's3:TestEvent';
|
|
180
|
+
export type S3EventCategory = 'Object Creation' | 'Object Deletion' | 'Object Restoration' | 'Lifecycle' | 'Replication' | 'Object Tagging' | 'Storage & Access' | 'Testing';
|
|
@@ -4,8 +4,8 @@
|
|
|
4
4
|
*
|
|
5
5
|
* @internal
|
|
6
6
|
*/
|
|
7
|
-
import React from
|
|
8
|
-
import type { DataBrowserUIProps } from
|
|
7
|
+
import React from 'react';
|
|
8
|
+
import type { DataBrowserUIProps } from '../config/types';
|
|
9
9
|
interface DataBrowserUICustomizationProviderProps {
|
|
10
10
|
config: DataBrowserUIProps;
|
|
11
11
|
children: React.ReactNode;
|