🐛 fix: fix api key input issue (#6112)

* fix api key input issue

* try to fix clerk auth
This commit is contained in:
Arvin Xu
2025-02-13 23:47:11 +08:00
committed by GitHub
parent 8ed48c93f2
commit 48e3b85029
5 changed files with 72 additions and 51 deletions
@@ -45,5 +45,3 @@ const Page = async (props: PagePropsWithId) => {
};
export default Page;
export const dynamic = 'auto';
@@ -0,0 +1,11 @@
import { createContext } from 'react';
interface LoadingContextValue {
loading: boolean;
setLoading: (loading: boolean) => void;
}
export const LoadingContext = createContext<LoadingContextValue>({
loading: false,
setLoading: () => {},
});
@@ -1,9 +1,11 @@
import { Icon } from '@lobehub/ui';
import { Button, Input } from 'antd';
import { Network } from 'lucide-react';
import { ReactNode, memo, useState } from 'react';
import { Button } from 'antd';
import { Loader2Icon, Network } from 'lucide-react';
import { ReactNode, memo, useContext, useState } from 'react';
import { useTranslation } from 'react-i18next';
import { FormInput, FormPassword } from '@/components/FormInput';
import { LoadingContext } from '@/features/Conversation/Error/APIKeyForm/LoadingContext';
import { useProviderName } from '@/hooks/useProviderName';
import { featureFlagsSelectors, useServerConfigStore } from '@/store/serverConfig';
import { GlobalLLMProviderKey } from '@/types/user/settings';
@@ -27,6 +29,7 @@ const ProviderApiKeyForm = memo<ProviderApiKeyFormProps>(
const { apiKey, baseURL, setConfig } = useApiKey(provider);
const { showOpenAIProxyUrl } = useServerConfigStore(featureFlagsSelectors);
const providerName = useProviderName(provider);
const { loading } = useContext(LoadingContext);
return (
<FormAction
@@ -34,25 +37,25 @@ const ProviderApiKeyForm = memo<ProviderApiKeyFormProps>(
description={t(`unlock.apiKey.description`, { name: providerName, ns: 'error' })}
title={t(`unlock.apiKey.title`, { name: providerName, ns: 'error' })}
>
<Input.Password
<FormPassword
autoComplete={'new-password'}
onChange={(e) => {
setConfig(provider, { apiKey: e.target.value });
onChange={(value) => {
setConfig(provider, { apiKey: value });
}}
placeholder={apiKeyPlaceholder || 'sk-***********************'}
type={'block'}
suffix={<div>{loading && <Icon icon={Loader2Icon} spin />}</div>}
value={apiKey}
/>
{showEndpoint &&
showOpenAIProxyUrl &&
(showProxy ? (
<Input
onChange={(e) => {
setConfig(provider, { baseURL: e.target.value });
<FormInput
onChange={(value) => {
setConfig(provider, { baseURL: value });
}}
placeholder={'https://api.openai.com/v1'}
type={'block'}
suffix={<div>{loading && <Icon icon={Loader2Icon} spin />}</div>}
value={baseURL}
/>
) : (
@@ -1,6 +1,6 @@
import { ProviderIcon } from '@lobehub/icons';
import { Button } from 'antd';
import { memo, useMemo } from 'react';
import { memo, useMemo, useState } from 'react';
import { useTranslation } from 'react-i18next';
import { Center, Flexbox } from 'react-layout-kit';
@@ -9,6 +9,7 @@ import { useChatStore } from '@/store/chat';
import { GlobalLLMProviderKey } from '@/types/user/settings';
import BedrockForm from './Bedrock';
import { LoadingContext } from './LoadingContext';
import ProviderApiKeyForm from './ProviderApiKeyForm';
interface APIKeyFormProps {
@@ -18,6 +19,7 @@ interface APIKeyFormProps {
const APIKeyForm = memo<APIKeyFormProps>(({ id, provider }) => {
const { t } = useTranslation('error');
const [loading, setLoading] = useState(false);
const [resend, deleteMessage] = useChatStore((s) => [s.regenerateMessage, s.deleteMessage]);
@@ -62,38 +64,41 @@ const APIKeyForm = memo<APIKeyFormProps>(({ id, provider }) => {
}, [provider]);
return (
<Center gap={16} style={{ maxWidth: 300 }}>
{provider === ModelProvider.Bedrock ? (
<BedrockForm />
) : (
<ProviderApiKeyForm
apiKeyPlaceholder={apiKeyPlaceholder}
avatar={<ProviderIcon provider={provider} size={80} type={'avatar'} />}
provider={provider as GlobalLLMProviderKey}
showEndpoint={provider === ModelProvider.OpenAI}
/>
)}
<Flexbox gap={12} width={'100%'}>
<Button
block
onClick={() => {
resend(id);
deleteMessage(id);
}}
style={{ marginTop: 8 }}
type={'primary'}
>
{t('unlock.confirm')}
</Button>
<Button
onClick={() => {
deleteMessage(id);
}}
>
{t('unlock.closeMessage')}
</Button>
</Flexbox>
</Center>
<LoadingContext value={{ loading, setLoading }}>
<Center gap={16} style={{ maxWidth: 300 }}>
{provider === ModelProvider.Bedrock ? (
<BedrockForm />
) : (
<ProviderApiKeyForm
apiKeyPlaceholder={apiKeyPlaceholder}
avatar={<ProviderIcon provider={provider} size={80} type={'avatar'} />}
provider={provider as GlobalLLMProviderKey}
showEndpoint={provider === ModelProvider.OpenAI}
/>
)}
<Flexbox gap={12} width={'100%'}>
<Button
block
disabled={loading}
onClick={() => {
resend(id);
deleteMessage(id);
}}
style={{ marginTop: 8 }}
type={'primary'}
>
{t('unlock.confirm')}
</Button>
<Button
onClick={() => {
deleteMessage(id);
}}
>
{t('unlock.closeMessage')}
</Button>
</Flexbox>
</Center>
</LoadingContext>
);
});
@@ -1,6 +1,8 @@
import isEqual from 'fast-deep-equal';
import { useContext } from 'react';
import { isDeprecatedEdition } from '@/const/version';
import { LoadingContext } from '@/features/Conversation/Error/APIKeyForm/LoadingContext';
import { aiProviderSelectors, useAiInfraStore } from '@/store/aiInfra';
import { useUserStore } from '@/store/user';
import { keyVaultsConfigSelectors } from '@/store/user/selectors';
@@ -11,7 +13,7 @@ export const useApiKey = (provider: string) => {
keyVaultsConfigSelectors.getVaultByProvider(provider as any)(s)?.baseURL,
s.updateKeyVaultConfig,
]);
const { setLoading } = useContext(LoadingContext);
const updateAiProviderConfig = useAiInfraStore((s) => s.updateAiProviderConfig);
const data = useAiInfraStore(aiProviderSelectors.providerConfigById(provider), isEqual);
@@ -23,12 +25,14 @@ export const useApiKey = (provider: string) => {
apiKey: data?.keyVaults.apiKey,
baseURL: data?.keyVaults?.baseURL,
setConfig: async (id: string, params: Record<string, string>) => {
const next = { ...data?.keyVaults, ...params };
if (isEqual(data?.keyVaults, next)) return;
setLoading(true);
await updateAiProviderConfig(id, {
keyVaults: {
...data?.keyVaults,
...params,
},
keyVaults: { ...data?.keyVaults, ...params },
});
setLoading(false);
},
};
};