From ba0adbfad3c0856819d143c45f257904a874fb4e Mon Sep 17 00:00:00 2001 From: Dhruwang Jariwala <67850763+Dhruwang@users.noreply.github.com> Date: Tue, 8 Oct 2024 19:20:58 +0530 Subject: [PATCH] chore: move billing page under ee route (#3251) Co-authored-by: Matthias Nannt --- LICENSE | 2 +- .../lib/checkoutSessionCompleted.ts | 0 .../billing/stripe-webhook}/lib/constants.ts | 0 .../lib/createCustomerPortalSession.ts | 0 .../stripe-webhook/lib/createSubscription.ts | 0 .../stripe-webhook/lib/invoiceFinalized.ts | 0 .../lib/isSubscriptionCancelled.ts | 0 .../stripe-webhook/lib/stripeWebhook.ts | 8 +-- .../lib/subscriptionCreatedOrUpdated.ts | 0 .../stripe-webhook/lib/subscriptionDeleted.ts | 0 .../api/billing/stripe-webhook/route.ts | 2 +- .../environments/[environmentId]/layout.tsx | 67 +++++++++++++++++++ .../(organization)/billing/actions.ts | 6 +- .../billing/components/PricingTable.tsx | 4 +- .../(organization)/billing/layout.tsx | 0 .../(organization)/billing/loading.tsx | 0 .../settings/(organization)/billing/page.tsx | 0 17 files changed, 78 insertions(+), 11 deletions(-) rename packages/ee/billing/handlers/checkout-session-completed.ts => apps/web/app/(ee)/api/billing/stripe-webhook/lib/checkoutSessionCompleted.ts (100%) rename {packages/ee/billing => apps/web/app/(ee)/api/billing/stripe-webhook}/lib/constants.ts (100%) rename packages/ee/billing/lib/create-customer-portal-session.ts => apps/web/app/(ee)/api/billing/stripe-webhook/lib/createCustomerPortalSession.ts (100%) rename packages/ee/billing/lib/create-subscription.ts => apps/web/app/(ee)/api/billing/stripe-webhook/lib/createSubscription.ts (100%) rename packages/ee/billing/handlers/invoice-finalized.ts => apps/web/app/(ee)/api/billing/stripe-webhook/lib/invoiceFinalized.ts (100%) rename packages/ee/billing/lib/is-subscription-cancelled.ts => apps/web/app/(ee)/api/billing/stripe-webhook/lib/isSubscriptionCancelled.ts (100%) rename packages/ee/billing/api/stripe-webhook.ts => apps/web/app/(ee)/api/billing/stripe-webhook/lib/stripeWebhook.ts (78%) rename packages/ee/billing/handlers/subscription-created-or-updated.ts => apps/web/app/(ee)/api/billing/stripe-webhook/lib/subscriptionCreatedOrUpdated.ts (100%) rename packages/ee/billing/handlers/subscription-deleted.ts => apps/web/app/(ee)/api/billing/stripe-webhook/lib/subscriptionDeleted.ts (100%) rename apps/web/app/{ => (ee)}/api/billing/stripe-webhook/route.ts (86%) create mode 100644 apps/web/app/(ee)/environments/[environmentId]/layout.tsx rename apps/web/app/{(app) => (ee)}/environments/[environmentId]/settings/(organization)/billing/actions.ts (89%) rename apps/web/app/{(app) => (ee)}/environments/[environmentId]/settings/(organization)/billing/components/PricingTable.tsx (97%) rename apps/web/app/{(app) => (ee)}/environments/[environmentId]/settings/(organization)/billing/layout.tsx (100%) rename apps/web/app/{(app) => (ee)}/environments/[environmentId]/settings/(organization)/billing/loading.tsx (100%) rename apps/web/app/{(app) => (ee)}/environments/[environmentId]/settings/(organization)/billing/page.tsx (100%) diff --git a/LICENSE b/LICENSE index 5c40bd8dcd..b0a7cb4564 100644 --- a/LICENSE +++ b/LICENSE @@ -2,7 +2,7 @@ Copyright (c) 2024 Formbricks GmbH Portions of this software are licensed as follows: -- All content that resides under the "packages/ee/" directory of this repository, if that directory exists, is licensed under the license defined in "packages/ee/LICENSE". +- All content that resides under the "packages/ee/" & "apps/web/app/(ee)" directories of this repository, if these directories exist, is licensed under the license defined in "packages/ee/LICENSE". - All content that resides under the "packages/js/", "packages/react-native/" and "packages/api/" directories of this repository, if that directories exist, is licensed under the "MIT" license as defined in the "LICENSE" files of these packages. - All third party components incorporated into the Formbricks Software are licensed under the original license provided by the owner of the applicable component. - Content outside of the above mentioned directories or restrictions above is available under the "AGPLv3" license as defined below. diff --git a/packages/ee/billing/handlers/checkout-session-completed.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/checkoutSessionCompleted.ts similarity index 100% rename from packages/ee/billing/handlers/checkout-session-completed.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/lib/checkoutSessionCompleted.ts diff --git a/packages/ee/billing/lib/constants.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/constants.ts similarity index 100% rename from packages/ee/billing/lib/constants.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/lib/constants.ts diff --git a/packages/ee/billing/lib/create-customer-portal-session.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/createCustomerPortalSession.ts similarity index 100% rename from packages/ee/billing/lib/create-customer-portal-session.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/lib/createCustomerPortalSession.ts diff --git a/packages/ee/billing/lib/create-subscription.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/createSubscription.ts similarity index 100% rename from packages/ee/billing/lib/create-subscription.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/lib/createSubscription.ts diff --git a/packages/ee/billing/handlers/invoice-finalized.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/invoiceFinalized.ts similarity index 100% rename from packages/ee/billing/handlers/invoice-finalized.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/lib/invoiceFinalized.ts diff --git a/packages/ee/billing/lib/is-subscription-cancelled.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/isSubscriptionCancelled.ts similarity index 100% rename from packages/ee/billing/lib/is-subscription-cancelled.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/lib/isSubscriptionCancelled.ts diff --git a/packages/ee/billing/api/stripe-webhook.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/stripeWebhook.ts similarity index 78% rename from packages/ee/billing/api/stripe-webhook.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/lib/stripeWebhook.ts index 91f96eb3a5..f511e9da61 100644 --- a/packages/ee/billing/api/stripe-webhook.ts +++ b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/stripeWebhook.ts @@ -1,10 +1,10 @@ import Stripe from "stripe"; import { STRIPE_API_VERSION } from "@formbricks/lib/constants"; import { env } from "@formbricks/lib/env"; -import { handleCheckoutSessionCompleted } from "../handlers/checkout-session-completed"; -import { handleInvoiceFinalized } from "../handlers/invoice-finalized"; -import { handleSubscriptionCreatedOrUpdated } from "../handlers/subscription-created-or-updated"; -import { handleSubscriptionDeleted } from "../handlers/subscription-deleted"; +import { handleCheckoutSessionCompleted } from "./checkoutSessionCompleted"; +import { handleInvoiceFinalized } from "./invoiceFinalized"; +import { handleSubscriptionCreatedOrUpdated } from "./subscriptionCreatedOrUpdated"; +import { handleSubscriptionDeleted } from "./subscriptionDeleted"; const stripe = new Stripe(env.STRIPE_SECRET_KEY!, { apiVersion: STRIPE_API_VERSION, diff --git a/packages/ee/billing/handlers/subscription-created-or-updated.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/subscriptionCreatedOrUpdated.ts similarity index 100% rename from packages/ee/billing/handlers/subscription-created-or-updated.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/lib/subscriptionCreatedOrUpdated.ts diff --git a/packages/ee/billing/handlers/subscription-deleted.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/lib/subscriptionDeleted.ts similarity index 100% rename from packages/ee/billing/handlers/subscription-deleted.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/lib/subscriptionDeleted.ts diff --git a/apps/web/app/api/billing/stripe-webhook/route.ts b/apps/web/app/(ee)/api/billing/stripe-webhook/route.ts similarity index 86% rename from apps/web/app/api/billing/stripe-webhook/route.ts rename to apps/web/app/(ee)/api/billing/stripe-webhook/route.ts index 016a5399b6..13849bdc5a 100644 --- a/apps/web/app/api/billing/stripe-webhook/route.ts +++ b/apps/web/app/(ee)/api/billing/stripe-webhook/route.ts @@ -1,6 +1,6 @@ import { responses } from "@/app/lib/api/response"; import { headers } from "next/headers"; -import { webhookHandler } from "@formbricks/ee/billing/api/stripe-webhook"; +import { webhookHandler } from "./lib/stripeWebhook"; export const POST = async (request: Request) => { const body = await request.text(); diff --git a/apps/web/app/(ee)/environments/[environmentId]/layout.tsx b/apps/web/app/(ee)/environments/[environmentId]/layout.tsx new file mode 100644 index 0000000000..8aebc3a42c --- /dev/null +++ b/apps/web/app/(ee)/environments/[environmentId]/layout.tsx @@ -0,0 +1,67 @@ +import { FormbricksClient } from "@/app/(app)/components/FormbricksClient"; +import { EnvironmentLayout } from "@/app/(app)/environments/[environmentId]/components/EnvironmentLayout"; +import EnvironmentStorageHandler from "@/app/(app)/environments/[environmentId]/components/EnvironmentStorageHandler"; +import { PosthogIdentify } from "@/app/(app)/environments/[environmentId]/components/PosthogIdentify"; +import { ResponseFilterProvider } from "@/app/(app)/environments/[environmentId]/components/ResponseFilterContext"; +import { getServerSession } from "next-auth"; +import { notFound, redirect } from "next/navigation"; +import { authOptions } from "@formbricks/lib/authOptions"; +import { hasUserEnvironmentAccess } from "@formbricks/lib/environment/auth"; +import { getMembershipByUserIdOrganizationId } from "@formbricks/lib/membership/service"; +import { getOrganizationByEnvironmentId } from "@formbricks/lib/organization/service"; +import { getProductByEnvironmentId } from "@formbricks/lib/product/service"; +import { getUser } from "@formbricks/lib/user/service"; +import { AuthorizationError } from "@formbricks/types/errors"; +import { ToasterClient } from "@formbricks/ui/components/ToasterClient"; + +const EnvLayout = async ({ children, params }) => { + const session = await getServerSession(authOptions); + if (!session || !session.user) { + return redirect(`/auth/login`); + } + + const user = await getUser(session.user.id); + if (!user) { + throw new Error("User not found"); + } + + const hasAccess = await hasUserEnvironmentAccess(session.user.id, params.environmentId); + if (!hasAccess) { + throw new AuthorizationError("Not authorized"); + } + + const organization = await getOrganizationByEnvironmentId(params.environmentId); + if (!organization) { + throw new Error("Organization not found"); + } + const product = await getProductByEnvironmentId(params.environmentId); + if (!product) { + throw new Error("Product not found"); + } + + const membership = await getMembershipByUserIdOrganizationId(session.user.id, organization.id); + if (!membership) return notFound(); + + return ( + <> + + + + + + + {children} + + + + ); +}; + +export default EnvLayout; diff --git a/apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/actions.ts b/apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/actions.ts similarity index 89% rename from apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/actions.ts rename to apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/actions.ts index 14bdc9d988..277646de9e 100644 --- a/apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/actions.ts +++ b/apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/actions.ts @@ -1,9 +1,9 @@ "use server"; +import { createCustomerPortalSession } from "@/app/(ee)/api/billing/stripe-webhook/lib/createCustomerPortalSession"; +import { createSubscription } from "@/app/(ee)/api/billing/stripe-webhook/lib/createSubscription"; +import { isSubscriptionCancelled } from "@/app/(ee)/api/billing/stripe-webhook/lib/isSubscriptionCancelled"; import { z } from "zod"; -import { createCustomerPortalSession } from "@formbricks/ee/billing/lib/create-customer-portal-session"; -import { createSubscription } from "@formbricks/ee/billing/lib/create-subscription"; -import { isSubscriptionCancelled } from "@formbricks/ee/billing/lib/is-subscription-cancelled"; import { authenticatedActionClient } from "@formbricks/lib/actionClient"; import { checkAuthorization } from "@formbricks/lib/actionClient/utils"; import { STRIPE_PRICE_LOOKUP_KEYS } from "@formbricks/lib/constants"; diff --git a/apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/components/PricingTable.tsx b/apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/components/PricingTable.tsx similarity index 97% rename from apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/components/PricingTable.tsx rename to apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/components/PricingTable.tsx index 9eafb8a7ff..478bab3ffc 100644 --- a/apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/components/PricingTable.tsx +++ b/apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/components/PricingTable.tsx @@ -1,14 +1,14 @@ "use client"; +import { CLOUD_PRICING_DATA } from "@/app/(ee)/api/billing/stripe-webhook/lib/constants"; import { isSubscriptionCancelledAction, manageSubscriptionAction, upgradePlanAction, -} from "@/app/(app)/environments/[environmentId]/settings/(organization)/billing/actions"; +} from "@/app/(ee)/environments/[environmentId]/settings/(organization)/billing/actions"; import { useRouter } from "next/navigation"; import { useEffect, useState } from "react"; import toast from "react-hot-toast"; -import { CLOUD_PRICING_DATA } from "@formbricks/ee/billing/lib/constants"; import { cn } from "@formbricks/lib/cn"; import { capitalizeFirstLetter } from "@formbricks/lib/utils/strings"; import { TOrganization, TOrganizationBillingPeriod } from "@formbricks/types/organizations"; diff --git a/apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/layout.tsx b/apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/layout.tsx similarity index 100% rename from apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/layout.tsx rename to apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/layout.tsx diff --git a/apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/loading.tsx b/apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/loading.tsx similarity index 100% rename from apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/loading.tsx rename to apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/loading.tsx diff --git a/apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/page.tsx b/apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/page.tsx similarity index 100% rename from apps/web/app/(app)/environments/[environmentId]/settings/(organization)/billing/page.tsx rename to apps/web/app/(ee)/environments/[environmentId]/settings/(organization)/billing/page.tsx