fix: dub installation on teams (#21654)

Co-authored-by: cubic-dev-ai[bot] <191113872+cubic-dev-ai[bot]@users.noreply.github.com>
This commit is contained in:
Amit Sharmaandcubic-dev-ai[bot] authored and GitHub committed 2025-06-11 18:17:55 +02:00
1 parent 86d5c43307
commit 50c15f0d51
8 files changed
+40 -1

No files matched your search

@@ -6,6 +6,7 @@ import { appKeysSchema as alby_zod_ts } from "./alby/zod";
import { appKeysSchema as basecamp3_zod_ts } from "./basecamp3/zod";
import { appKeysSchema as closecom_zod_ts } from "./closecom/zod";
import { appKeysSchema as dailyvideo_zod_ts } from "./dailyvideo/zod";
import { appKeysSchema as dub_zod_ts } from "./dub/zod";
import { appKeysSchema as fathom_zod_ts } from "./fathom/zod";
import { appKeysSchema as feishucalendar_zod_ts } from "./feishucalendar/zod";
import { appKeysSchema as ga4_zod_ts } from "./ga4/zod";
@@ -55,6 +56,7 @@ export const appKeysSchemas = {
basecamp3: basecamp3_zod_ts,
closecom: closecom_zod_ts,
dailyvideo: dailyvideo_zod_ts,
dub: dub_zod_ts,
fathom: fathom_zod_ts,
feishucalendar: feishucalendar_zod_ts,
ga4: ga4_zod_ts,
@@ -6,6 +6,7 @@ import { appDataSchema as alby_zod_ts } from "./alby/zod";
import { appDataSchema as basecamp3_zod_ts } from "./basecamp3/zod";
import { appDataSchema as closecom_zod_ts } from "./closecom/zod";
import { appDataSchema as dailyvideo_zod_ts } from "./dailyvideo/zod";
import { appDataSchema as dub_zod_ts } from "./dub/zod";
import { appDataSchema as fathom_zod_ts } from "./fathom/zod";
import { appDataSchema as feishucalendar_zod_ts } from "./feishucalendar/zod";
import { appDataSchema as ga4_zod_ts } from "./ga4/zod";
@@ -55,6 +56,7 @@ export const appDataSchemas = {
basecamp3: basecamp3_zod_ts,
closecom: closecom_zod_ts,
dailyvideo: dailyvideo_zod_ts,
dub: dub_zod_ts,
fathom: fathom_zod_ts,
feishucalendar: feishucalendar_zod_ts,
ga4: ga4_zod_ts,
+4
View File
@@ -20,6 +20,7 @@ async function handler(req: NextApiRequest, res: NextApiResponse) {
throw new HttpError({ statusCode: 400, message: "Session user must have an email" });
}
const { teamId } = req.query;
const { client_id, redirect_uris } = await getParsedAppKeysFromSlug("dub", dubAppKeysSchema);
const url = new URL("https://app.dub.co/oauth/authorize");
@@ -27,6 +28,9 @@ async function handler(req: NextApiRequest, res: NextApiResponse) {
url.searchParams.append("redirect_uri", redirect_uris);
url.searchParams.append("response_type", "code");
url.searchParams.append("scope", scopeString);
if (typeof teamId === "string" && !Number.isNaN(Number(teamId))) {
url.searchParams.append("state", JSON.stringify({ teamId: Number(teamId) }));
}
const oauthUrl = url.toString();
return res.status(200).json({ url: oauthUrl });
@@ -73,6 +73,19 @@ export default class DubService implements AnalyticsService {
"Content-Type": "application/x-www-form-urlencoded",
},
});
if (!response.ok) {
const res = await response.json();
if (response.status === 401) {
await CredentialRepository.updateCredentialById({
id: this.credential.id,
data: {
invalid: true,
},
});
}
throw new Error(`Error refreshing dub token: ${res?.error?.message ?? response.statusText}`);
}
return await response.json();
},
"dub",
@@ -89,6 +102,7 @@ export default class DubService implements AnalyticsService {
return newToken;
} catch (err) {
this.log.error(err);
throw err;
}
}
+9
View File
@@ -0,0 +1,9 @@
import { z } from "zod";
export const appKeysSchema = z.object({
redirect_uris: z.string(),
client_id: z.string(),
client_secret: z.string(),
});
export const appDataSchema = z.object({});
@@ -2195,6 +2195,7 @@ async function handler(
email: bookerEmail,
eventName: "Cal.com lead",
},
isTeamEventType,
});
}
@@ -9,18 +9,24 @@ interface HandleAnalyticsEventsProps {
name: string;
eventName: string;
};
isTeamEventType: boolean;
}
export const handleAnalyticsEvents = async ({
credentials,
rawBookingData,
bookingInfo,
isTeamEventType,
}: HandleAnalyticsEventsProps) => {
const { dub_id } = await rawBookingData;
if (!dub_id || typeof dub_id !== "string") return;
const dubCredential = credentials.find((cred) => cred.appId === "dub");
const dubCredential = credentials.find((cred) => {
if (cred.appId !== "dub") return false;
if (isTeamEventType && !cred.teamId) return false;
return true;
});
if (!dubCredential) return;
@@ -23,6 +23,7 @@ type CredentialUpdateInput = {
userId?: number;
appId?: string;
delegationCredentialId?: string | null;
invalid?: boolean;
};
export class CredentialRepository {