import { describe, it, expect } from "vitest"; import type { App } from "@calcom/types/App"; import type { CredentialForCalendarService } from "@calcom/types/Credential"; import { sanitizeAppForViewer } from "./utils"; import type { CredentialDataWithTeamName, LocationOption } from "./utils"; describe("sanitizeAppForViewer", () => { it("should remove key, credential, and credentials properties", () => { const mockCredential: CredentialDataWithTeamName = { id: 1, type: "daily_video", key: { api_key: "secret-api-key" }, userId: 1, user: { email: "test@example.com" }, teamId: null, appId: "daily-video", invalid: false, delegatedTo: null, delegatedToId: null, delegationCredentialId: null, team: null, encryptedKey: null, }; const mockApp: App & { credential: CredentialDataWithTeamName | null; credentials: CredentialDataWithTeamName[]; locationOption: LocationOption | null; } = { type: "daily_video", name: "Daily Video", description: "Video conferencing", variant: "conferencing", slug: "daily-video", categories: ["conferencing"], logo: "/logo.png", publisher: "Daily", url: "https://daily.co", email: "support@daily.co", key: { api_key: "secret-global-api-key" }, credential: mockCredential, credentials: [mockCredential], locationOption: { value: "integrations:daily_video", label: "Daily Video", }, }; const sanitized = sanitizeAppForViewer(mockApp); // Should not have key, credential, or credentials expect(sanitized).not.toHaveProperty("key"); expect(sanitized).not.toHaveProperty("credential"); expect(sanitized).not.toHaveProperty("credentials"); // Should have all other properties expect(sanitized).toHaveProperty("type", "daily_video"); expect(sanitized).toHaveProperty("name", "Daily Video"); expect(sanitized).toHaveProperty("slug", "daily-video"); expect(sanitized).toHaveProperty("locationOption"); expect(sanitized.locationOption).toEqual({ value: "integrations:daily_video", label: "Daily Video", }); }); it("should handle apps without credential or credentials", () => { const mockApp: App & { credential?: CredentialDataWithTeamName | null; credentials?: CredentialDataWithTeamName[]; locationOption?: LocationOption | null; } = { type: "zoom_video", name: "Zoom", description: "Video conferencing", variant: "conferencing", slug: "zoom", categories: ["conferencing"], logo: "/logo.png", publisher: "Zoom", url: "https://zoom.us", email: "support@zoom.us", key: { api_key: "secret-key" }, }; const sanitized = sanitizeAppForViewer(mockApp); expect(sanitized).not.toHaveProperty("key"); expect(sanitized).not.toHaveProperty("credential"); expect(sanitized).not.toHaveProperty("credentials"); expect(sanitized).toHaveProperty("slug", "zoom"); }); it("should preserve all non-sensitive properties", () => { const mockApp: App & { credential: CredentialDataWithTeamName | null; credentials: CredentialDataWithTeamName[]; locationOption: LocationOption | null; } = { type: "stripe_payment", name: "Stripe", description: "Payment processing", variant: "payment", slug: "stripe", categories: ["payment"], logo: "/logo.png", publisher: "Stripe", url: "https://stripe.com", email: "support@stripe.com", verified: true, trending: true, rating: 4.5, reviews: 1000, isGlobal: false, key: { api_key: "sk_live_secret" }, credential: null, credentials: [], locationOption: null, appData: { location: { type: "integrations:stripe", label: "Stripe", linkType: "dynamic", }, }, }; const sanitized = sanitizeAppForViewer(mockApp); expect(sanitized).not.toHaveProperty("key"); expect(sanitized).not.toHaveProperty("credential"); expect(sanitized).not.toHaveProperty("credentials"); expect(sanitized.verified).toBe(true); expect(sanitized.trending).toBe(true); expect(sanitized.rating).toBe(4.5); expect(sanitized.reviews).toBe(1000); expect(sanitized.appData).toBeDefined(); }); });