From e6d37e04f9bda5e3863286dd79e826181dc325c0 Mon Sep 17 00:00:00 2001 From: paritosh18 Date: Wed, 24 Dec 2025 19:04:51 +0530 Subject: [PATCH] updated create activtiy hanlder --- prisma/schema.prisma | 2 +- src/modules/host/dto/createActivity.schema.ts | 4 +- src/modules/host/services/host.service.ts | 117 +++++++++++++++--- 3 files changed, 103 insertions(+), 20 deletions(-) diff --git a/prisma/schema.prisma b/prisma/schema.prisma index 0deabab..ce4fe1a 100644 --- a/prisma/schema.prisma +++ b/prisma/schema.prisma @@ -860,7 +860,7 @@ model Activities { frequenciesXid Int? @map("frequencies_xid") frequency Frequencies? @relation(fields: [frequenciesXid], references: [id], onDelete: Restrict) activityRefNumber String? @map("activity_ref_number") @db.VarChar(30) - activityTitle String? @map("activity_title") @db.VarChar(30) + activityTitle String? @map("activity_title") @db.VarChar(150) activityDescription String? @map("activity_description") @db.VarChar(255) checkInLat Float? @map("check_in_lat") checkInLong Float? @map("check_in_long") diff --git a/src/modules/host/dto/createActivity.schema.ts b/src/modules/host/dto/createActivity.schema.ts index 7a8b416..27d1db8 100644 --- a/src/modules/host/dto/createActivity.schema.ts +++ b/src/modules/host/dto/createActivity.schema.ts @@ -114,7 +114,7 @@ export const CreateActivityDto = z.object({ /* DURATION / ENERGY */ energyLevelXid: z.number().int().nullable().optional(), - durationDays:z.number().int().optional(), + durationDays: z.number().int().optional(), durationHours: z.number().int().optional(), durationMins: z.number().int().optional(), @@ -158,6 +158,8 @@ export const CreateActivityDto = z.object({ equipments: z.array(EquipmentDto).optional().default([]), amenitiesIds: z.array(z.number().int()).optional().default([]), + foodTotalAmount: z.number().int().optional().default(0), + /* EXTRA OBJECTS */ eligibility: EligibilityDto.optional(), otherDetails: OtherDetailsDto.optional(), diff --git a/src/modules/host/services/host.service.ts b/src/modules/host/services/host.service.ts index 5bad61f..4ab54ff 100644 --- a/src/modules/host/services/host.service.ts +++ b/src/modules/host/services/host.service.ts @@ -107,7 +107,7 @@ const bucket = config.aws.bucketName; @Injectable() export class HostService { - constructor(private prisma: PrismaClient) { } + constructor(private prisma: PrismaClient) {} async createHost(data: CreateHostDto) { return this.prisma.user.create({ data }); @@ -762,7 +762,7 @@ export class HostService { if ( existingHostCompany && existingHostCompany.hostStatusInternal === - HOST_STATUS_INTERNAL.HOST_TO_UPDATE && + HOST_STATUS_INTERNAL.HOST_TO_UPDATE && !isDraft ) { hostStatusInternal = HOST_STATUS_INTERNAL.HOST_SUBMITTED; @@ -775,7 +775,7 @@ export class HostService { else if ( existingHostCompany && existingHostCompany.hostStatusInternal === - HOST_STATUS_INTERNAL.HOST_TO_UPDATE && + HOST_STATUS_INTERNAL.HOST_TO_UPDATE && isDraft ) { // keep original @@ -886,19 +886,19 @@ export class HostService { // Safely handle city connection - only connect if valid ID exists cities: parentCompanyData?.cityXid && - !isNaN(Number(parentCompanyData.cityXid)) + !isNaN(Number(parentCompanyData.cityXid)) ? { connect: { id: Number(parentCompanyData.cityXid) } } : undefined, states: parentCompanyData?.stateXid && - !isNaN(Number(parentCompanyData.stateXid)) + !isNaN(Number(parentCompanyData.stateXid)) ? { connect: { id: Number(parentCompanyData.stateXid) } } : undefined, countries: parentCompanyData?.countryXid && - !isNaN(Number(parentCompanyData.countryXid)) + !isNaN(Number(parentCompanyData.countryXid)) ? { connect: { id: Number(parentCompanyData.countryXid) } } : undefined, pinCode: parentCompanyData.pinCode || null, @@ -1048,19 +1048,19 @@ export class HostService { address2: parentCompanyData.address2 || null, cities: parentCompanyData?.cityXid && - !isNaN(Number(parentCompanyData.cityXid)) + !isNaN(Number(parentCompanyData.cityXid)) ? { connect: { id: Number(parentCompanyData.cityXid) } } : undefined, states: parentCompanyData?.stateXid && - !isNaN(Number(parentCompanyData.stateXid)) + !isNaN(Number(parentCompanyData.stateXid)) ? { connect: { id: Number(parentCompanyData.stateXid) } } : undefined, countries: parentCompanyData?.countryXid && - !isNaN(Number(parentCompanyData.countryXid)) + !isNaN(Number(parentCompanyData.countryXid)) ? { connect: { id: Number(parentCompanyData.countryXid) } } : undefined, pinCode: parentCompanyData.pinCode || null, @@ -1106,19 +1106,19 @@ export class HostService { address2: parentCompanyData.address2 || null, cities: parentCompanyData?.cityXid && - !isNaN(Number(parentCompanyData.cityXid)) + !isNaN(Number(parentCompanyData.cityXid)) ? { connect: { id: Number(parentCompanyData.cityXid) } } : undefined, states: parentCompanyData?.stateXid && - !isNaN(Number(parentCompanyData.stateXid)) + !isNaN(Number(parentCompanyData.stateXid)) ? { connect: { id: Number(parentCompanyData.stateXid) } } : undefined, countries: parentCompanyData?.countryXid && - !isNaN(Number(parentCompanyData.countryXid)) + !isNaN(Number(parentCompanyData.countryXid)) ? { connect: { id: Number(parentCompanyData.countryXid) } } : undefined, pinCode: parentCompanyData.pinCode || null, @@ -2284,7 +2284,11 @@ export class HostService { * ActivityPickUpTransport/Details + ActivityNavigationModes + ActivityEquipments + * ActivityAmenities + ActivityEligibility */ - async createOrUpdateActivity(userId: number, payload: CreateActivityInput, isDraft: boolean) { + async createOrUpdateActivity( + userId: number, + payload: CreateActivityInput, + isDraft: boolean, + ) { /* ===================================================== * HELPERS * ===================================================== */ @@ -2324,7 +2328,7 @@ export class HostService { const durationHours = Number(payload.durationHours ?? 0); const durationMins = Number(payload.durationMins ?? 0); - payload.activityDurationMins = + const activityDurationMins = durationDays * 24 * 60 + durationHours * 60 + durationMins; /* ===================================================== @@ -2346,6 +2350,7 @@ export class HostService { payload.cancellationAvailable = toBool(payload.cancellationAvailable); payload.isInstantBooking = toBool(payload.isInstantBooking); payload.isCheckOutSame = toBool(payload.isCheckOutSame); + payload.alcoholAvailable = toBool(payload.alcoholAvailable); payload.trainerTotalAmount = toNumber(payload.trainerTotalAmount); @@ -2394,9 +2399,9 @@ export class HostService { const rootTaxes = taxIds.length > 0 ? await this.prisma.taxes.findMany({ - where: { id: { in: taxIds }, isActive: true }, - select: { id: true, taxPer: true }, - }) + where: { id: { in: taxIds }, isActive: true }, + select: { id: true, taxPer: true }, + }) : []; if (taxIds.length !== rootTaxes.length) { @@ -2517,7 +2522,7 @@ export class HostService { checkOutAddress: payload.checkOutAddress ?? undefined, energyLevelXid: payload.energyLevelXid ?? undefined, - activityDurationMins: payload.activityDurationMins ?? undefined, + activityDurationMins: activityDurationMins ?? undefined, currencyXid: payload.currencyXid ?? undefined, sustainabilityScore: payload.sustainabilityScore ?? undefined, @@ -2666,6 +2671,77 @@ export class HostService { } } } + /* 8.1️⃣ CLEAN & CREATE FOOD COST (if chargeable) */ + const oldFoodCostIds = ( + await tx.activityFoodCost.findMany({ + where: { activityXid }, + select: { id: true }, + }) + ).map((f) => f.id); + + if (oldFoodCostIds.length) { + await tx.activityFoodTaxes.deleteMany({ + where: { activityFoodCostXid: { in: oldFoodCostIds } }, + }); + await tx.activityFoodCost.deleteMany({ + where: { id: { in: oldFoodCostIds } }, + }); + } + + if (payload.foodAvailable && payload.foodIsChargeable) { + const foodTotalAmount = toNumber(payload.foodTotalAmount) ?? 0; + if (foodTotalAmount <= 0) + throw new ApiError( + 400, + 'foodTotalAmount must be > 0 when foodIsChargeable', + ); + + const { basePrice, taxDetails } = computeBasePriceAndTaxes( + foodTotalAmount, + rootTaxes, + ); + + const foodCost = await tx.activityFoodCost.create({ + data: { + activityXid, + baseAmount: basePrice, + totalAmount: foodTotalAmount, + }, + }); + + if (taxDetails.length) { + await tx.activityFoodTaxes.createMany({ + data: taxDetails.map((t) => ({ + activityFoodCostXid: foodCost.id, + taxXid: t.taxXid, + taxPer: t.taxPer, + taxAmount: t.taxAmount, + })), + }); + } + } + + // 🍲 FOOD TYPES + await tx.activityFoodTypes.deleteMany({ where: { activityXid } }); + if (Array.isArray(payload.foodTypeIds) && payload.foodTypeIds.length) { + await tx.activityFoodTypes.createMany({ + data: payload.foodTypeIds.map((foodTypeId) => ({ + activityXid, + foodTypeXid: foodTypeId, + })), + }); + } + + // 🍛 CUISINES + await tx.activityCuisine.deleteMany({ where: { activityXid } }); + if (Array.isArray(payload.cuisineIds) && payload.cuisineIds.length) { + await tx.activityCuisine.createMany({ + data: payload.cuisineIds.map((cuisineId) => ({ + activityXid, + foodCuisineXid: cuisineId, + })), + }); + } /* -------------------------------- * 9️⃣ CLEAN & CREATE EQUIPMENT WITH TAXES @@ -2932,6 +3008,11 @@ export class HostService { data: { activityXid, isAgeRestriction: toBool(payload.eligibility.isAgeRestriction), + ageRestrictionName: payload.eligibility.ageRestrictionName, + ageEntered: payload.eligibility.ageEntered, + ageIn: payload.eligibility.ageIn, + minAge: payload.eligibility.minAge, + maxAge: payload.eligibility.maxAge, isWeightRestriction: toBool( payload.eligibility.isWeightRestriction, ),