sanity-plugin-media 2.1.0 → 2.1.1

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.
@@ -1,17 +1,17 @@
1
1
  import {Box} from '@sanity/ui'
2
2
  import React from 'react'
3
- import {Controller, FieldError} from 'react-hook-form'
3
+ import {Controller} from 'react-hook-form'
4
4
  import CreatableSelect from 'react-select/creatable'
5
5
  import useTypedSelector from '../../hooks/useTypedSelector'
6
6
  import {reactSelectComponents, reactSelectStyles} from '../../styled/react-select/creatable'
7
- import type {ReactSelectOption} from '../../types'
7
+ import type {TagSelectOption} from '../../types'
8
8
  import FormFieldInputLabel from '../FormFieldInputLabel'
9
9
 
10
10
  type Props = {
11
11
  control: any
12
12
  description?: string
13
13
  disabled?: boolean
14
- error?: FieldError
14
+ error?: string
15
15
  label: string
16
16
  name: string
17
17
  onCreateTag: (tagName: string) => void
@@ -20,7 +20,7 @@ type Props = {
20
20
  value: string
21
21
  }[]
22
22
  placeholder?: string
23
- value?: ReactSelectOption[] | null
23
+ value?: TagSelectOption[] | null
24
24
  }
25
25
 
26
26
  const FormFieldInputTags = (props: Props) => {
@@ -54,7 +54,8 @@ const FormFieldInputTags = (props: Props) => {
54
54
  control={control}
55
55
  defaultValue={value}
56
56
  name={name}
57
- render={({onBlur, onChange, value: controllerValue}) => {
57
+ render={({field}) => {
58
+ const {onBlur, onChange, value: controllerValue} = field
58
59
  // TODO: investigate overriding `onChange` and updating form state manually.
59
60
  // `opt.media.tags` is initialised with `null` as a defaultValue in react-hook-form
60
61
  // Ideally, we'd be able to set `opt.media.tags` as null when all items are cleared, rather than
@@ -1,13 +1,12 @@
1
1
  import {Box, TextInput} from '@sanity/ui'
2
2
  import React, {forwardRef} from 'react'
3
- import {FieldError} from 'react-hook-form'
4
3
 
5
4
  import FormFieldInputLabel from '../FormFieldInputLabel'
6
5
 
7
6
  type Props = {
8
7
  description?: string
9
8
  disabled?: boolean
10
- error?: FieldError
9
+ error?: string
11
10
  label: string
12
11
  name: string
13
12
  placeholder?: string
@@ -17,7 +16,7 @@ type Props = {
17
16
  type Ref = HTMLInputElement
18
17
 
19
18
  const FormFieldInputText = forwardRef<Ref, Props>((props: Props, ref) => {
20
- const {description, disabled, error, label, name, placeholder, value} = props
19
+ const {description, disabled, error, label, name, placeholder, value, ...rest} = props
21
20
 
22
21
  return (
23
22
  <Box>
@@ -25,6 +24,7 @@ const FormFieldInputText = forwardRef<Ref, Props>((props: Props, ref) => {
25
24
  <FormFieldInputLabel description={description} error={error} label={label} name={name} />
26
25
  {/* Input */}
27
26
  <TextInput
27
+ {...rest}
28
28
  autoComplete="off"
29
29
  autoFocus
30
30
  defaultValue={value}
@@ -1,13 +1,12 @@
1
1
  import {Box, TextArea} from '@sanity/ui'
2
2
  import React, {forwardRef} from 'react'
3
- import {FieldError} from 'react-hook-form'
4
3
 
5
4
  import FormFieldInputLabel from '../FormFieldInputLabel'
6
5
 
7
6
  type Props = {
8
7
  description?: string
9
8
  disabled?: boolean
10
- error?: FieldError
9
+ error?: string
11
10
  label: string
12
11
  name: string
13
12
  placeholder?: string
@@ -1,7 +1,7 @@
1
1
  import {SelectIcon} from '@sanity/icons'
2
2
  import {Box, Button, Menu, MenuButton, MenuDivider, MenuItem} from '@sanity/ui'
3
3
  import {
4
- ReactSelectOption,
4
+ TagSelectOption,
5
5
  SearchFacetInputSearchableProps,
6
6
  SearchFacetOperatorType,
7
7
  WithId
@@ -31,7 +31,7 @@ const SearchFacetTags = ({facet}: Props) => {
31
31
 
32
32
  const popoverProps = usePortalPopoverProps()
33
33
 
34
- const handleChange = (option: ReactSelectOption) => {
34
+ const handleChange = (option: TagSelectOption) => {
35
35
  dispatch(
36
36
  searchActions.facetsUpdateById({
37
37
  id: facet.id,
@@ -100,7 +100,7 @@ const SearchFacetTags = ({facet}: Props) => {
100
100
  isSearchable
101
101
  name="tags"
102
102
  noOptionsMessage={() => 'No tags'}
103
- onChange={value => handleChange(value as ReactSelectOption)}
103
+ onChange={value => handleChange(value as TagSelectOption)}
104
104
  options={allTagOptions}
105
105
  placeholder={tagsFetching ? 'Loading...' : 'Select...'}
106
106
  styles={reactSelectStyles}
@@ -0,0 +1,22 @@
1
+ import * as z from 'zod'
2
+
3
+ export const tagOptionSchema = z.object({
4
+ label: z.string().trim().min(1, {message: 'Label cannot be empty'}),
5
+ value: z.string().trim().min(1, {message: 'Value cannot be empty'})
6
+ })
7
+
8
+ export const assetFormSchema = z.object({
9
+ altText: z.string().trim().optional(),
10
+ description: z.string().trim().optional(),
11
+ opt: z.object({
12
+ media: z.object({
13
+ tags: z.array(tagOptionSchema).nullable()
14
+ })
15
+ }),
16
+ originalFilename: z.string().trim().min(1, {message: 'Filename cannot be empty'}),
17
+ title: z.string().trim().optional()
18
+ })
19
+
20
+ export const tagFormSchema = z.object({
21
+ name: z.string().min(1, {message: 'Name cannot be empty'})
22
+ })
@@ -1,6 +1,6 @@
1
1
  import {createSelector, createSlice, PayloadAction} from '@reduxjs/toolkit'
2
2
  import type {ClientError, Transaction} from '@sanity/client'
3
- import type {Asset, HttpError, MyEpic, ReactSelectOption, Tag, TagItem} from '@types'
3
+ import type {Asset, HttpError, MyEpic, TagSelectOption, Tag, TagItem} from '@types'
4
4
  import groq from 'groq'
5
5
  import {Selector} from 'react-redux'
6
6
  import {ofType} from 'redux-observable'
@@ -523,7 +523,7 @@ export const selectTagById = createSelector(
523
523
  // Map tag references to react-select options, skipping over items with no linked tags
524
524
  export const selectTagSelectOptions =
525
525
  (asset?: Asset) =>
526
- (state: RootReducerState): ReactSelectOption[] | null => {
526
+ (state: RootReducerState): TagSelectOption[] | null => {
527
527
  const tags = asset?.opt?.media?.tags?.reduce((acc: TagItem[], v) => {
528
528
  const tagItem = state.tags.byIds[v._ref]
529
529
  if (tagItem?.tag) {
@@ -6,6 +6,8 @@ import type {
6
6
  SanityImageAssetDocument
7
7
  } from '@sanity/client'
8
8
  import type {Epic} from 'redux-observable'
9
+ import * as z from 'zod'
10
+ import {assetFormSchema, tagFormSchema, tagOptionSchema} from '../formSchema'
9
11
  import {RootReducerState} from '../modules/types'
10
12
 
11
13
  type CustomFields = {
@@ -30,6 +32,8 @@ type SearchFacetInputCommon = {
30
32
 
31
33
  export type Asset = FileAsset | ImageAsset
32
34
 
35
+ export type AssetFormData = z.infer<typeof assetFormSchema>
36
+
33
37
  export type AssetItem = {
34
38
  _type: 'asset'
35
39
  asset: Asset
@@ -164,11 +168,6 @@ export type Order = {
164
168
 
165
169
  export type OrderDirection = 'asc' | 'desc'
166
170
 
167
- export type ReactSelectOption = {
168
- label: string
169
- value: string
170
- }
171
-
172
171
  export type SanityReference = {
173
172
  _ref: string
174
173
  _type: 'reference'
@@ -210,7 +209,7 @@ export type SearchFacetInputSearchableProps = SearchFacetInputCommon & {
210
209
  name: string
211
210
  options?: SearchFacetInputSelectListItemProps[]
212
211
  type: 'searchable'
213
- value?: ReactSelectOption
212
+ value?: TagSelectOption
214
213
  }
215
214
 
216
215
  export type SearchFacetInputSelectProps = SearchFacetInputCommon & {
@@ -312,6 +311,8 @@ export type Tag = SanityDocument & {
312
311
 
313
312
  export type TagActions = 'applyAll' | 'delete' | 'edit' | 'removeAll' | 'search'
314
313
 
314
+ export type TagFormData = z.infer<typeof tagFormSchema>
315
+
315
316
  export type TagItem = {
316
317
  _type: 'tag'
317
318
  tag: Tag
@@ -320,6 +321,8 @@ export type TagItem = {
320
321
  updating: boolean
321
322
  }
322
323
 
324
+ export type TagSelectOption = z.infer<typeof tagOptionSchema>
325
+
323
326
  export type UploadItem = {
324
327
  _type: 'upload'
325
328
  assetType: AssetType
@@ -1,7 +1,7 @@
1
- import {ReactSelectOption, TagItem} from '@types'
1
+ import {TagSelectOption, TagItem} from '@types'
2
2
 
3
- const getTagSelectOptions = (tags: TagItem[]): ReactSelectOption[] => {
4
- return tags.reduce((acc: ReactSelectOption[], val) => {
3
+ const getTagSelectOptions = (tags: TagItem[]): TagSelectOption[] => {
4
+ return tags.reduce((acc: TagSelectOption[], val) => {
5
5
  const tag = val?.tag
6
6
  if (tag) {
7
7
  acc.push({