From cc401c40419c71fe1fff24323d6165716f03cf3c Mon Sep 17 00:00:00 2001 From: mateo-berri <277851410+mateo-berri@users.noreply.github.com> Date: Thu, 10 Sep 2026 13:16:01 -0700 Subject: [PATCH] fix(ui): skip organization fetches when the session is not premium --- .../organizations/useOrganizations.test.ts | 52 ++++++++++++++++--- .../hooks/organizations/useOrganizations.ts | 9 ++-- 2 files changed, 51 insertions(+), 10 deletions(-) diff --git a/ui/litellm-dashboard/src/app/(dashboard)/hooks/organizations/useOrganizations.test.ts b/ui/litellm-dashboard/src/app/(dashboard)/hooks/organizations/useOrganizations.test.ts index 960afe7392c..5448b7182d7 100644 --- a/ui/litellm-dashboard/src/app/(dashboard)/hooks/organizations/useOrganizations.test.ts +++ b/ui/litellm-dashboard/src/app/(dashboard)/hooks/organizations/useOrganizations.test.ts @@ -81,7 +81,7 @@ describe("useOrganizations", () => { userRole: "Admin", token: "test-token", userEmail: "test@example.com", - premiumUser: false, + premiumUser: true, disabledPersonalKeyCreation: null, showSSOBanner: false, }); @@ -181,7 +181,7 @@ describe("useOrganizations", () => { userRole: "Admin", token: null, userEmail: "test@example.com", - premiumUser: false, + premiumUser: true, disabledPersonalKeyCreation: null, showSSOBanner: false, }); @@ -197,6 +197,26 @@ describe("useOrganizations", () => { expect(organizationListCall).not.toHaveBeenCalled(); }); + it("does not call the organization API when the session is not premium", async () => { + mockUseAuthorized.mockReturnValue({ + accessToken: "test-access-token", + userId: "test-user-id", + userRole: "Admin", + token: "test-token", + userEmail: "test@example.com", + premiumUser: false, + disabledPersonalKeyCreation: null, + showSSOBanner: false, + }); + + const { result } = renderHook(() => useOrganizations(), { wrapper }); + + expect(result.current.isLoading).toBe(false); + expect(result.current.data).toBeUndefined(); + expect(result.current.isFetched).toBe(false); + expect(organizationListCall).not.toHaveBeenCalled(); + }); + it("should not execute query when userId is missing", async () => { // Mock missing userId mockUseAuthorized.mockReturnValue({ @@ -205,7 +225,7 @@ describe("useOrganizations", () => { userRole: "Admin", token: "test-token", userEmail: "test@example.com", - premiumUser: false, + premiumUser: true, disabledPersonalKeyCreation: null, showSSOBanner: false, }); @@ -229,7 +249,7 @@ describe("useOrganizations", () => { userRole: null, token: "test-token", userEmail: "test@example.com", - premiumUser: false, + premiumUser: true, disabledPersonalKeyCreation: null, showSSOBanner: false, }); @@ -253,7 +273,7 @@ describe("useOrganizations", () => { userRole: null, token: null, userEmail: "test@example.com", - premiumUser: false, + premiumUser: true, disabledPersonalKeyCreation: null, showSSOBanner: false, }); @@ -335,7 +355,7 @@ describe("useOrganization", () => { userRole: "Admin", token: "test-token", userEmail: "test@example.com", - premiumUser: false, + premiumUser: true, disabledPersonalKeyCreation: null, showSSOBanner: false, }); @@ -356,6 +376,26 @@ describe("useOrganization", () => { expect(result.current.isLoading).toBe(false); }); + it("does not call the organization info API when the session is not premium", () => { + mockUseAuthorized.mockReturnValue({ + accessToken: "test-access-token", + userId: "test-user-id", + userRole: "Admin", + token: "test-token", + userEmail: "test@example.com", + premiumUser: false, + disabledPersonalKeyCreation: null, + showSSOBanner: false, + }); + + const { result } = renderHook(() => useOrganization("org-1"), { wrapper }); + + expect(result.current.isLoading).toBe(false); + expect(result.current.data).toBeUndefined(); + expect(result.current.isFetched).toBe(false); + expect(organizationInfoCall).not.toHaveBeenCalled(); + }); + it("falls through to the detail API call when no cached list contains the organization", async () => { (organizationInfoCall as any).mockResolvedValue(mockOrganizations[0]); queryClient.setQueryData(organizationKeys.list({ filters: { org_id: "org-2" } }), [mockOrganizations[1]]); diff --git a/ui/litellm-dashboard/src/app/(dashboard)/hooks/organizations/useOrganizations.ts b/ui/litellm-dashboard/src/app/(dashboard)/hooks/organizations/useOrganizations.ts index 734c1986f8f..98053fdf038 100644 --- a/ui/litellm-dashboard/src/app/(dashboard)/hooks/organizations/useOrganizations.ts +++ b/ui/litellm-dashboard/src/app/(dashboard)/hooks/organizations/useOrganizations.ts @@ -11,9 +11,10 @@ export interface OrganizationListFilters { } export const useOrganizations = (filters?: OrganizationListFilters): UseQueryResult => { - const { accessToken, userId, userRole } = useAuthorized(); + const { accessToken, userId, userRole, premiumUser } = useAuthorized(); const orgId = filters?.org_id || null; const orgAlias = filters?.org_alias || null; + const hasSession = Boolean(accessToken && userId && userRole); return useQuery({ queryKey: organizationKeys.list( orgId || orgAlias @@ -21,16 +22,16 @@ export const useOrganizations = (filters?: OrganizationListFilters): UseQueryRes : {}, ), queryFn: async () => await organizationListCall(accessToken!, orgId, orgAlias), - enabled: Boolean(accessToken && userId && userRole), + enabled: hasSession && premiumUser === true, }); }; export const useOrganization = (organizationID?: string) => { const queryClient = useQueryClient(); - const { accessToken } = useAuthorized(); + const { accessToken, premiumUser } = useAuthorized(); return useQuery({ queryKey: organizationKeys.detail(organizationID!), - enabled: Boolean(accessToken && organizationID), + enabled: Boolean(accessToken && organizationID) && premiumUser === true, queryFn: async () => { if (!accessToken || !organizationID) {