From 340d47a708d72c9ed7de4bcfdcd20f3dc0b4cfac Mon Sep 17 00:00:00 2001 From: paritosh18 Date: Thu, 19 Feb 2026 16:25:43 +0530 Subject: [PATCH] add school or company api --- serverless/functions/user.yml | 17 +++- .../user/dto/addSchoolCompanyDetail.dto.ts | 11 +++ .../connections/addSchoolCompanyDetail.ts | 85 +++++++++++++++++ src/modules/user/services/user.service.ts | 92 +++++++++++++++---- 4 files changed, 187 insertions(+), 18 deletions(-) create mode 100644 src/modules/user/dto/addSchoolCompanyDetail.dto.ts create mode 100644 src/modules/user/handlers/connections/addSchoolCompanyDetail.ts diff --git a/serverless/functions/user.yml b/serverless/functions/user.yml index 2596c96..45cdc9f 100644 --- a/serverless/functions/user.yml +++ b/serverless/functions/user.yml @@ -226,4 +226,19 @@ searchCities: events: - httpApi: path: /user/connections/search-cities - method: get \ No newline at end of file + method: get + +addSchoolCompanyDetail: + handler: src/modules/user/handlers/connections/addSchoolCompanyDetail.handler + memorySize: 384 + package: + patterns: + - 'src/modules/user/handlers/connections/**' + - ${file(./serverless/patterns/base.yml):pattern1} + - ${file(./serverless/patterns/base.yml):pattern2} + - ${file(./serverless/patterns/base.yml):pattern3} + - ${file(./serverless/patterns/base.yml):pattern4} + events: + - httpApi: + path: /user/connections/add-school-company + method: post \ No newline at end of file diff --git a/src/modules/user/dto/addSchoolCompanyDetail.dto.ts b/src/modules/user/dto/addSchoolCompanyDetail.dto.ts new file mode 100644 index 0000000..97592e6 --- /dev/null +++ b/src/modules/user/dto/addSchoolCompanyDetail.dto.ts @@ -0,0 +1,11 @@ +export class AddSchoolCompanyDetailDTO { + schoolCompanyName: string; + isSchool: boolean; + cityXid: number; + + constructor(schoolCompanyName: string, isSchool: boolean, cityXid: number) { + this.schoolCompanyName = schoolCompanyName; + this.isSchool = isSchool; + this.cityXid = cityXid; + } +} diff --git a/src/modules/user/handlers/connections/addSchoolCompanyDetail.ts b/src/modules/user/handlers/connections/addSchoolCompanyDetail.ts new file mode 100644 index 0000000..8575bf8 --- /dev/null +++ b/src/modules/user/handlers/connections/addSchoolCompanyDetail.ts @@ -0,0 +1,85 @@ +import { + APIGatewayProxyEvent, + APIGatewayProxyResult, + Context, +} from 'aws-lambda'; +import { prismaClient } from '../../../../common/database/prisma.lambda.service'; +import { safeHandler } from '../../../../common/utils/handlers/safeHandler'; +import ApiError from '../../../../common/utils/helper/ApiError'; +import { AddSchoolCompanyDetailDTO } from '../../dto/addSchoolCompanyDetail.dto'; +import { UserService } from '../../services/user.service'; + +const userService = new UserService(prismaClient); + +export const handler = safeHandler( + async ( + event: APIGatewayProxyEvent, + context?: Context, + ): Promise => { + // Extract body parameters + let body; + try { + body = JSON.parse(event.body || '{}'); + } catch (error) { + throw new ApiError(400, 'Invalid JSON in request body'); + } + + const { schoolCompanyName, isSchool, cityXid } = body; + + // Validate required inputs + if (!schoolCompanyName || schoolCompanyName.trim().length === 0) { + throw new ApiError(400, 'schoolCompanyName is required'); + } + + if (schoolCompanyName.trim().length < 2) { + throw new ApiError( + 400, + 'schoolCompanyName must be at least 2 characters long', + ); + } + + if (isSchool === undefined || isSchool === null) { + throw new ApiError( + 400, + 'isSchool is required and must be a boolean value', + ); + } + + if (typeof isSchool !== 'boolean') { + throw new ApiError( + 400, + 'isSchool must be a boolean value (true or false)', + ); + } + + if (!cityXid || typeof cityXid !== 'number') { + throw new ApiError(400, 'cityXid is required and must be a number'); + } + + // Create DTO + const dto = new AddSchoolCompanyDetailDTO( + schoolCompanyName.trim(), + isSchool, + cityXid, + ); + + // Call service to add or find school/company + const result = await userService.addOrFindSchoolCompanyDetail(dto); + + return { + statusCode: 201, + headers: { + 'Content-Type': 'application/json', + 'Access-Control-Allow-Origin': '*', + }, + body: JSON.stringify({ + success: true, + message: result.isNew + ? `${isSchool ? 'School' : 'Company'} created successfully` + : `${isSchool ? 'School' : 'Company'} already exists, returning existing record`, + data: result.data, + isNew: result.isNew, + }), + }; + }, +); diff --git a/src/modules/user/services/user.service.ts b/src/modules/user/services/user.service.ts index e933810..7ec3c0f 100644 --- a/src/modules/user/services/user.service.ts +++ b/src/modules/user/services/user.service.ts @@ -8,6 +8,7 @@ import { } from '../../../common/utils/constants/host.constant'; import ApiError from '../../../common/utils/helper/ApiError'; import { UserPersonalInfoSchema } from '../../../common/utils/validation/user/addPersonalInfo.validation'; +import { AddSchoolCompanyDetailDTO } from '../dto/addSchoolCompanyDetail.dto'; import config from '@/config/config'; // function deg2rad(deg) { @@ -1844,24 +1845,23 @@ export class UserService { return activitiesWithCounts; } + // CONNECTIONS - // CONNECTIONS - - async getAllConnectionDetailsOfUser(userXid: number) { - return await this.prisma.connectDetails.findMany({ - where: { userXid, isActive: true }, - select: { - id: true, - schoolCompany: { - select: { - id: true, - schoolCompanyName: true, - isSchool: true, - } - } - } - }) - } + async getAllConnectionDetailsOfUser(userXid: number) { + return await this.prisma.connectDetails.findMany({ + where: { userXid, isActive: true }, + select: { + id: true, + schoolCompany: { + select: { + id: true, + schoolCompanyName: true, + isSchool: true, + }, + }, + }, + }); + } async searchSchoolsAndCompanies(searchQuery: string, isSchool: boolean) { if (!searchQuery) { @@ -1921,4 +1921,62 @@ export class UserService { return results; } + + /** + * Add or Find School/Company Detail + * If school/company with same name exists in same city, return existing record + * Otherwise, create a new record + */ + async addOrFindSchoolCompanyDetail(dto: AddSchoolCompanyDetailDTO) { + const { schoolCompanyName, isSchool, cityXid } = dto; + + // Verify that the city exists + const cityExists = await this.prisma.cities.findFirst({ + where: { + id: cityXid, + isActive: true, + deletedAt: null, + }, + }); + + if (!cityExists) { + throw new ApiError(404, 'City not found'); + } + + // Check if school/company with same name already exists in this city + const existingSchoolCompany = await this.prisma.schoolCompany.findFirst({ + where: { + schoolCompanyName: { + equals: schoolCompanyName, + mode: 'insensitive', + }, + cityXid: cityXid, + isSchool: isSchool, + isActive: true, + deletedAt: null, + }, + }); + + if (existingSchoolCompany) { + // Return existing record + return { + isNew: false, + data: existingSchoolCompany, + }; + } + + // Create new school/company record + const newSchoolCompany = await this.prisma.schoolCompany.create({ + data: { + schoolCompanyName: schoolCompanyName, + isSchool: isSchool, + cityXid : cityXid + }, + }); + + return { + isNew: true, + data: newSchoolCompany, + }; + } }