perf: optimize payment app imports to avoid loading entire app store (#23408)

* perf: optimize payment app imports to avoid loading entire app store

- Add PaymentServiceMap generation to app-store-cli build process
- Generate payment.services.generated.ts with lazy imports for 6 payment services
- Update handlePayment.ts, deletePayment.ts, handlePaymentRefund.ts to use PaymentServiceMap
- Update getConnectedApps.ts and tRPC payment routers to use PaymentServiceMap
- Follow same pattern as analytics optimization in PR #23372
- Reduces bundle size by avoiding import of 100+ apps when only payment functionality needed

Co-Authored-By: keith@cal.com <keithwillcode@gmail.com>

* Update build.ts

* fix: update payment service test mocking to work with PaymentServiceMap

- Remove obsolete appStoreMock line from bookingScenario.ts since handlePayment now uses PaymentServiceMap
- Update setupVitest.ts to import prismaMock from correct PrismockClient instance
- Add PaymentServiceMap mock following PR #22450 pattern for calendar services
- Ensure MockPaymentService uses consistent externalId across test files
- Fix webhook handler to return 200 status by ensuring payment records are found correctly

Co-Authored-By: keith@cal.com <keithwillcode@gmail.com>

* fix: revert prismaMock import to avoid interfering with other tests' vi.spyOn() calls

- Remove global prismaMock import from setupVitest.ts that was causing 'is not a spy' errors
- Update MockPaymentService to import prismaMock locally to maintain payment test functionality
- Fixes organization and outOfOffice tests while preserving payment service optimization

Co-Authored-By: keith@cal.com <keithwillcode@gmail.com>

* fix: remove E2E conditional check from payment services map generation

- Payment services map now always includes all payment apps regardless of E2E environment
- Ensures payment functionality is consistently available across all environments
- Addresses CI failures caused by conditional payment service loading

Co-Authored-By: keith@cal.com <keithwillcode@gmail.com>

* refactor: use direct PaymentService imports instead of .lib structure

- Update app-store-cli to import directly from lib/PaymentService.ts files
- Modify all payment handlers to access PaymentService directly
- Update test mocks to match new direct import structure
- Remove .lib property access pattern across payment system
- Maintain backward compatibility while improving import efficiency

Co-Authored-By: keith@cal.com <keithwillcode@gmail.com>

* fix: revert chargeCard booking.id parameter additions

- Remove booking.id parameter from chargeCard calls in chargeCard.handler.ts and payments.tsx
- Addresses GitHub feedback to investigate chargeCard signature changes in separate PR
- Keeps all other direct PaymentService import refactor changes intact

Co-Authored-By: keith@cal.com <keithwillcode@gmail.com>

---------

Co-authored-by: Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com>
This commit is contained in:
Keith Williams
2025-08-28 10:05:36 -03:00
committed by GitHub
co-authored by keith@cal.com <keithwillcode@gmail.com> Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com>
parent 381125becd
commit baaa04151d
12 changed files with 218 additions and 74 deletions
@@ -1,7 +1,6 @@
import prismaMock from "../../../../../tests/libs/__mocks__/prisma";
import type { Payment, Prisma, PaymentOption, Booking } from "@prisma/client";
import { v4 as uuidv4 } from "uuid";
import "vitest-fetch-mock";
import { sendAwaitingPaymentEmailAndSMS } from "@calcom/emails";
@@ -13,8 +12,8 @@ export function getMockPaymentService() {
function createPaymentLink(/*{ paymentUid, name, email, date }*/) {
return "http://mock-payment.example.com/";
}
const paymentUid = uuidv4();
const externalId = uuidv4();
const paymentUid = "MOCK_PAYMENT_UID";
const externalId = "mock_payment_external_id";
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
@@ -37,7 +36,7 @@ export function getMockPaymentService() {
bookingId,
// booking Booking? @relation(fields: [bookingId], references: [id], onDelete: Cascade)
fee: 10,
success: true,
success: false,
refunded: false,
data: {},
externalId,
@@ -46,11 +45,16 @@ export function getMockPaymentService() {
currency: payment.currency,
};
const paymentData = prismaMock.payment.create({
const paymentData = await prismaMock.payment.create({
data: paymentCreateData,
});
logger.silly("Created mock payment", JSON.stringify({ paymentData }));
const verifyPayment = await prismaMock.payment.findFirst({
where: { externalId: paymentCreateData.externalId },
});
logger.silly("Verified payment exists", JSON.stringify({ verifyPayment }));
return paymentData;
}
async afterPayment(
@@ -2105,18 +2105,7 @@ export function mockPaymentApp({
appStoreLookupKey?: string;
}) {
appStoreLookupKey = appStoreLookupKey || metadataLookupKey;
const { paymentUid, externalId, MockPaymentService } = getMockPaymentService();
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
//@ts-ignore
appStoreMock.default[appStoreLookupKey as keyof typeof appStoreMock.default].mockImplementation(() => {
return new Promise((resolve) => {
resolve({
lib: {
PaymentService: MockPaymentService,
},
});
});
});
const { paymentUid, externalId } = getMockPaymentService();
return {
paymentUid,