sanity-plugin-media 4.3.6 → 5.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +6 -15
- package/dist/index.cjs +0 -4721
- package/dist/index.cjs.map +0 -1
- package/dist/index.d.cts +0 -239
- package/dist/index.d.cts.map +0 -1
- package/sanity.json +0 -8
- package/src/__tests__/fixtures/createEpicTestStore.ts +0 -28
- package/src/__tests__/fixtures/listenMock.ts +0 -9
- package/src/__tests__/fixtures/mockSanityClient.ts +0 -84
- package/src/__tests__/fixtures/renderWithProviders.tsx +0 -55
- package/src/__tests__/fixtures/rootState.ts +0 -27
- package/src/__tests__/fixtures/withinDialog.ts +0 -28
- package/src/components/AssetGridVirtualized/index.tsx +0 -94
- package/src/components/AssetMetadata/index.tsx +0 -122
- package/src/components/AssetTableVirtualized/index.tsx +0 -73
- package/src/components/AutoTagInputWrapper/index.tsx +0 -85
- package/src/components/Browser/Browser.test.tsx +0 -45
- package/src/components/Browser/index.tsx +0 -90
- package/src/components/Browser/useBrowserInit.ts +0 -126
- package/src/components/ButtonAssetCopy/index.tsx +0 -65
- package/src/components/ButtonViewGroup/index.tsx +0 -39
- package/src/components/CardAsset/CardAsset.test.tsx +0 -323
- package/src/components/CardAsset/index.tsx +0 -290
- package/src/components/CardUpload/index.tsx +0 -161
- package/src/components/Controls/index.tsx +0 -136
- package/src/components/DebugControls/index.tsx +0 -80
- package/src/components/Dialog/index.tsx +0 -11
- package/src/components/DialogAssetEdit/Details.tsx +0 -181
- package/src/components/DialogAssetEdit/DialogAssetEdit.test.tsx +0 -216
- package/src/components/DialogAssetEdit/index.tsx +0 -493
- package/src/components/DialogConfirm/index.tsx +0 -90
- package/src/components/DialogSearchFacets/index.tsx +0 -42
- package/src/components/DialogTagCreate/DialogTagCreate.test.tsx +0 -121
- package/src/components/DialogTagCreate/index.tsx +0 -111
- package/src/components/DialogTagEdit/DialogTagEdit.test.tsx +0 -165
- package/src/components/DialogTagEdit/index.tsx +0 -201
- package/src/components/DialogTags/index.tsx +0 -45
- package/src/components/Dialogs/index.tsx +0 -76
- package/src/components/DocumentList/index.tsx +0 -62
- package/src/components/FileAssetPreview/index.tsx +0 -37
- package/src/components/FileIcon/index.tsx +0 -43
- package/src/components/FormBuilderTool/FormBuilderTool.test.tsx +0 -63
- package/src/components/FormBuilderTool/index.tsx +0 -69
- package/src/components/FormFieldInputLabel/index.tsx +0 -66
- package/src/components/FormFieldInputTags/index.tsx +0 -98
- package/src/components/FormFieldInputText/index.tsx +0 -41
- package/src/components/FormFieldInputTextarea/index.tsx +0 -43
- package/src/components/FormSubmitButton/index.tsx +0 -59
- package/src/components/Header/index.tsx +0 -80
- package/src/components/Image/index.tsx +0 -41
- package/src/components/Items/index.tsx +0 -68
- package/src/components/Notifications/index.tsx +0 -24
- package/src/components/OrderSelect/index.tsx +0 -66
- package/src/components/PickedBar/index.tsx +0 -77
- package/src/components/Progress/index.tsx +0 -38
- package/src/components/ReduxProvider/index.tsx +0 -96
- package/src/components/SearchFacet/index.tsx +0 -66
- package/src/components/SearchFacetNumber/index.tsx +0 -133
- package/src/components/SearchFacetSelect/index.tsx +0 -110
- package/src/components/SearchFacetString/index.tsx +0 -88
- package/src/components/SearchFacetTags/index.tsx +0 -121
- package/src/components/SearchFacets/index.tsx +0 -72
- package/src/components/SearchFacetsControl/index.tsx +0 -140
- package/src/components/TableHeader/index.tsx +0 -110
- package/src/components/TableHeaderItem/index.tsx +0 -61
- package/src/components/TableRowAsset/index.tsx +0 -419
- package/src/components/TableRowUpload/index.tsx +0 -164
- package/src/components/Tag/index.tsx +0 -200
- package/src/components/TagIcon/index.tsx +0 -22
- package/src/components/TagView/index.tsx +0 -39
- package/src/components/TagViewHeader/index.tsx +0 -70
- package/src/components/TagsPanel/index.tsx +0 -40
- package/src/components/TagsVirtualized/index.tsx +0 -160
- package/src/components/TextInputNumber/index.tsx +0 -32
- package/src/components/TextInputSearch/index.tsx +0 -60
- package/src/components/Tool/index.tsx +0 -13
- package/src/components/UploadDropzone/UploadDropzone.test.tsx +0 -40
- package/src/components/UploadDropzone/index.tsx +0 -173
- package/src/config/orders.ts +0 -28
- package/src/config/searchFacets.ts +0 -312
- package/src/constants.ts +0 -87
- package/src/contexts/AssetSourceDispatchContext.tsx +0 -38
- package/src/contexts/DropzoneDispatchContext.tsx +0 -32
- package/src/contexts/ToolOptionsContext.tsx +0 -66
- package/src/formSchema/index.test.ts +0 -56
- package/src/formSchema/index.ts +0 -39
- package/src/hooks/useBreakpointIndex.ts +0 -50
- package/src/hooks/useKeyPress.ts +0 -39
- package/src/hooks/usePortalPopoverProps.ts +0 -13
- package/src/hooks/useTypedSelector.ts +0 -7
- package/src/hooks/useVersionedClient.ts +0 -6
- package/src/index.ts +0 -5
- package/src/modules/assets/actions.ts +0 -42
- package/src/modules/assets/deleteAndUpdateEpics.test.ts +0 -87
- package/src/modules/assets/fetchEpic.test.ts +0 -73
- package/src/modules/assets/index.ts +0 -782
- package/src/modules/assets/reducer.test.ts +0 -91
- package/src/modules/assets/tagsAndListenerEpics.test.ts +0 -206
- package/src/modules/debug/index.ts +0 -28
- package/src/modules/dialog/actions.ts +0 -10
- package/src/modules/dialog/epics.test.ts +0 -168
- package/src/modules/dialog/index.ts +0 -238
- package/src/modules/dialog/reducer.test.ts +0 -185
- package/src/modules/index.ts +0 -117
- package/src/modules/notifications/epics.test.ts +0 -374
- package/src/modules/notifications/index.ts +0 -199
- package/src/modules/notifications/reducer.test.ts +0 -54
- package/src/modules/search/index.test.ts +0 -36
- package/src/modules/search/index.ts +0 -167
- package/src/modules/selected/index.ts +0 -22
- package/src/modules/selectors.test.ts +0 -21
- package/src/modules/selectors.ts +0 -17
- package/src/modules/tags/epics.test.ts +0 -96
- package/src/modules/tags/index.test.ts +0 -42
- package/src/modules/tags/index.ts +0 -540
- package/src/modules/types.ts +0 -3
- package/src/modules/uploads/actions.ts +0 -13
- package/src/modules/uploads/epics.test.ts +0 -109
- package/src/modules/uploads/index.test.ts +0 -59
- package/src/modules/uploads/index.ts +0 -272
- package/src/operators/checkTagName.test.ts +0 -29
- package/src/operators/checkTagName.ts +0 -33
- package/src/operators/debugThrottle.ts +0 -25
- package/src/plugin.tsx +0 -54
- package/src/schemas/tag.ts +0 -28
- package/src/styled/GlobalStyles/index.tsx +0 -40
- package/src/styled/react-select/creatable.tsx +0 -184
- package/src/styled/react-select/single.tsx +0 -184
- package/src/types/index.ts +0 -346
- package/src/types/sanity-ui.d.ts +0 -5
- package/src/utils/applyMediaTags.ts +0 -87
- package/src/utils/blocksToText.test.ts +0 -43
- package/src/utils/blocksToText.ts +0 -27
- package/src/utils/constructFilter.test.ts +0 -120
- package/src/utils/constructFilter.ts +0 -98
- package/src/utils/generatePreviewBlobUrl.test.ts +0 -68
- package/src/utils/generatePreviewBlobUrl.ts +0 -53
- package/src/utils/getAssetResolution.test.ts +0 -13
- package/src/utils/getAssetResolution.ts +0 -7
- package/src/utils/getDocumentAssetIds.test.ts +0 -50
- package/src/utils/getDocumentAssetIds.ts +0 -35
- package/src/utils/getSchemeColor.test.ts +0 -12
- package/src/utils/getSchemeColor.ts +0 -43
- package/src/utils/getTagSelectOptions.test.ts +0 -44
- package/src/utils/getTagSelectOptions.ts +0 -16
- package/src/utils/getUniqueDocuments.test.ts +0 -26
- package/src/utils/getUniqueDocuments.ts +0 -15
- package/src/utils/imageDprUrl.test.ts +0 -46
- package/src/utils/imageDprUrl.ts +0 -27
- package/src/utils/isSupportedAssetType.test.ts +0 -16
- package/src/utils/isSupportedAssetType.ts +0 -15
- package/src/utils/mediaField.ts +0 -73
- package/src/utils/sanitizeFormData.test.ts +0 -59
- package/src/utils/sanitizeFormData.ts +0 -26
- package/src/utils/typeGuards.test.ts +0 -18
- package/src/utils/typeGuards.ts +0 -9
- package/src/utils/uploadSanityAsset.test.ts +0 -29
- package/src/utils/uploadSanityAsset.ts +0 -97
- package/src/utils/withMaxConcurrency.test.ts +0 -43
- package/src/utils/withMaxConcurrency.ts +0 -55
- package/src/utils/zodFormResolver.ts +0 -17
- package/v2-incompatible.js +0 -11
|
@@ -1,66 +0,0 @@
|
|
|
1
|
-
import {type PropsWithChildren, createContext, useContext, useMemo} from 'react'
|
|
2
|
-
import type {DropzoneOptions} from 'react-dropzone'
|
|
3
|
-
|
|
4
|
-
import type {MediaToolOptions, Locale} from '../types'
|
|
5
|
-
|
|
6
|
-
type ContextProps = {
|
|
7
|
-
dropzone: Pick<DropzoneOptions, 'maxSize'>
|
|
8
|
-
components: MediaToolOptions['components']
|
|
9
|
-
createTagsOnUpload: boolean
|
|
10
|
-
creditLine: MediaToolOptions['creditLine']
|
|
11
|
-
directUploads: MediaToolOptions['directUploads']
|
|
12
|
-
locales?: Locale[]
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
const ToolOptionsContext = createContext<ContextProps | null>(null)
|
|
16
|
-
|
|
17
|
-
type Props = {
|
|
18
|
-
options?: MediaToolOptions | void
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
export const ToolOptionsProvider = ({options, children}: PropsWithChildren<Props>) => {
|
|
22
|
-
// oxlint-disable-next-line react-compiler
|
|
23
|
-
const value = useMemo<ContextProps>(() => {
|
|
24
|
-
let creditLineExcludeSources
|
|
25
|
-
|
|
26
|
-
if (options?.creditLine?.excludeSources) {
|
|
27
|
-
creditLineExcludeSources = Array.isArray(options?.creditLine?.excludeSources)
|
|
28
|
-
? options.creditLine.excludeSources
|
|
29
|
-
: [options?.creditLine?.excludeSources]
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
return {
|
|
33
|
-
dropzone: {maxSize: options?.maximumUploadSize},
|
|
34
|
-
components: {
|
|
35
|
-
details: options?.components?.details,
|
|
36
|
-
},
|
|
37
|
-
createTagsOnUpload: options?.createTagsOnUpload ?? true,
|
|
38
|
-
creditLine: {
|
|
39
|
-
enabled: options?.creditLine?.enabled || false,
|
|
40
|
-
excludeSources: creditLineExcludeSources,
|
|
41
|
-
},
|
|
42
|
-
directUploads: options?.directUploads ?? true,
|
|
43
|
-
locales: options?.locales,
|
|
44
|
-
}
|
|
45
|
-
}, [
|
|
46
|
-
options?.creditLine?.enabled,
|
|
47
|
-
options?.components,
|
|
48
|
-
options?.createTagsOnUpload,
|
|
49
|
-
options?.creditLine?.excludeSources,
|
|
50
|
-
options?.maximumUploadSize,
|
|
51
|
-
options?.directUploads,
|
|
52
|
-
options?.locales,
|
|
53
|
-
])
|
|
54
|
-
|
|
55
|
-
return <ToolOptionsContext.Provider value={value}>{children}</ToolOptionsContext.Provider>
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
export const useToolOptions = () => {
|
|
59
|
-
const context = useContext(ToolOptionsContext)
|
|
60
|
-
|
|
61
|
-
if (!context) {
|
|
62
|
-
throw new Error('useToolOptions must be used within an ToolOptionsProvider')
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
return context
|
|
66
|
-
}
|
|
@@ -1,56 +0,0 @@
|
|
|
1
|
-
// @vitest-environment node
|
|
2
|
-
|
|
3
|
-
import {describe, expect, it} from 'vitest'
|
|
4
|
-
|
|
5
|
-
import {assetFormSchema, tagFormSchema, tagOptionSchema} from './index'
|
|
6
|
-
|
|
7
|
-
describe('tagOptionSchema', () => {
|
|
8
|
-
it('accepts trimmed non-empty label and value', () => {
|
|
9
|
-
expect(tagOptionSchema.safeParse({label: 'A', value: 'b'}).success).toBe(true)
|
|
10
|
-
})
|
|
11
|
-
|
|
12
|
-
it('rejects empty label or value after trim', () => {
|
|
13
|
-
expect(tagOptionSchema.safeParse({label: ' ', value: 'x'}).success).toBe(false)
|
|
14
|
-
expect(tagOptionSchema.safeParse({label: 'x', value: ''}).success).toBe(false)
|
|
15
|
-
})
|
|
16
|
-
})
|
|
17
|
-
|
|
18
|
-
describe('tagFormSchema', () => {
|
|
19
|
-
it('requires non-empty name', () => {
|
|
20
|
-
expect(tagFormSchema.safeParse({name: 'x'}).success).toBe(true)
|
|
21
|
-
expect(tagFormSchema.safeParse({name: ''}).success).toBe(false)
|
|
22
|
-
})
|
|
23
|
-
})
|
|
24
|
-
|
|
25
|
-
describe('assetFormSchema', () => {
|
|
26
|
-
const base = {
|
|
27
|
-
altText: '',
|
|
28
|
-
creditLine: '',
|
|
29
|
-
description: '',
|
|
30
|
-
opt: {media: {tags: null}},
|
|
31
|
-
originalFilename: 'file.png',
|
|
32
|
-
title: '',
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
it('accepts valid asset form payload', () => {
|
|
36
|
-
expect(assetFormSchema.safeParse(base).success).toBe(true)
|
|
37
|
-
})
|
|
38
|
-
|
|
39
|
-
it('rejects empty originalFilename', () => {
|
|
40
|
-
expect(
|
|
41
|
-
assetFormSchema.safeParse({
|
|
42
|
-
...base,
|
|
43
|
-
originalFilename: ' ',
|
|
44
|
-
}).success,
|
|
45
|
-
).toBe(false)
|
|
46
|
-
})
|
|
47
|
-
|
|
48
|
-
it('validates nested tag options', () => {
|
|
49
|
-
expect(
|
|
50
|
-
assetFormSchema.safeParse({
|
|
51
|
-
...base,
|
|
52
|
-
opt: {media: {tags: [{label: '', value: 'v'}]}},
|
|
53
|
-
}).success,
|
|
54
|
-
).toBe(false)
|
|
55
|
-
})
|
|
56
|
-
})
|
package/src/formSchema/index.ts
DELETED
|
@@ -1,39 +0,0 @@
|
|
|
1
|
-
import * as z from 'zod'
|
|
2
|
-
|
|
3
|
-
// Helper to generate localized string schema
|
|
4
|
-
function localizedStringSchema(locales?: {id: string}[]) {
|
|
5
|
-
if (!locales || locales.length === 0) {
|
|
6
|
-
return z.string().trim().optional()
|
|
7
|
-
}
|
|
8
|
-
const shape: Record<string, z.ZodTypeAny> = {}
|
|
9
|
-
for (const locale of locales) {
|
|
10
|
-
shape[locale.id] = z.string().trim().optional()
|
|
11
|
-
}
|
|
12
|
-
return z.object(shape).passthrough()
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
export const tagOptionSchema = z.object({
|
|
16
|
-
label: z.string().trim().min(1, {message: 'Label cannot be empty'}),
|
|
17
|
-
value: z.string().trim().min(1, {message: 'Value cannot be empty'}),
|
|
18
|
-
})
|
|
19
|
-
|
|
20
|
-
export function getAssetFormSchema(locales?: {id: string}[]) {
|
|
21
|
-
return z.object({
|
|
22
|
-
altText: localizedStringSchema(locales),
|
|
23
|
-
creditLine: localizedStringSchema(locales),
|
|
24
|
-
description: localizedStringSchema(locales),
|
|
25
|
-
opt: z.object({
|
|
26
|
-
media: z.object({
|
|
27
|
-
tags: z.array(tagOptionSchema).nullable(),
|
|
28
|
-
}),
|
|
29
|
-
}),
|
|
30
|
-
originalFilename: z.string().trim().min(1, {message: 'Filename cannot be empty'}),
|
|
31
|
-
title: localizedStringSchema(locales),
|
|
32
|
-
})
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
export const assetFormSchema = getAssetFormSchema()
|
|
36
|
-
|
|
37
|
-
export const tagFormSchema = z.object({
|
|
38
|
-
name: z.string().min(1, {message: 'Name cannot be empty'}),
|
|
39
|
-
})
|
|
@@ -1,50 +0,0 @@
|
|
|
1
|
-
import {studioTheme} from '@sanity/ui'
|
|
2
|
-
import {useEffect, useState} from 'react'
|
|
3
|
-
|
|
4
|
-
// Determine the current breakpoint index
|
|
5
|
-
// - create MediaQueryLists from every breakpoint defined in our sanity studio theme
|
|
6
|
-
// - for each MQL, listen to change events and return the selected breakpoint index
|
|
7
|
-
const useBreakpointIndex = (): number => {
|
|
8
|
-
const mediaQueryLists = studioTheme?.container?.map((width) =>
|
|
9
|
-
window.matchMedia(`(max-width: ${width}px)`),
|
|
10
|
-
)
|
|
11
|
-
|
|
12
|
-
const getBreakpointIndex = () => mediaQueryLists.findIndex((mql) => mql.matches)
|
|
13
|
-
|
|
14
|
-
const [value, setValue] = useState(getBreakpointIndex())
|
|
15
|
-
|
|
16
|
-
useEffect(() => {
|
|
17
|
-
const handleBreakpoint = () => {
|
|
18
|
-
setValue(getBreakpointIndex)
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
// NOTE: older versions of Safari use the older `addListener` and `removeListener` methods
|
|
22
|
-
mediaQueryLists.forEach((mql) => {
|
|
23
|
-
try {
|
|
24
|
-
mql.addEventListener('change', handleBreakpoint)
|
|
25
|
-
} catch {
|
|
26
|
-
try {
|
|
27
|
-
mql.addListener(handleBreakpoint)
|
|
28
|
-
} catch {
|
|
29
|
-
// Do nothing
|
|
30
|
-
}
|
|
31
|
-
}
|
|
32
|
-
})
|
|
33
|
-
return () => {
|
|
34
|
-
try {
|
|
35
|
-
mediaQueryLists.forEach((mql) => mql.removeEventListener('change', handleBreakpoint))
|
|
36
|
-
} catch {
|
|
37
|
-
try {
|
|
38
|
-
mediaQueryLists.forEach((mql) => mql.removeListener(handleBreakpoint))
|
|
39
|
-
} catch {
|
|
40
|
-
// Do nothing
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
}
|
|
44
|
-
// oxlint-disable-next-line react-hooks/exhaustive-deps - use the hook from `@sanity/ui` instead of this home-rolled one
|
|
45
|
-
}, [])
|
|
46
|
-
|
|
47
|
-
return value
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
export default useBreakpointIndex
|
package/src/hooks/useKeyPress.ts
DELETED
|
@@ -1,39 +0,0 @@
|
|
|
1
|
-
import {isHotkey} from 'is-hotkey-esm'
|
|
2
|
-
import {type RefObject, useCallback, useEffect, useRef} from 'react'
|
|
3
|
-
|
|
4
|
-
const useKeyPress = (hotkey: string, onPress?: () => void): RefObject<boolean> => {
|
|
5
|
-
const keyPressed = useRef(false)
|
|
6
|
-
|
|
7
|
-
// If pressed key is our target key then set to true
|
|
8
|
-
const downHandler = useCallback(
|
|
9
|
-
(e: KeyboardEvent) => {
|
|
10
|
-
if (isHotkey(hotkey, e)) {
|
|
11
|
-
keyPressed.current = true
|
|
12
|
-
if (onPress) {
|
|
13
|
-
onPress()
|
|
14
|
-
}
|
|
15
|
-
}
|
|
16
|
-
},
|
|
17
|
-
[hotkey, onPress],
|
|
18
|
-
)
|
|
19
|
-
|
|
20
|
-
// If released key is our target key then set to false
|
|
21
|
-
const upHandler = useCallback(() => {
|
|
22
|
-
keyPressed.current = false
|
|
23
|
-
}, [])
|
|
24
|
-
|
|
25
|
-
// Add event listeners
|
|
26
|
-
useEffect(() => {
|
|
27
|
-
window.addEventListener('keydown', downHandler)
|
|
28
|
-
window.addEventListener('keyup', upHandler)
|
|
29
|
-
// Remove event listeners on cleanup
|
|
30
|
-
return () => {
|
|
31
|
-
window.removeEventListener('keydown', downHandler)
|
|
32
|
-
window.removeEventListener('keyup', upHandler)
|
|
33
|
-
}
|
|
34
|
-
}, [downHandler, upHandler])
|
|
35
|
-
|
|
36
|
-
return keyPressed
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
export default useKeyPress
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
import {type PopoverProps, usePortal} from '@sanity/ui'
|
|
2
|
-
|
|
3
|
-
export function usePortalPopoverProps(): PopoverProps {
|
|
4
|
-
const portal = usePortal()
|
|
5
|
-
|
|
6
|
-
return {
|
|
7
|
-
animate: true,
|
|
8
|
-
constrainSize: true,
|
|
9
|
-
floatingBoundary: portal.element,
|
|
10
|
-
portal: true,
|
|
11
|
-
referenceBoundary: portal.element,
|
|
12
|
-
}
|
|
13
|
-
}
|
package/src/index.ts
DELETED
|
@@ -1,5 +0,0 @@
|
|
|
1
|
-
export {media, mediaAssetSource} from './plugin'
|
|
2
|
-
export {AutoTagInput} from './components/AutoTagInputWrapper'
|
|
3
|
-
export type {AutoTagInputProps} from './components/AutoTagInputWrapper'
|
|
4
|
-
export {mediaField} from './utils/mediaField'
|
|
5
|
-
export type {MediaTagsOptions, MediaToolOptions} from './types'
|
|
@@ -1,42 +0,0 @@
|
|
|
1
|
-
import {createAction} from '@reduxjs/toolkit'
|
|
2
|
-
|
|
3
|
-
import type {AssetItem, HttpError, Tag} from '../../types'
|
|
4
|
-
|
|
5
|
-
export const ASSETS_ACTIONS = {
|
|
6
|
-
tagsAddComplete: createAction(
|
|
7
|
-
'actions/tagsAddComplete',
|
|
8
|
-
function prepare({assets, tag}: {assets: AssetItem[]; tag: Tag}) {
|
|
9
|
-
return {payload: {assets, tag}}
|
|
10
|
-
},
|
|
11
|
-
),
|
|
12
|
-
tagsAddError: createAction(
|
|
13
|
-
'actions/tagsAddError',
|
|
14
|
-
function prepare({assets, error, tag}: {assets: AssetItem[]; error: HttpError; tag: Tag}) {
|
|
15
|
-
return {payload: {assets, error, tag}}
|
|
16
|
-
},
|
|
17
|
-
),
|
|
18
|
-
tagsAddRequest: createAction(
|
|
19
|
-
'actions/tagsAddRequest',
|
|
20
|
-
function prepare({assets, tag}: {assets: AssetItem[]; tag: Tag}) {
|
|
21
|
-
return {payload: {assets, tag}}
|
|
22
|
-
},
|
|
23
|
-
),
|
|
24
|
-
tagsRemoveComplete: createAction(
|
|
25
|
-
'actions/tagsRemoveComplete',
|
|
26
|
-
function prepare({assets, tag}: {assets: AssetItem[]; tag: Tag}) {
|
|
27
|
-
return {payload: {assets, tag}}
|
|
28
|
-
},
|
|
29
|
-
),
|
|
30
|
-
tagsRemoveError: createAction(
|
|
31
|
-
'actions/tagsRemoveError',
|
|
32
|
-
function prepare({assets, error, tag}: {assets: AssetItem[]; error: HttpError; tag: Tag}) {
|
|
33
|
-
return {payload: {assets, error, tag}}
|
|
34
|
-
},
|
|
35
|
-
),
|
|
36
|
-
tagsRemoveRequest: createAction(
|
|
37
|
-
'actions/tagsRemoveRequest',
|
|
38
|
-
function prepare({assets, tag}: {assets: AssetItem[]; tag: Tag}) {
|
|
39
|
-
return {payload: {assets, tag}}
|
|
40
|
-
},
|
|
41
|
-
),
|
|
42
|
-
}
|
|
@@ -1,87 +0,0 @@
|
|
|
1
|
-
// @vitest-environment node
|
|
2
|
-
|
|
3
|
-
import {of} from 'rxjs'
|
|
4
|
-
import {describe, expect, it, vi} from 'vitest'
|
|
5
|
-
|
|
6
|
-
import {createEpicTestStore} from '../../__tests__/fixtures/createEpicTestStore'
|
|
7
|
-
import {createMockSanityClient, mockPatchChain} from '../../__tests__/fixtures/mockSanityClient'
|
|
8
|
-
import type {ImageAsset} from '../../types'
|
|
9
|
-
import {
|
|
10
|
-
assetsActions,
|
|
11
|
-
assetsDeleteEpic,
|
|
12
|
-
assetsUpdateEpic,
|
|
13
|
-
initialState as assetsInitialState,
|
|
14
|
-
} from './index'
|
|
15
|
-
|
|
16
|
-
const sampleAsset = {
|
|
17
|
-
_id: 'a1',
|
|
18
|
-
_type: 'sanity.imageAsset',
|
|
19
|
-
_createdAt: '',
|
|
20
|
-
_updatedAt: '',
|
|
21
|
-
_rev: 'r',
|
|
22
|
-
originalFilename: 'x.png',
|
|
23
|
-
size: 1,
|
|
24
|
-
mimeType: 'image/png',
|
|
25
|
-
url: '',
|
|
26
|
-
} as ImageAsset
|
|
27
|
-
|
|
28
|
-
describe('assetsDeleteEpic', () => {
|
|
29
|
-
it('dispatches deleteComplete when observable.delete succeeds', async () => {
|
|
30
|
-
const client = createMockSanityClient({
|
|
31
|
-
observable: {
|
|
32
|
-
delete: vi.fn(() => of({})),
|
|
33
|
-
},
|
|
34
|
-
})
|
|
35
|
-
|
|
36
|
-
const store = createEpicTestStore(assetsDeleteEpic, client, {
|
|
37
|
-
assets: {
|
|
38
|
-
...assetsInitialState,
|
|
39
|
-
assetTypes: ['image'],
|
|
40
|
-
allIds: ['a1'],
|
|
41
|
-
byIds: {
|
|
42
|
-
a1: {_type: 'asset', asset: sampleAsset, picked: false, updating: false},
|
|
43
|
-
},
|
|
44
|
-
},
|
|
45
|
-
})
|
|
46
|
-
|
|
47
|
-
store.dispatch(assetsActions.deleteRequest({assets: [sampleAsset]}))
|
|
48
|
-
|
|
49
|
-
await vi.waitFor(() => {
|
|
50
|
-
expect(store.getState().assets.byIds['a1']).toBeUndefined()
|
|
51
|
-
expect(client.observable.delete).toHaveBeenCalled()
|
|
52
|
-
})
|
|
53
|
-
})
|
|
54
|
-
})
|
|
55
|
-
|
|
56
|
-
describe('assetsUpdateEpic', () => {
|
|
57
|
-
it('commits patch and dispatches updateComplete', async () => {
|
|
58
|
-
const updated = {...sampleAsset, title: 'Updated'}
|
|
59
|
-
const chain = mockPatchChain(updated)
|
|
60
|
-
const client = createMockSanityClient({
|
|
61
|
-
patch: vi.fn(() => chain),
|
|
62
|
-
})
|
|
63
|
-
|
|
64
|
-
const store = createEpicTestStore(assetsUpdateEpic, client, {
|
|
65
|
-
assets: {
|
|
66
|
-
...assetsInitialState,
|
|
67
|
-
assetTypes: ['image'],
|
|
68
|
-
allIds: ['a1'],
|
|
69
|
-
byIds: {
|
|
70
|
-
a1: {_type: 'asset', asset: sampleAsset, picked: false, updating: false},
|
|
71
|
-
},
|
|
72
|
-
},
|
|
73
|
-
})
|
|
74
|
-
|
|
75
|
-
store.dispatch(
|
|
76
|
-
assetsActions.updateRequest({
|
|
77
|
-
asset: sampleAsset,
|
|
78
|
-
formData: {title: 'Updated'},
|
|
79
|
-
}),
|
|
80
|
-
)
|
|
81
|
-
|
|
82
|
-
await vi.waitFor(() => {
|
|
83
|
-
expect(chain.commit).toHaveBeenCalled()
|
|
84
|
-
expect(store.getState().assets.byIds['a1']!.asset.title).toBe('Updated')
|
|
85
|
-
})
|
|
86
|
-
})
|
|
87
|
-
})
|
|
@@ -1,73 +0,0 @@
|
|
|
1
|
-
// @vitest-environment node
|
|
2
|
-
|
|
3
|
-
import {of, throwError} from 'rxjs'
|
|
4
|
-
import {describe, expect, it, vi} from 'vitest'
|
|
5
|
-
|
|
6
|
-
import {createEpicTestStore} from '../../__tests__/fixtures/createEpicTestStore'
|
|
7
|
-
import {createMockSanityClient} from '../../__tests__/fixtures/mockSanityClient'
|
|
8
|
-
import type {ImageAsset} from '../../types'
|
|
9
|
-
import {assetsActions, assetsFetchEpic} from './index'
|
|
10
|
-
|
|
11
|
-
function assertFetchSucceeded(store: ReturnType<typeof createEpicTestStore>, asset: ImageAsset) {
|
|
12
|
-
expect(store.getState().assets.byIds['a1']?.asset).toEqual(asset)
|
|
13
|
-
expect(store.getState().assets.fetching).toBe(false)
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
function assertFetchFailed(store: ReturnType<typeof createEpicTestStore>) {
|
|
17
|
-
expect(store.getState().assets.fetchingError?.message).toBe('boom')
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
const sampleAsset = {
|
|
21
|
-
_id: 'a1',
|
|
22
|
-
_type: 'sanity.imageAsset',
|
|
23
|
-
_createdAt: '',
|
|
24
|
-
_updatedAt: '',
|
|
25
|
-
_rev: 'r',
|
|
26
|
-
originalFilename: 'x.png',
|
|
27
|
-
size: 1,
|
|
28
|
-
mimeType: 'image/png',
|
|
29
|
-
url: '',
|
|
30
|
-
} as ImageAsset
|
|
31
|
-
|
|
32
|
-
describe('assetsFetchEpic', () => {
|
|
33
|
-
it('dispatches fetchComplete when observable.fetch succeeds', async () => {
|
|
34
|
-
const client = createMockSanityClient({
|
|
35
|
-
observable: {
|
|
36
|
-
fetch: vi.fn(() => of({items: [sampleAsset]})),
|
|
37
|
-
},
|
|
38
|
-
})
|
|
39
|
-
|
|
40
|
-
const store = createEpicTestStore(assetsFetchEpic, client)
|
|
41
|
-
store.dispatch(
|
|
42
|
-
assetsActions.fetchRequest({
|
|
43
|
-
params: {},
|
|
44
|
-
queryFilter: '_type == "sanity.imageAsset"',
|
|
45
|
-
selector: '',
|
|
46
|
-
sort: '',
|
|
47
|
-
}),
|
|
48
|
-
)
|
|
49
|
-
|
|
50
|
-
await vi.waitFor(() => assertFetchSucceeded(store, sampleAsset))
|
|
51
|
-
})
|
|
52
|
-
|
|
53
|
-
it('dispatches fetchError when fetch fails', async () => {
|
|
54
|
-
const fetchErr = throwError(() => ({message: 'boom', statusCode: 500}))
|
|
55
|
-
const client = createMockSanityClient({
|
|
56
|
-
observable: {
|
|
57
|
-
fetch: vi.fn(() => fetchErr),
|
|
58
|
-
},
|
|
59
|
-
})
|
|
60
|
-
|
|
61
|
-
const store = createEpicTestStore(assetsFetchEpic, client)
|
|
62
|
-
store.dispatch(
|
|
63
|
-
assetsActions.fetchRequest({
|
|
64
|
-
params: {},
|
|
65
|
-
queryFilter: '_type == "sanity.imageAsset"',
|
|
66
|
-
selector: '',
|
|
67
|
-
sort: '',
|
|
68
|
-
}),
|
|
69
|
-
)
|
|
70
|
-
|
|
71
|
-
await vi.waitFor(() => assertFetchFailed(store))
|
|
72
|
-
})
|
|
73
|
-
})
|