fix(ui): rename All Models tab to Deployed Models and model filters to All Proxy Models (#43638)

* fix(ui): rename All Models tab to Deployed Models and view filter to All Proxy Models

Co-Authored-By: Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com>

* fix(ui): use All Proxy Models label for the public model name filter

Co-Authored-By: Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com>

* test(e2e): rename ALL_MODELS_VIEW constant to ALL_PROXY_MODELS_VIEW

Co-Authored-By: Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com>

---------

Co-authored-by: kerry <kerry@berri.ai>
Co-authored-by: Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com>
This commit is contained in:
devin-ai-integration[bot] 2026-09-28 17:59:47 -07:00 • committed by GitHub
parent 98c710c411
commit f4a217d005
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
7 changed files with 37 additions and 25 deletions

View file

@ -17,7 +17,7 @@ import { CHAT_MODEL_A, CHAT_MODEL_B, masterKey } from "../../helpers/traffic";
const MOCK_LLM_BASE = `http://127.0.0.1:${process.env.MOCK_LLM_PORT ?? "8090"}/v1`;
const CURRENT_TEAM_VIEW = "Current Team Models";
const ALL_MODELS_VIEW = "All Available Models";
const ALL_PROXY_MODELS_VIEW = "All Proxy Models";
const PERSONAL_TEAM = "Personal";
const teamSelector = (page: PlaywrightPage): Locator =>
@ -174,10 +174,10 @@ test.describe("Models and Endpoints for an internal user", () => {
`${ungrantedModelName} is granted to no team and must not leak into ${E2E_TEAM_ORG_ALIAS}`,
).toHaveCount(0);
await chooseOption(page, viewSelector(page), ALL_MODELS_VIEW);
await chooseOption(page, viewSelector(page), ALL_PROXY_MODELS_VIEW);
await expect(
modelRow(page, CHAT_MODEL_A),
`switching to ${ALL_MODELS_VIEW} leaves the table populated rather than blanking it`,
`switching to ${ALL_PROXY_MODELS_VIEW} leaves the table populated rather than blanking it`,
).toHaveCount(1, { timeout: 15_000 });
await expect(page).toHaveURL((url) =>
@ -192,7 +192,7 @@ test.describe("Models and Endpoints for an internal user", () => {
await expect(
viewSelector(page),
"the selected view is restored from the URL after a reload",
).toContainText(ALL_MODELS_VIEW, { timeout: 15_000 });
).toContainText(ALL_PROXY_MODELS_VIEW, { timeout: 15_000 });
await expect(modelRow(page, CHAT_MODEL_A)).toHaveCount(1, { timeout: 15_000 });
await expect(page.getByTestId("pagination-range")).toHaveText("Showing 1-1 of 1");
await expect(modelRow(page, CHAT_MODEL_B)).toHaveCount(0);

View file

@ -362,7 +362,7 @@ test.describe("Add Model", () => {
await expect(page.getByText(/Connection to .* failed/)).toBeVisible({ timeout: 30_000 });
});
test("Add specific model and verify it appears in All Models", async ({ page }) => {
test("Add specific model and verify it appears in Deployed Models", async ({ page }) => {
await navigateToPage(page, Page.Models);
await page.getByRole("tab", { name: "Add Model" }).click();
@ -389,8 +389,8 @@ test.describe("Add Model", () => {
// Wait for success notification
await expect(page.getByText("created successfully")).toBeVisible({ timeout: 15_000 });
// Navigate to All Models tab
await page.getByRole("tab", { name: "All Models" }).click();
// Navigate to Deployed Models tab
await page.getByRole("tab", { name: "Deployed Models" }).click();
await page.waitForLoadState("networkidle");
// Search for the model we just added
@ -469,7 +469,7 @@ test.describe("Add Model", () => {
});
// The Models table renders team-scoped models with the team id in the row.
await page.getByRole("tab", { name: "All Models" }).click();
await page.getByRole("tab", { name: "Deployed Models" }).click();
await page.waitForLoadState("networkidle");
await page.getByPlaceholder("Search model names").fill("cohere");
@ -488,7 +488,7 @@ test.describe("Add Model", () => {
}
});
test("Add wildcard route and verify it appears in All Models", async ({ page }) => {
test("Add wildcard route and verify it appears in Deployed Models", async ({ page }) => {
await navigateToPage(page, Page.Models);
await page.getByRole("tab", { name: "Add Model" }).click();
@ -513,8 +513,8 @@ test.describe("Add Model", () => {
// Wait for success notification
await expect(page.getByText("created successfully")).toBeVisible({ timeout: 15_000 });
// Navigate to All Models tab
await page.getByRole("tab", { name: "All Models" }).click();
// Navigate to Deployed Models tab
await page.getByRole("tab", { name: "Deployed Models" }).click();
await page.waitForLoadState("networkidle");
// Search for the wildcard model

View file

@ -403,6 +403,17 @@ describe("AllModelsTab", () => {
});
});
it("uses All Proxy Models as the public model name filter default", async () => {
const user = userEvent.setup();
renderWithProviders(<AllModelsTab {...defaultProps} />);
await user.click(screen.getByTestId("datatable-filters-trigger"));
await user.click(await screen.findByPlaceholderText("Filter by Public Model Name"));
expect(await screen.findByRole("option", { name: "All Proxy Models" })).toBeInTheDocument();
expect(screen.queryByRole("option", { name: "All Models" })).not.toBeInTheDocument();
});
it("renders every row the server returned for the selected model group so rows match the footer total", () => {
setModelsInfo([makeRow(), { ...makeRow({ model_info: { id: "model-2" } }), model_name: "claude-opus" }], 2);
renderWithProviders(<AllModelsTab {...defaultProps} selectedModelGroup="claude-opus" />);
@ -567,7 +578,7 @@ describe("AllModelsTab", () => {
renderWithProviders(<AllModelsTab {...defaultProps} />);
await user.click(screen.getByTestId("models-view-select"));
await user.click(await screen.findByRole("option", { name: "All Available Models" }));
await user.click(await screen.findByRole("option", { name: "All Proxy Models" }));
await waitFor(() => {
expect(screen.queryByText(/create a Virtual Key/i)).not.toBeInTheDocument();

View file

@ -31,6 +31,7 @@ export const ALL_MODEL_GROUPS_VALUE = "all";
export const WILDCARD_MODEL_GROUP_VALUE = "wildcard";
const MODEL_TABLE_BODY_HEIGHT = 600;
const ALL_PROXY_MODELS_LABEL = "All Proxy Models";
const FILTER_LABELS: Record<string, string> = {
[MODEL_NAME_COLUMN_ID]: "Public Model Name",
@ -39,7 +40,7 @@ const FILTER_LABELS: Record<string, string> = {
const VIEW_MODE_LABELS: Record<ModelViewMode, string> = {
current_team: "Current Team Models",
all: "All Available Models",
all: ALL_PROXY_MODELS_LABEL,
};
export interface ModelsTableTeamOption {
@ -146,7 +147,7 @@ export function AllModelsTable({
const modelGroupOptions = useMemo(
() => [
{ label: "All Models", value: ALL_MODEL_GROUPS_VALUE },
{ label: ALL_PROXY_MODELS_LABEL, value: ALL_MODEL_GROUPS_VALUE },
{ label: "Wildcard Models (*)", value: WILDCARD_MODEL_GROUP_VALUE },
...availableModelGroups.map((group) => ({ label: group, value: group })),
],

View file

@ -38,7 +38,7 @@ export function AutoRoutersPanel({
const canCreate = createScope !== "forbidden";
const { data: deployments, isLoading } = useAutoRouters();
const invalidateAutoRouters = useInvalidateAutoRouters();
// Clicking a router opens the same ?model= drill-in the All Models table uses, so an auto
// Clicking a router opens the same ?model= drill-in the Deployed Models table uses, so an auto
// router gets the full ModelInfoView: Model Settings, Edit Settings, Edit Auto Router and
// Delete. A separate detail view here would be a worse copy of it.
const { openModel } = useModelDetailRouting();

View file

@ -81,9 +81,9 @@ describe("ModelsAndEndpointsPage", () => {
};
});
it("renders the admin tab bar and the All Models panel by default", () => {
it("renders the admin tab bar and the Deployed Models panel by default", () => {
renderPage();
expect(screen.getByRole("tab", { name: "All Models" })).toBeInTheDocument();
expect(screen.getByRole("tab", { name: "Deployed Models" })).toBeInTheDocument();
expect(screen.getByRole("tab", { name: "LLM Credentials" })).toBeInTheDocument();
expect(screen.getByRole("tab", { name: "Health Status" })).toBeInTheDocument();
expect(screen.getByTestId("panel-all-models")).toBeInTheDocument();
@ -101,7 +101,7 @@ describe("ModelsAndEndpointsPage", () => {
detailState.modelId = "abc-123";
renderPage();
expect(screen.getByTestId("model-info")).toHaveTextContent("model:abc-123");
expect(screen.queryByRole("tab", { name: "All Models" })).not.toBeInTheDocument();
expect(screen.queryByRole("tab", { name: "Deployed Models" })).not.toBeInTheDocument();
});
it("renders the team detail overlay from the ?team drill-in with admin edit rights", () => {
@ -138,7 +138,7 @@ describe("ModelsAndEndpointsPage", () => {
it("keeps the full admin tab order for a real admin", () => {
renderPage();
expect(screen.getAllByRole("tab").map((tab) => tab.textContent)).toEqual([
"All Models",
"Deployed Models",
"Add Model",
"Auto-Routers Beta",
"LLM Credentials",
@ -154,7 +154,7 @@ describe("ModelsAndEndpointsPage", () => {
it("hides the admin write-form tabs from a view-only admin, keeping the read views", () => {
mockUseAuthorized.mockReturnValue(VIEW_ONLY_ADMIN);
renderPage();
expect(screen.getByRole("tab", { name: "All Models" })).toBeInTheDocument();
expect(screen.getByRole("tab", { name: "Deployed Models" })).toBeInTheDocument();
expect(screen.getByRole("tab", { name: "Health Status" })).toBeInTheDocument();
expect(screen.queryByRole("tab", { name: "LLM Credentials" })).not.toBeInTheDocument();
expect(screen.queryByRole("tab", { name: "Pass-Through Endpoints" })).not.toBeInTheDocument();
@ -169,7 +169,7 @@ describe("ModelsAndEndpointsPage", () => {
mockUseAuthorized.mockReturnValue(VIEW_ONLY_ADMIN);
renderPage();
expect(screen.queryByRole("tab", { name: "Add Model" })).not.toBeInTheDocument();
expect(screen.getByRole("tab", { name: "All Models" })).toBeInTheDocument();
expect(screen.getByRole("tab", { name: "Deployed Models" })).toBeInTheDocument();
});
// Read parity: the Auto-Routers list stays reachable for a view-only admin; only the
@ -180,14 +180,14 @@ describe("ModelsAndEndpointsPage", () => {
expect(screen.getByRole("tab", { name: /Auto-Routers/ })).toBeInTheDocument();
});
// Auto-routers are excluded from the All Models table, so this tab is their home: the only
// Auto-routers are excluded from the Deployed Models table, so this tab is their home: the only
// place in the product to list, create, edit or delete one.
describe("Auto-Routers tab", () => {
it("sits third, after All Models and Add Model", () => {
it("sits third, after Deployed Models and Add Model", () => {
renderPage();
const tabs = screen.getAllByRole("tab").map((tab) => tab.textContent);
expect(tabs[0]).toContain("All Models");
expect(tabs[0]).toContain("Deployed Models");
expect(tabs[1]).toBe("Add Model");
expect(tabs[2]).toContain("Auto-Routers");
// Badged Beta while the tab settles; BetaBadge renders the label text.

View file

@ -123,7 +123,7 @@ export default function ModelsAndEndpointsPage() {
[canCreate, canViewAutoRouters, isAdmin, isViewOnly],
);
const allModelsLabel = isAdmin ? "All Models" : "Your Models";
const allModelsLabel = isAdmin ? "Deployed Models" : "Your Models";
const tabLabel = (slug: "" | ModelTabSlug): React.ReactNode => {
if (!slug) return allModelsLabel;
if (slug === "auto-routers" || slug === "access-group-budgets") {