import { memo, useCallback, useRef, useState, } from 'react' import { RiArrowDownSLine, } from '@remixicon/react' import { useTranslation } from 'react-i18next' import { PortalToFollowElem, PortalToFollowElemContent, PortalToFollowElemTrigger, } from '@/app/components/base/portal-to-follow-elem' import Button from '@/app/components/base/button' import Indicator from '@/app/components/header/indicator' import cn from '@/utils/classnames' import Confirm from '@/app/components/base/confirm' import Authorize from '../authorize' import type { Credential } from '../types' import { CredentialTypeEnum } from '../types' import ApiKeyModal from '../authorize/api-key-modal' import Item from './item' import { useDeletePluginToolCredential, useInvalidPluginToolCredentialInfo, useSetPluginToolDefaultCredential, } from '@/service/use-plugins-auth' import { useToastContext } from '@/app/components/base/toast' type AuthorizedProps = { provider: string credentials: Credential[] canOAuth?: boolean canApiKey?: boolean disabled?: boolean } const Authorized = ({ provider, credentials, canOAuth, canApiKey, disabled, }: AuthorizedProps) => { const { t } = useTranslation() const { notify } = useToastContext() const [isOpen, setIsOpen] = useState(false) const oAuthCredentials = credentials.filter(credential => credential.credential_type === CredentialTypeEnum.OAUTH2) const apiKeyCredentials = credentials.filter(credential => credential.credential_type === CredentialTypeEnum.API_KEY) const pendingOperationCredentialId = useRef(null) const [deleteCredentialId, setDeleteCredentialId] = useState(null) const { mutateAsync: deletePluginToolCredential } = useDeletePluginToolCredential(provider) const invalidatePluginToolCredentialInfo = useInvalidPluginToolCredentialInfo(provider) const openConfirm = useCallback((credentialId?: string) => { if (credentialId) pendingOperationCredentialId.current = credentialId setDeleteCredentialId(pendingOperationCredentialId.current) }, []) const closeConfirm = useCallback(() => { setDeleteCredentialId(null) pendingOperationCredentialId.current = null }, []) const handleConfirm = useCallback(async () => { if (!pendingOperationCredentialId.current) { setDeleteCredentialId(null) return } await deletePluginToolCredential({ credential_id: pendingOperationCredentialId.current }) notify({ type: 'success', message: t('common.api.actionSuccess'), }) invalidatePluginToolCredentialInfo() setDeleteCredentialId(null) pendingOperationCredentialId.current = null }, [deletePluginToolCredential, invalidatePluginToolCredentialInfo, notify, t]) const [editValues, setEditValues] = useState | null>(null) const handleEdit = useCallback((id: string, values: Record) => { pendingOperationCredentialId.current = id setEditValues(values) }, []) const handleRemove = useCallback(() => { setDeleteCredentialId(pendingOperationCredentialId.current) }, []) const { mutateAsync: setPluginToolDefaultCredential } = useSetPluginToolDefaultCredential(provider) const handleSetDefault = useCallback(async (id: string) => { await setPluginToolDefaultCredential(id) notify({ type: 'success', message: t('common.api.actionSuccess'), }) invalidatePluginToolCredentialInfo() }, [setPluginToolDefaultCredential, invalidatePluginToolCredentialInfo, notify, t]) return ( <> setIsOpen(!isOpen)} asChild >
{ !!oAuthCredentials.length && (
OAuth
{ oAuthCredentials.map(credential => ( )) }
) } { !!apiKeyCredentials.length && (
API Keys
{ apiKeyCredentials.map(credential => ( )) }
) }
{ deleteCredentialId && ( ) } { !!editValues && ( { setEditValues(null) pendingOperationCredentialId.current = null }} onRemove={handleRemove} /> ) } ) } export default memo(Authorized)