store twilio stuff in TwilioAccount table and remodel session data

This commit is contained in:
m5r
2022-05-21 21:33:23 +02:00
parent 19a35bac92
commit 6684dcc0e5
23 changed files with 411 additions and 365 deletions

View File

@ -1,41 +1,20 @@
import { type LoaderFunction, json } from "@remix-run/node";
import { Outlet, useCatch, useMatches } from "@remix-run/react";
import { type SessionData, type SessionOrganization, requireLoggedIn } from "~/utils/auth.server";
import { type SessionData, requireLoggedIn } from "~/utils/auth.server";
import Footer from "~/features/core/components/footer";
import db from "~/utils/db.server";
export type AppLoaderData = SessionData;
export const loader: LoaderFunction = async ({ request }) => {
const user = await requireLoggedIn(request);
const organization = await db.organization.findUnique({
where: { id: user.organizations[0].id },
include: {
memberships: {
where: { userId: user.id },
select: { role: true },
},
phoneNumbers: {
where: { isCurrent: true },
select: { id: true, number: true },
},
},
});
const currentOrganization: SessionOrganization = {
id: organization!.id,
twilioAccountSid: organization!.twilioAccountSid,
twilioSubAccountSid: organization!.twilioSubAccountSid,
role: organization!.memberships[0].role,
};
const currentPhoneNumber = organization!.phoneNumbers[0];
const sessionData = await requireLoggedIn(request);
return json<AppLoaderData>({ ...user, currentOrganization, currentPhoneNumber });
return json<AppLoaderData>(sessionData);
};
export default function __App() {
const matches = useMatches();
const hideFooter = matches.some(match => match.handle?.hideFooter === true);
const hideFooter = matches.some((match) => match.handle?.hideFooter === true);
return (
<div className="h-full w-full overflow-hidden fixed bg-gray-100">

View File

@ -26,10 +26,13 @@ export type PhoneCallsLoaderData = {
};
export const loader: LoaderFunction = async ({ request }) => {
const { organizations } = await requireLoggedIn(request);
const organizationId = organizations[0].id;
const sessionData = await requireLoggedIn(request);
if (!sessionData.phoneNumber) {
throw new Error("unreachable");
}
const phoneNumber = await db.phoneNumber.findUnique({
where: { organizationId_isCurrent: { organizationId, isCurrent: true } },
where: { id: sessionData.phoneNumber.id },
});
if (!phoneNumber || phoneNumber.isFetchingCalls) {
return json<PhoneCallsLoaderData>({

View File

@ -13,7 +13,7 @@ import useKeyPress from "~/features/keypad/hooks/use-key-press";
import KeypadErrorModal from "~/features/keypad/components/keypad-error-modal";
import InactiveSubscription from "~/features/core/components/inactive-subscription";
export default function SettingsLayout() {
export default function KeypadPage() {
const { hasFilledTwilioCredentials, hasPhoneNumber, hasOngoingSubscription } = {
hasFilledTwilioCredentials: false,
hasPhoneNumber: false,

View File

@ -1,4 +1,3 @@
import { Suspense } from "react";
import type { LoaderFunction, MetaFunction } from "@remix-run/node";
import { Link, useNavigate, useParams } from "@remix-run/react";
import { json, useLoaderData } from "superjson-remix";
@ -35,14 +34,14 @@ export type ConversationLoaderData = {
};
export const loader: LoaderFunction = async ({ request, params }) => {
const { organizations } = await requireLoggedIn(request);
const { organization } = await requireLoggedIn(request);
const recipient = decodeURIComponent(params.recipient ?? "");
const conversation = await getConversation(recipient);
return json<ConversationLoaderData>({ conversation });
async function getConversation(recipient: string): Promise<ConversationType> {
const organizationId = organizations[0].id;
const organizationId = organization.id;
const phoneNumber = await db.phoneNumber.findUnique({
where: { organizationId_isCurrent: { organizationId, isCurrent: true } },
});

View File

@ -13,9 +13,8 @@ export type PhoneSettingsLoaderData = {
};
export const loader: LoaderFunction = async ({ request }) => {
const { organizations } = await requireLoggedIn(request);
const organization = organizations[0];
if (!organization.twilioAccountSid) {
const { organization, twilioAccount } = await requireLoggedIn(request);
if (!twilioAccount) {
logger.warn("Twilio account is not connected");
return json<PhoneSettingsLoaderData>({ phoneNumbers: [] });
}

View File

@ -8,10 +8,10 @@ import serverConfig from "~/config/config.server";
import getTwilioClient from "~/utils/twilio.server";
import fetchPhoneCallsQueue from "~/queues/fetch-phone-calls.server";
import fetchMessagesQueue from "~/queues/fetch-messages.server";
import { encrypt } from "~/utils/encryption";
export const loader: LoaderFunction = async ({ request }) => {
const user = await requireLoggedIn(request);
const organization = user.organizations[0];
const { organization } = await requireLoggedIn(request);
const url = new URL(request.url);
const twilioSubAccountSid = url.searchParams.get("AccountSid");
if (!twilioSubAccountSid) {
@ -20,13 +20,21 @@ export const loader: LoaderFunction = async ({ request }) => {
let twilioClient = twilio(twilioSubAccountSid, serverConfig.twilio.authToken);
const twilioSubAccount = await twilioClient.api.accounts(twilioSubAccountSid).fetch();
const twilioAccountSid = twilioSubAccount.ownerAccountSid;
await db.organization.update({
where: { id: organization.id },
data: { twilioSubAccountSid, twilioAccountSid },
const twilioMainAccountSid = twilioSubAccount.ownerAccountSid;
const twilioMainAccount = await twilioClient.api.accounts(twilioMainAccountSid).fetch();
console.log("twilioSubAccount", twilioSubAccount);
console.log("twilioAccount", twilioMainAccount);
const twilioAccount = await db.twilioAccount.update({
where: { organizationId: organization.id },
data: {
subAccountSid: twilioSubAccount.sid,
subAccountAuthToken: encrypt(twilioSubAccount.authToken),
accountSid: twilioMainAccount.sid,
accountAuthToken: encrypt(twilioMainAccount.authToken),
},
});
twilioClient = getTwilioClient({ twilioAccountSid, twilioSubAccountSid });
twilioClient = getTwilioClient(twilioAccount);
const phoneNumbers = await twilioClient.incomingPhoneNumbers.list();
await Promise.all(
phoneNumbers.map(async (phoneNumber) => {