You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

credential-panel.tsx 4.9KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147
  1. import { useMemo } from 'react'
  2. import { useTranslation } from 'react-i18next'
  3. import type {
  4. ModelProvider,
  5. } from '../declarations'
  6. import {
  7. ConfigurationMethodEnum,
  8. CustomConfigurationStatusEnum,
  9. PreferredProviderTypeEnum,
  10. } from '../declarations'
  11. import {
  12. useUpdateModelList,
  13. useUpdateModelProviders,
  14. } from '../hooks'
  15. import PrioritySelector from './priority-selector'
  16. import PriorityUseTip from './priority-use-tip'
  17. import { UPDATE_MODEL_PROVIDER_CUSTOM_MODEL_LIST } from './index'
  18. import Indicator from '@/app/components/header/indicator'
  19. import { changeModelProviderPriority } from '@/service/common'
  20. import { useToastContext } from '@/app/components/base/toast'
  21. import { useEventEmitterContextContext } from '@/context/event-emitter'
  22. import cn from '@/utils/classnames'
  23. import { useCredentialStatus } from '@/app/components/header/account-setting/model-provider-page/model-auth/hooks'
  24. import { ConfigProvider } from '@/app/components/header/account-setting/model-provider-page/model-auth'
  25. type CredentialPanelProps = {
  26. provider: ModelProvider
  27. }
  28. const CredentialPanel = ({
  29. provider,
  30. }: CredentialPanelProps) => {
  31. const { t } = useTranslation()
  32. const { notify } = useToastContext()
  33. const { eventEmitter } = useEventEmitterContextContext()
  34. const updateModelList = useUpdateModelList()
  35. const updateModelProviders = useUpdateModelProviders()
  36. const customConfig = provider.custom_configuration
  37. const systemConfig = provider.system_configuration
  38. const priorityUseType = provider.preferred_provider_type
  39. const isCustomConfigured = customConfig.status === CustomConfigurationStatusEnum.active
  40. const configurateMethods = provider.configurate_methods
  41. const {
  42. hasCredential,
  43. authorized,
  44. authRemoved,
  45. current_credential_name,
  46. notAllowedToUse,
  47. } = useCredentialStatus(provider)
  48. const handleChangePriority = async (key: PreferredProviderTypeEnum) => {
  49. const res = await changeModelProviderPriority({
  50. url: `/workspaces/current/model-providers/${provider.provider}/preferred-provider-type`,
  51. body: {
  52. preferred_provider_type: key,
  53. },
  54. })
  55. if (res.result === 'success') {
  56. notify({ type: 'success', message: t('common.actionMsg.modifiedSuccessfully') })
  57. updateModelProviders()
  58. configurateMethods.forEach((method) => {
  59. if (method === ConfigurationMethodEnum.predefinedModel)
  60. provider.supported_model_types.forEach(modelType => updateModelList(modelType))
  61. })
  62. eventEmitter?.emit({
  63. type: UPDATE_MODEL_PROVIDER_CUSTOM_MODEL_LIST,
  64. payload: provider.provider,
  65. } as any)
  66. }
  67. }
  68. const credentialLabel = useMemo(() => {
  69. if (!hasCredential)
  70. return t('common.modelProvider.auth.unAuthorized')
  71. if (authorized)
  72. return current_credential_name
  73. if (authRemoved)
  74. return t('common.modelProvider.auth.authRemoved')
  75. return ''
  76. }, [authorized, authRemoved, current_credential_name, hasCredential])
  77. const color = useMemo(() => {
  78. if (authRemoved)
  79. return 'red'
  80. if (notAllowedToUse)
  81. return 'gray'
  82. return 'green'
  83. }, [authRemoved, notAllowedToUse])
  84. return (
  85. <>
  86. {
  87. provider.provider_credential_schema && (
  88. <div className={cn(
  89. 'relative ml-1 w-[120px] shrink-0 rounded-lg border-[0.5px] border-components-panel-border bg-white/[0.18] p-1',
  90. authRemoved && 'border-state-destructive-border bg-state-destructive-hover',
  91. )}>
  92. <div className='system-xs-medium mb-1 flex h-5 items-center justify-between pl-2 pr-[7px] pt-1 text-text-tertiary'>
  93. <div
  94. className={cn(
  95. 'grow truncate',
  96. authRemoved && 'text-text-destructive',
  97. )}
  98. title={credentialLabel}
  99. >
  100. {credentialLabel}
  101. </div>
  102. <Indicator className='shrink-0' color={color} />
  103. </div>
  104. <div className='flex items-center gap-0.5'>
  105. <ConfigProvider
  106. provider={provider}
  107. configurationMethod={ConfigurationMethodEnum.predefinedModel}
  108. />
  109. {
  110. systemConfig.enabled && isCustomConfigured && (
  111. <PrioritySelector
  112. value={priorityUseType}
  113. onSelect={handleChangePriority}
  114. />
  115. )
  116. }
  117. </div>
  118. {
  119. priorityUseType === PreferredProviderTypeEnum.custom && systemConfig.enabled && (
  120. <PriorityUseTip />
  121. )
  122. }
  123. </div>
  124. )
  125. }
  126. {
  127. systemConfig.enabled && isCustomConfigured && !provider.provider_credential_schema && (
  128. <div className='ml-1'>
  129. <PrioritySelector
  130. value={priorityUseType}
  131. onSelect={handleChangePriority}
  132. />
  133. </div>
  134. )
  135. }
  136. </>
  137. )
  138. }
  139. export default CredentialPanel