api-input.tsx 2.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081
  1. 'use client'
  2. import type { FC } from 'react'
  3. import React, { useState } from 'react'
  4. import { useTranslation } from 'react-i18next'
  5. import { RiArrowDownSLine } from '@remixicon/react'
  6. import { Method } from '../types'
  7. import Selector from '../../_base/components/selector'
  8. import useAvailableVarList from '../../_base/hooks/use-available-var-list'
  9. import { VarType } from '../../../types'
  10. import type { Var } from '../../../types'
  11. import cn from '@/utils/classnames'
  12. import Input from '@/app/components/workflow/nodes/_base/components/input-support-select-var'
  13. const MethodOptions = [
  14. { label: 'GET', value: Method.get },
  15. { label: 'POST', value: Method.post },
  16. { label: 'HEAD', value: Method.head },
  17. { label: 'PATCH', value: Method.patch },
  18. { label: 'PUT', value: Method.put },
  19. { label: 'DELETE', value: Method.delete },
  20. ]
  21. type Props = {
  22. nodeId: string
  23. readonly: boolean
  24. method: Method
  25. onMethodChange: (method: Method) => void
  26. url: string
  27. onUrlChange: (url: string) => void
  28. }
  29. const ApiInput: FC<Props> = ({
  30. nodeId,
  31. readonly,
  32. method,
  33. onMethodChange,
  34. url,
  35. onUrlChange,
  36. }) => {
  37. const { t } = useTranslation()
  38. const [isFocus, setIsFocus] = useState(false)
  39. const { availableVars, availableNodesWithParent } = useAvailableVarList(nodeId, {
  40. onlyLeafNodeVar: false,
  41. filterVar: (varPayload: Var) => {
  42. return [VarType.string, VarType.number, VarType.secret].includes(varPayload.type)
  43. },
  44. })
  45. return (
  46. <div className='flex items-start space-x-1'>
  47. <Selector
  48. value={method}
  49. onChange={onMethodChange}
  50. options={MethodOptions}
  51. trigger={
  52. <div className={cn(readonly && 'cursor-pointer', 'h-8 shrink-0 flex items-center px-2.5 bg-gray-100 border-black/5 rounded-lg')} >
  53. <div className='w-12 pl-0.5 leading-[18px] text-xs font-medium text-gray-900 uppercase'>{method}</div>
  54. {!readonly && <RiArrowDownSLine className='ml-1 w-3.5 h-3.5 text-gray-700' />}
  55. </div>
  56. }
  57. popupClassName='top-[34px] w-[108px]'
  58. showChecked
  59. readonly={readonly}
  60. />
  61. <Input
  62. instanceId='http-api-url'
  63. className={cn(isFocus ? 'shadow-xs bg-gray-50 border-gray-300' : 'bg-gray-100 border-gray-100', 'w-0 grow rounded-lg px-3 py-[6px] border')}
  64. value={url}
  65. onChange={onUrlChange}
  66. readOnly={readonly}
  67. nodesOutputVars={availableVars}
  68. availableNodes={availableNodesWithParent}
  69. onFocusChange={setIsFocus}
  70. placeholder={!readonly ? t('workflow.nodes.http.apiPlaceholder')! : ''}
  71. placeholderClassName='!leading-[21px]'
  72. />
  73. </div >
  74. )
  75. }
  76. export default React.memo(ApiInput)