feat: update provider row after saving credentials (#8914)
This commit is contained in:
@@ -78,7 +78,6 @@ export function ModelProviderRow({
|
|||||||
const [setupOutput, setSetupOutput] = useState<SetupOutputLine[]>([]);
|
const [setupOutput, setSetupOutput] = useState<SetupOutputLine[]>([]);
|
||||||
const [setupError, setSetupError] = useState("");
|
const [setupError, setSetupError] = useState("");
|
||||||
const [showSavedState, setShowSavedState] = useState(false);
|
const [showSavedState, setShowSavedState] = useState(false);
|
||||||
const [preserveSetupLayout, setPreserveSetupLayout] = useState(false);
|
|
||||||
const setupLineCounter = useRef(0);
|
const setupLineCounter = useRef(0);
|
||||||
const hasLoadedConfig = useRef(false);
|
const hasLoadedConfig = useRef(false);
|
||||||
const shouldRestorePanelFocus = useRef(false);
|
const shouldRestorePanelFocus = useRef(false);
|
||||||
@@ -170,7 +169,6 @@ export function ModelProviderRow({
|
|||||||
setEditingKey(null);
|
setEditingKey(null);
|
||||||
setError("");
|
setError("");
|
||||||
setShowSavedState(false);
|
setShowSavedState(false);
|
||||||
setPreserveSetupLayout(false);
|
|
||||||
|
|
||||||
const unlisten = await onModelSetupOutput(provider.id, appendSetupOutput);
|
const unlisten = await onModelSetupOutput(provider.id, appendSetupOutput);
|
||||||
|
|
||||||
@@ -195,7 +193,6 @@ export function ModelProviderRow({
|
|||||||
setExpanded((current) => {
|
setExpanded((current) => {
|
||||||
if (current) {
|
if (current) {
|
||||||
setShowSavedState(false);
|
setShowSavedState(false);
|
||||||
setPreserveSetupLayout(false);
|
|
||||||
}
|
}
|
||||||
return !current;
|
return !current;
|
||||||
});
|
});
|
||||||
@@ -295,8 +292,7 @@ export function ModelProviderRow({
|
|||||||
})),
|
})),
|
||||||
);
|
);
|
||||||
await loadConfig();
|
await loadConfig();
|
||||||
setShowSavedState(true);
|
setShowSavedState(false);
|
||||||
setPreserveSetupLayout(true);
|
|
||||||
} catch (nextError) {
|
} catch (nextError) {
|
||||||
setError(
|
setError(
|
||||||
nextError instanceof Error ? nextError.message : "Failed to save",
|
nextError instanceof Error ? nextError.message : "Failed to save",
|
||||||
@@ -312,7 +308,6 @@ export function ModelProviderRow({
|
|||||||
setEditingKey(null);
|
setEditingKey(null);
|
||||||
setError("");
|
setError("");
|
||||||
setShowSavedState(false);
|
setShowSavedState(false);
|
||||||
setPreserveSetupLayout(false);
|
|
||||||
} catch (nextError) {
|
} catch (nextError) {
|
||||||
setError(
|
setError(
|
||||||
nextError instanceof Error ? nextError.message : "Failed to remove",
|
nextError instanceof Error ? nextError.message : "Failed to remove",
|
||||||
@@ -403,7 +398,7 @@ export function ModelProviderRow({
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (hasFields && isConnected && !preserveSetupLayout) {
|
if (hasFields && isConnected) {
|
||||||
return (
|
return (
|
||||||
<ConnectedFieldsPanel
|
<ConnectedFieldsPanel
|
||||||
panelRef={panelRef}
|
panelRef={panelRef}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import { render, screen, waitFor } from "@testing-library/react";
|
import { render, screen, waitFor } from "@testing-library/react";
|
||||||
import userEvent from "@testing-library/user-event";
|
import userEvent from "@testing-library/user-event";
|
||||||
import type { ComponentType } from "react";
|
import { useState, type ComponentType } from "react";
|
||||||
import { beforeEach, describe, expect, it, vi } from "vitest";
|
import { beforeEach, describe, expect, it, vi } from "vitest";
|
||||||
import { getModelProviders } from "@/features/providers/providerCatalog";
|
import { getModelProviders } from "@/features/providers/providerCatalog";
|
||||||
import { ModelProviderRow } from "../ModelProviderRow";
|
import { ModelProviderRow } from "../ModelProviderRow";
|
||||||
@@ -110,4 +110,59 @@ describe("ModelProviderRow", () => {
|
|||||||
|
|
||||||
expect(screen.getByText(/model refresh failed/i)).toBeInTheDocument();
|
expect(screen.getByText(/model refresh failed/i)).toBeInTheDocument();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it("switches from setup save to connected controls after first configuration", async () => {
|
||||||
|
const user = userEvent.setup();
|
||||||
|
let saved = false;
|
||||||
|
|
||||||
|
function SetupSaveRow() {
|
||||||
|
const [status, setStatus] = useState<"connected" | "not_configured">(
|
||||||
|
"not_configured",
|
||||||
|
);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<ModelProviderRow
|
||||||
|
provider={modelProvider("google", status)}
|
||||||
|
onGetConfig={async () =>
|
||||||
|
saved
|
||||||
|
? [
|
||||||
|
{
|
||||||
|
key: "GOOGLE_API_KEY",
|
||||||
|
value: null,
|
||||||
|
isSet: true,
|
||||||
|
isSecret: true,
|
||||||
|
required: true,
|
||||||
|
},
|
||||||
|
]
|
||||||
|
: []
|
||||||
|
}
|
||||||
|
onSaveFields={async () => {
|
||||||
|
saved = true;
|
||||||
|
setStatus("connected");
|
||||||
|
}}
|
||||||
|
onRemoveConfig={onRemoveConfig}
|
||||||
|
onCompleteNativeSetup={onCompleteNativeSetup}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
render(<SetupSaveRow />);
|
||||||
|
|
||||||
|
await user.click(screen.getByRole("button", { name: /google gemini/i }));
|
||||||
|
await user.type(
|
||||||
|
await screen.findByPlaceholderText(/paste your api key/i),
|
||||||
|
"google-token",
|
||||||
|
);
|
||||||
|
await user.click(screen.getByRole("button", { name: /^save$/i }));
|
||||||
|
|
||||||
|
await waitFor(() =>
|
||||||
|
expect(
|
||||||
|
screen.getByRole("button", { name: /disconnect/i }),
|
||||||
|
).toBeInTheDocument(),
|
||||||
|
);
|
||||||
|
expect(screen.getByRole("button", { name: /edit/i })).toBeInTheDocument();
|
||||||
|
expect(
|
||||||
|
screen.queryByRole("button", { name: /saved/i }),
|
||||||
|
).not.toBeInTheDocument();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
Reference in New Issue
Block a user