setting-content.tsx 3.2 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889
  1. import React, { useCallback, useMemo, useState } from 'react'
  2. import produce from 'immer'
  3. import { useTranslation } from 'react-i18next'
  4. import { RiCloseLine } from '@remixicon/react'
  5. import FileUploadSetting from '@/app/components/workflow/nodes/_base/components/file-upload-setting'
  6. import Button from '@/app/components/base/button'
  7. import { useFeatures, useFeaturesStore } from '@/app/components/base/features/hooks'
  8. import type { OnFeaturesChange } from '@/app/components/base/features/types'
  9. import type { UploadFileSetting } from '@/app/components/workflow/types'
  10. import { SupportUploadFileTypes } from '@/app/components/workflow/types'
  11. import { FILE_EXTS } from '@/app/components/base/prompt-editor/constants'
  12. type SettingContentProps = {
  13. imageUpload?: boolean
  14. onClose: () => void
  15. onChange?: OnFeaturesChange
  16. }
  17. const SettingContent = ({
  18. imageUpload,
  19. onClose,
  20. onChange,
  21. }: SettingContentProps) => {
  22. const { t } = useTranslation()
  23. const featuresStore = useFeaturesStore()
  24. const file = useFeatures(state => state.features.file)
  25. const fileSettingPayload = useMemo(() => {
  26. return {
  27. allowed_file_upload_methods: file?.allowed_file_upload_methods || ['local_file', 'remote_url'],
  28. allowed_file_types: file?.allowed_file_types || [SupportUploadFileTypes.image],
  29. allowed_file_extensions: file?.allowed_file_extensions || FILE_EXTS[SupportUploadFileTypes.image],
  30. max_length: file?.number_limits || 3,
  31. } as UploadFileSetting
  32. }, [file])
  33. const [tempPayload, setTempPayload] = useState<UploadFileSetting>(fileSettingPayload)
  34. const handleChange = useCallback(() => {
  35. const {
  36. features,
  37. setFeatures,
  38. } = featuresStore!.getState()
  39. const newFeatures = produce(features, (draft) => {
  40. draft.file = {
  41. ...draft.file,
  42. allowed_file_upload_methods: tempPayload.allowed_file_upload_methods,
  43. number_limits: tempPayload.max_length,
  44. allowed_file_types: tempPayload.allowed_file_types,
  45. allowed_file_extensions: tempPayload.allowed_file_extensions,
  46. }
  47. })
  48. setFeatures(newFeatures)
  49. if (onChange)
  50. onChange()
  51. }, [featuresStore, onChange, tempPayload])
  52. return (
  53. <>
  54. <div className='mb-4 flex items-center justify-between'>
  55. <div className='text-text-primary system-xl-semibold'>{!imageUpload ? t('appDebug.feature.fileUpload.modalTitle') : t('appDebug.feature.imageUpload.modalTitle')}</div>
  56. <div className='p-1 cursor-pointer' onClick={onClose}><RiCloseLine className='w-4 h-4 text-text-tertiary'/></div>
  57. </div>
  58. <FileUploadSetting
  59. isMultiple
  60. inFeaturePanel
  61. hideSupportFileType={imageUpload}
  62. payload={tempPayload}
  63. onChange={(p: UploadFileSetting) => setTempPayload(p)}
  64. />
  65. <div className='mt-4 flex items-center justify-end'>
  66. <Button
  67. onClick={onClose}
  68. className='mr-2'
  69. >
  70. {t('common.operation.cancel')}
  71. </Button>
  72. <Button
  73. variant='primary'
  74. onClick={handleChange}
  75. disabled={tempPayload.allowed_file_types.length === 0}
  76. >
  77. {t('common.operation.save')}
  78. </Button>
  79. </div>
  80. </>
  81. )
  82. }
  83. export default React.memo(SettingContent)