Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions apps/web/app/api/teams/[team]/upgrade/route.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import stripe from "@calcom/features/ee/payments/server/stripe";
import { WEBAPP_URL } from "@calcom/lib/constants";
import { HttpError } from "@calcom/lib/http-error";
import prisma from "@calcom/prisma";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";

import { buildLegacyRequest } from "@lib/buildLegacyCtx";

Expand Down Expand Up @@ -50,7 +50,7 @@ async function getHandler(req: NextRequest, { params }: { params: Promise<Params
if (!team) {
const prevTeam = await prisma.team.findFirstOrThrow({ where: { id } });

metadata = teamMetadataSchema.safeParse(prevTeam.metadata);
metadata = teamMetadataStrictSchema.safeParse(prevTeam.metadata);
if (!metadata.success) {
throw new HttpError({ statusCode: 400, message: "Invalid team metadata" });
}
Expand Down Expand Up @@ -80,7 +80,7 @@ async function getHandler(req: NextRequest, { params }: { params: Promise<Params
}

if (!metadata) {
metadata = teamMetadataSchema.safeParse(team.metadata);
metadata = teamMetadataStrictSchema.safeParse(team.metadata);
if (!metadata.success) {
throw new HttpError({ statusCode: 400, message: "Invalid team metadata" });
}
Expand Down
4 changes: 2 additions & 2 deletions apps/web/playwright/lib/orgMigration.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import type { Team, User } from "@calcom/prisma/client";
import { RedirectType } from "@calcom/prisma/client";
import { Prisma } from "@calcom/prisma/client";
import type { MembershipRole } from "@calcom/prisma/enums";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataSchema, teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";

const log = logger.getSubLogger({ prefix: ["orgMigration"] });

Expand Down Expand Up @@ -588,7 +588,7 @@ async function dbRemoveTeamFromOrg({ teamId }: { teamId: number }) {
});
}

const teamMetadata = teamMetadataSchema.parse(team?.metadata);
const teamMetadata = teamMetadataStrictSchema.parse(team?.metadata);
try {
return await prisma.team.update({
where: {
Expand Down
4 changes: 2 additions & 2 deletions packages/features/ee/billing/teams/internal-team-billing.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,14 +10,14 @@ import { Redirect } from "@calcom/lib/redirect";
import { safeStringify } from "@calcom/lib/safeStringify";
import { OrganizationOnboardingRepository } from "@calcom/lib/server/repository/organizationOnboarding";
import prisma from "@calcom/prisma";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";

import billing from "..";
import { TeamBillingPublishResponseStatus, type TeamBilling, type TeamBillingInput } from "./team-billing";

const log = logger.getSubLogger({ prefix: ["TeamBilling"] });

const teamPaymentMetadataSchema = teamMetadataSchema.unwrap();
const teamPaymentMetadataSchema = teamMetadataStrictSchema.unwrap();

export class InternalTeamBilling implements TeamBilling {
private _team!: Omit<TeamBillingInput, "metadata"> & {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ import {
orgOnboardingInvitedMembersSchema,
orgOnboardingTeamsSchema,
} from "@calcom/prisma/zod-utils";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";
import { createTeamsHandler } from "@calcom/trpc/server/routers/viewer/organizations/createTeams.handler";
import { inviteMembersWithNoInviterPermissionCheck } from "@calcom/trpc/server/routers/viewer/teams/inviteMember/inviteMember.handler";

Expand Down Expand Up @@ -344,7 +344,7 @@ async function backwardCompatibilityForSubscriptionDetails({
return organization;
}

const existingMetadata = teamMetadataSchema.parse(organization.metadata);
const existingMetadata = teamMetadataStrictSchema.parse(organization.metadata);
const updatedOrganization = await OrganizationRepository.updateStripeSubscriptionDetails({
id: organization.id,
stripeSubscriptionId: paymentSubscriptionId,
Expand Down
3 changes: 2 additions & 1 deletion packages/lib/server/repository/organization.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import { safeStringify } from "@calcom/lib/safeStringify";
import { prisma } from "@calcom/prisma";
import { MembershipRole } from "@calcom/prisma/enums";
import type { CreationSource } from "@calcom/prisma/enums";
import type { teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";

import { createAProfileForAnExistingUser } from "../../createAProfileForAnExistingUser";
Expand Down Expand Up @@ -448,7 +449,7 @@ export class OrganizationRepository {
id: number;
stripeSubscriptionId: string;
stripeSubscriptionItemId: string;
existingMetadata: z.infer<typeof teamMetadataSchema>;
existingMetadata: z.infer<typeof teamMetadataStrictSchema>;
}) {
return await prisma.team.update({
where: { id, isOrganization: true },
Expand Down
51 changes: 34 additions & 17 deletions packages/prisma/zod-utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -372,24 +372,41 @@ export enum BillingPeriod {
ANNUALLY = "ANNUALLY",
}

export const teamMetadataSchema = z
.object({
defaultConferencingApp: schemaDefaultConferencingApp.optional(),
requestedSlug: z.string().or(z.null()),
paymentId: z.string(),
subscriptionId: z.string().nullable(),
subscriptionItemId: z.string().nullable(),
orgSeats: z.number().nullable(),
orgPricePerSeat: z.number().nullable(),
migratedToOrgFrom: z
.object({
teamSlug: z.string().or(z.null()).optional(),
lastMigrationTime: z.string().optional(),
reverted: z.boolean().optional(),
lastRevertTime: z.string().optional(),
const baseTeamMetadataSchema = z.object({
defaultConferencingApp: schemaDefaultConferencingApp.optional(),
requestedSlug: z.string().or(z.null()),
paymentId: z.string(),
subscriptionId: z.string().nullable(),
subscriptionItemId: z.string().nullable(),
orgSeats: z.number().nullable(),
orgPricePerSeat: z.number().nullable(),
migratedToOrgFrom: z
.object({
teamSlug: z.string().or(z.null()).optional(),
lastMigrationTime: z.string().optional(),
reverted: z.boolean().optional(),
lastRevertTime: z.string().optional(),
})
.optional(),
billingPeriod: z.nativeEnum(BillingPeriod).optional(),
});

export const teamMetadataSchema = baseTeamMetadataSchema.partial().nullable();

export const teamMetadataStrictSchema = baseTeamMetadataSchema
.extend({
subscriptionId: z
.string()
.refine((val) => val.startsWith("sub_"), {
message: "subscriptionId must start with 'sub_'",
})
.optional(),
billingPeriod: z.nativeEnum(BillingPeriod).optional(),
.nullable(),
subscriptionItemId: z
.string()
.refine((val) => val.startsWith("si_"), {
message: "subscriptionItemId must start with 'si_'",
})
.nullable(),
})
.partial()
.nullable();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { renameDomain } from "@calcom/lib/domainManager/organization";
import { getMetadataHelpers } from "@calcom/lib/getMetadataHelpers";
import { HttpError } from "@calcom/lib/http-error";
import { prisma } from "@calcom/prisma";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";

import type { TrpcSessionUser } from "../../../types";
import type { TAdminUpdate } from "./adminUpdate.schema";
Expand Down Expand Up @@ -34,7 +34,7 @@ export const adminUpdateHandler = async ({ input }: AdminUpdateOptions) => {
});
}

const { mergeMetadata } = getMetadataHelpers(teamMetadataSchema.unwrap(), existingOrg.metadata || {});
const { mergeMetadata } = getMetadataHelpers(teamMetadataStrictSchema.unwrap(), existingOrg.metadata || {});

const data: Prisma.TeamUpdateArgs["data"] = restInput;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import slugify from "@calcom/lib/slugify";
import { prisma } from "@calcom/prisma";
import type { CreationSource } from "@calcom/prisma/enums";
import { MembershipRole, RedirectType } from "@calcom/prisma/enums";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataSchema, teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";

import { TRPCError } from "@trpc/server";

Expand Down Expand Up @@ -295,7 +295,7 @@ async function tryToCancelSubscription(subscriptionId: string) {
}

function getSubscriptionId(metadata: Prisma.JsonValue) {
const parsedMetadata = teamMetadataSchema.safeParse(metadata);
const parsedMetadata = teamMetadataStrictSchema.safeParse(metadata);
if (parsedMetadata.success) {
const subscriptionId = parsedMetadata.data?.subscriptionId;
if (!subscriptionId) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { purchaseTeamOrOrgSubscription } from "@calcom/features/ee/teams/lib/pay
import { IS_TEAM_BILLING_ENABLED, WEBAPP_URL } from "@calcom/lib/constants";
import { isOrganisationAdmin } from "@calcom/lib/server/queries/organisations";
import { prisma } from "@calcom/prisma";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";

import { TRPCError } from "@trpc/server";

Expand Down Expand Up @@ -31,7 +31,7 @@ export const publishHandler = async ({ ctx }: PublishOptions) => {

if (!prevTeam) throw new TRPCError({ code: "NOT_FOUND", message: "Organization not found." });

const metadata = teamMetadataSchema.safeParse(prevTeam.metadata);
const metadata = teamMetadataStrictSchema.safeParse(prevTeam.metadata);
if (!metadata.success) throw new TRPCError({ code: "BAD_REQUEST", message: "Invalid team metadata" });

// Since this is an ORG we need to make sure ORG members are scyned with the team. Every time a user is added to the TEAM, we need to add them to the ORG
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import { resizeBase64Image } from "@calcom/lib/server/resizeBase64Image";
import type { PrismaClient } from "@calcom/prisma";
import { prisma } from "@calcom/prisma";
import { MembershipRole } from "@calcom/prisma/enums";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";

import { TRPCError } from "@trpc/server";

Expand Down Expand Up @@ -165,7 +165,10 @@ export const updateHandler = async ({ ctx, input }: UpdateOptions) => {

if (!prevOrganisation) throw new TRPCError({ code: "NOT_FOUND", message: "Organisation not found." });

const { mergeMetadata } = getMetadataHelpers(teamMetadataSchema.unwrap(), prevOrganisation.metadata ?? {});
const { mergeMetadata } = getMetadataHelpers(
teamMetadataStrictSchema.unwrap(),
prevOrganisation.metadata ?? {}
);

const data: Prisma.TeamUpdateArgs["data"] = {
logoUrl: input.logoUrl,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { z } from "zod";

import { timeZoneSchema } from "@calcom/lib/dayjs/timeZone.schema";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";

export const ZUpdateInputSchema = z.object({
name: z.string().optional(),
Expand All @@ -28,7 +28,7 @@ export const ZUpdateInputSchema = z.object({
timeZone: timeZoneSchema.optional(),
weekStart: z.string().optional(),
timeFormat: z.number().optional(),
metadata: teamMetadataSchema.unwrap().optional(),
metadata: teamMetadataStrictSchema.unwrap().optional(),
lockEventTypeCreation: z.boolean().optional(),
lockEventTypeCreationOptions: z.enum(["DELETE", "HIDE"]).optional(),
adminGetsNoSlotsNotification: z.boolean().optional(),
Expand Down
4 changes: 2 additions & 2 deletions packages/trpc/server/routers/viewer/teams/update.handler.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import { uploadLogo } from "@calcom/lib/server/avatar";
import { isTeamAdmin } from "@calcom/lib/server/queries/teams";
import { prisma } from "@calcom/prisma";
import { RedirectType, RRTimestampBasis } from "@calcom/prisma/enums";
import { teamMetadataSchema } from "@calcom/prisma/zod-utils";
import { teamMetadataStrictSchema } from "@calcom/prisma/zod-utils";

import { TRPCError } from "@trpc/server";

Expand Down Expand Up @@ -95,7 +95,7 @@ export const updateHandler = async ({ ctx, input }: UpdateOptions) => {
data.slug = input.slug;

// If we save slug, we don't need the requestedSlug anymore
const metadataParse = teamMetadataSchema.safeParse(prevTeam.metadata);
const metadataParse = teamMetadataStrictSchema.safeParse(prevTeam.metadata);
if (metadataParse.success) {
const { requestedSlug: _, ...cleanMetadata } = metadataParse.data || {};
data.metadata = {
Expand Down
Loading