Files
calendar/packages/app-store/closecom/api/callback.ts
T
Benny JooandGitHub d7960021aa perf: do not import from @calcom/lib/server barrel file (#19579)
* do not import from lib/server barrel file

* fix build
2025-02-26 18:10:52 -03:00

90 lines
3.0 KiB
TypeScript

import type { NextApiRequest, NextApiResponse } from "next";
import { WEBAPP_URL } from "@calcom/lib/constants";
import { getSafeRedirectUrl } from "@calcom/lib/getSafeRedirectUrl";
import { HttpError } from "@calcom/lib/http-error";
import { defaultHandler } from "@calcom/lib/server/defaultHandler";
import { defaultResponder } from "@calcom/lib/server/defaultResponder";
import prisma from "@calcom/prisma";
import getAppKeysFromSlug from "../../_utils/getAppKeysFromSlug";
import getInstalledAppPath from "../../_utils/getInstalledAppPath";
import { decodeOAuthState } from "../../_utils/oauth/decodeOAuthState";
import appConfig from "../config.json";
async function getHandler(req: NextApiRequest, res: NextApiResponse) {
const { code } = req.query;
const state = decodeOAuthState(req);
const redirectAfterSuccess =
getSafeRedirectUrl(state?.returnTo) ??
getInstalledAppPath({ variant: appConfig.variant, slug: appConfig.slug });
const redirectAfterSuccessOrError = getSafeRedirectUrl(state?.onErrorReturnTo) ?? redirectAfterSuccess;
if (!code || typeof code !== "string") {
if (state?.onErrorReturnTo || state?.returnTo) {
res.redirect(redirectAfterSuccessOrError);
return;
}
throw new HttpError({ statusCode: 400, message: "`code` must be a string" });
}
if (!req.session?.user?.id) {
throw new HttpError({ statusCode: 401, message: "You must be logged in to do this" });
}
const { client_id, client_secret } = await getAppKeysFromSlug("closecom");
if (!client_id || typeof client_id !== "string")
return res.status(400).json({ message: "Close.com client_id missing." });
if (!client_secret || typeof client_secret !== "string")
return res.status(400).json({ message: "Close.com client_secret missing." });
try {
const response = await fetch("https://api.close.com/oauth2/token/", {
method: "POST",
headers: {
"Content-Type": "application/x-www-form-urlencoded",
},
body: new URLSearchParams({
client_id,
client_secret,
grant_type: "authorization_code",
code: code as string,
redirect_uri: `${WEBAPP_URL}/api/integrations/closecom/callback`,
}),
});
if (!response.ok) {
throw new Error("Failed to get access token");
}
const responseJson = await response.json();
const { access_token, refresh_token, expires_in } = responseJson;
const expires_at = Date.now() + expires_in * 1000;
await prisma.credential.create({
data: {
type: "closecom_crm",
key: {
access_token,
refresh_token,
expires_at,
},
userId: req.session.user.id,
appId: "closecom",
},
});
return res.redirect(redirectAfterSuccess);
} catch (error) {
console.error("Error getting close.com access token", error);
return res.redirect(`${redirectAfterSuccessOrError}?error=Error getting close.com access token`);
}
}
export default defaultHandler({
GET: Promise.resolve({ default: defaultResponder(getHandler) }),
});