Compare commits
42 Commits
pqq-optimi
...
sprint2
| Author | SHA1 | Date | |
|---|---|---|---|
| a906dc5635 | |||
| 8ec8cf4854 | |||
| fab7642302 | |||
| 4d3796c5f3 | |||
| 2f3c531c56 | |||
| a2907929d4 | |||
|
|
ef2b23ef83 | ||
| 2767d29d79 | |||
| 46daec00ce | |||
| 43e494780d | |||
| 0da18b18f7 | |||
| b5304b3c26 | |||
| 82340c2918 | |||
| b8f5f92c98 | |||
| 3652d851f7 | |||
|
|
6166075967 | ||
|
|
b6cb5831c2 | ||
|
|
a39cc1c3c8 | ||
|
|
ae76618f7a | ||
| e957fc5c50 | |||
|
|
856db687c3 | ||
| a020a28993 | |||
| 1a520ae9e1 | |||
| d5d6951e64 | |||
| bbd55562af | |||
| 9abadba8f5 | |||
| 747566497c | |||
| 6c3e5ccd60 | |||
| ca9ba601ad | |||
| eab6565e12 | |||
| 6a84876518 | |||
| d8fb4b242d | |||
| 51b053310f | |||
| 06010ef6e8 | |||
| 7b9763c668 | |||
| 4c1a04d043 | |||
|
|
ecf45c3e7c | ||
|
|
20a931ab27 | ||
| 6a84fbc0c3 | |||
| 9fc8336bd9 | |||
| b049146664 | |||
| 963f84681c |
44
.env.example
Normal file
44
.env.example
Normal file
@@ -0,0 +1,44 @@
|
|||||||
|
# Environment Configuration Template
|
||||||
|
# Copy this file to .env.dev, .env.test, or .env.uat and fill in the values
|
||||||
|
|
||||||
|
# Database
|
||||||
|
DATABASE_URL=
|
||||||
|
DB_USERNAME=
|
||||||
|
DB_PASSWORD=
|
||||||
|
DB_DATABASE_NAME=
|
||||||
|
DB_HOSTNAME=
|
||||||
|
DB_PORT=5432
|
||||||
|
|
||||||
|
# Email Bypass (set to true for dev/test, false for production-like environments)
|
||||||
|
BY_PASS_EMAIL=
|
||||||
|
BYPASS_OTP=
|
||||||
|
|
||||||
|
# Brevo Email Configuration
|
||||||
|
BREVO_EMAIL_API_KEY=
|
||||||
|
BREVO_API_BASEURL=https://api.brevo.com
|
||||||
|
BREVO_FROM_EMAIL=
|
||||||
|
BREVO_SMTP_HOST=smtp-relay.brevo.com
|
||||||
|
BREVO_SMTP_PORT=587
|
||||||
|
BREVO_SMTP_USER=
|
||||||
|
BREVO_SMTP_PASS=
|
||||||
|
|
||||||
|
# JWT Configuration
|
||||||
|
REFRESH_TOKEN_SECRET=
|
||||||
|
JWT_SECRET=
|
||||||
|
JWT_ACCESS_EXPIRATION_MINUTES=30
|
||||||
|
JWT_REFRESH_EXPIRATION_DAYS=7
|
||||||
|
JWT_RESET_PASSWORD_EXPIRATION_MINUTES=15
|
||||||
|
JWT_VERIFY_EMAIL_EXPIRATION_MINUTES=15
|
||||||
|
|
||||||
|
# Security
|
||||||
|
SALT_ROUNDS=
|
||||||
|
NODE_ENV=
|
||||||
|
|
||||||
|
# AWS S3
|
||||||
|
S3_BUCKET_NAME=
|
||||||
|
|
||||||
|
# Admin Configuration
|
||||||
|
MINGLAR_ADMIN_NAME=
|
||||||
|
MINGLAR_ADMIN_EMAIL=
|
||||||
|
AM_INVITATION_LINK=
|
||||||
|
HOST_LINK=
|
||||||
4
.gitignore
vendored
4
.gitignore
vendored
@@ -40,10 +40,14 @@ lerna-debug.log*
|
|||||||
.env.test.local
|
.env.test.local
|
||||||
.env.production.local
|
.env.production.local
|
||||||
.env.local
|
.env.local
|
||||||
|
.env.dev
|
||||||
|
.env.test
|
||||||
|
.env.uat
|
||||||
|
|
||||||
# temp
|
# temp
|
||||||
.tmp
|
.tmp
|
||||||
.temp
|
.temp
|
||||||
|
undefined/
|
||||||
|
|
||||||
# Runtime data
|
# Runtime data
|
||||||
pids
|
pids
|
||||||
|
|||||||
490
LAMBDA_OPTIMIZATION_GUIDE.md
Normal file
490
LAMBDA_OPTIMIZATION_GUIDE.md
Normal file
@@ -0,0 +1,490 @@
|
|||||||
|
# AWS Lambda Bundle Size Optimization Guide
|
||||||
|
|
||||||
|
## Overview
|
||||||
|
|
||||||
|
This guide documents how to optimize AWS Lambda function bundle sizes when using:
|
||||||
|
- **Serverless Framework v4** (with built-in esbuild)
|
||||||
|
- **Prisma ORM** (with driver adapters)
|
||||||
|
- **NestJS** or any Node.js framework
|
||||||
|
|
||||||
|
## Problem
|
||||||
|
|
||||||
|
Lambda functions can become bloated (25+ MB) due to:
|
||||||
|
1. **Prisma binary engines** (~50MB uncompressed)
|
||||||
|
2. **AWS SDK v3** being bundled (~5-10MB)
|
||||||
|
3. **Dependencies copied to node_modules** instead of being bundled
|
||||||
|
|
||||||
|
## Solution Architecture
|
||||||
|
|
||||||
|
```
|
||||||
|
┌─────────────────────────────────────────────────────────┐
|
||||||
|
│ Lambda Function │
|
||||||
|
│ ┌─────────────────────────────────────────────────┐ │
|
||||||
|
│ │ Your Code (bundled by esbuild) ~50-500 KB │ │
|
||||||
|
│ └─────────────────────────────────────────────────┘ │
|
||||||
|
│ │ │
|
||||||
|
│ ▼ │
|
||||||
|
│ ┌─────────────────────────────────────────────────┐ │
|
||||||
|
│ │ Prisma Layer (shared) ~15 MB │ │
|
||||||
|
│ │ - @prisma/client │ │
|
||||||
|
│ │ - @prisma/adapter-pg │ │
|
||||||
|
│ │ - .prisma/client (generated) │ │
|
||||||
|
│ │ - pg driver │ │
|
||||||
|
│ └─────────────────────────────────────────────────┘ │
|
||||||
|
│ │ │
|
||||||
|
│ ▼ │
|
||||||
|
│ ┌─────────────────────────────────────────────────┐ │
|
||||||
|
│ │ AWS Lambda Runtime │ │
|
||||||
|
│ │ - AWS SDK v3 (built-in for Node.js 18+) │ │
|
||||||
|
│ └─────────────────────────────────────────────────┘ │
|
||||||
|
└─────────────────────────────────────────────────────────┘
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Step-by-Step Setup
|
||||||
|
|
||||||
|
### 1. Project Structure
|
||||||
|
|
||||||
|
```
|
||||||
|
your-project/
|
||||||
|
├── serverless.yml
|
||||||
|
├── package.json
|
||||||
|
├── prisma/
|
||||||
|
│ └── schema.prisma
|
||||||
|
├── layers/
|
||||||
|
│ └── prisma/
|
||||||
|
│ └── nodejs/
|
||||||
|
│ └── package.json
|
||||||
|
├── src/
|
||||||
|
│ └── ... your code
|
||||||
|
└── build-prisma-layer.ps1 (or .sh for Linux/Mac)
|
||||||
|
```
|
||||||
|
|
||||||
|
### 2. Prisma Schema Configuration
|
||||||
|
|
||||||
|
**`prisma/schema.prisma`**
|
||||||
|
```prisma
|
||||||
|
generator client {
|
||||||
|
provider = "prisma-client-js"
|
||||||
|
// For Prisma 7+ with driver adapters, no binary targets needed
|
||||||
|
// The WASM-based query engine is used automatically
|
||||||
|
}
|
||||||
|
|
||||||
|
datasource db {
|
||||||
|
provider = "postgresql"
|
||||||
|
url = env("DATABASE_URL")
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
> **Note**: Prisma 7+ uses WASM-based query compiler instead of binary engines when using driver adapters, which is much smaller.
|
||||||
|
|
||||||
|
### 3. Layer Package.json
|
||||||
|
|
||||||
|
**`layers/prisma/nodejs/package.json`**
|
||||||
|
```json
|
||||||
|
{
|
||||||
|
"name": "prisma-layer",
|
||||||
|
"version": "1.0.0",
|
||||||
|
"description": "Lambda layer for Prisma with pg driver adapter",
|
||||||
|
"dependencies": {
|
||||||
|
"@prisma/client": "^7.0.0",
|
||||||
|
"@prisma/adapter-pg": "^7.0.0",
|
||||||
|
"pg": "^8.13.0"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### 4. Serverless Configuration
|
||||||
|
|
||||||
|
**`serverless.yml`**
|
||||||
|
```yaml
|
||||||
|
service: your-service-name
|
||||||
|
|
||||||
|
provider:
|
||||||
|
name: aws
|
||||||
|
runtime: nodejs22.x
|
||||||
|
region: your-region
|
||||||
|
memorySize: 512
|
||||||
|
# Apply Prisma layer to ALL functions
|
||||||
|
layers:
|
||||||
|
- !Ref PrismaLambdaLayer
|
||||||
|
environment:
|
||||||
|
DATABASE_URL: ${env:DATABASE_URL}
|
||||||
|
# ... other env vars
|
||||||
|
|
||||||
|
# esbuild configuration (Serverless v4 built-in)
|
||||||
|
build:
|
||||||
|
esbuild:
|
||||||
|
bundle: true
|
||||||
|
minify: true
|
||||||
|
sourcemap: false
|
||||||
|
target: node20
|
||||||
|
platform: node
|
||||||
|
# Mark packages as external (not bundled into JS)
|
||||||
|
external:
|
||||||
|
- '@prisma/client'
|
||||||
|
- '@prisma/adapter-pg'
|
||||||
|
- '.prisma/client'
|
||||||
|
- '.prisma'
|
||||||
|
- 'pg'
|
||||||
|
- '@aws-sdk/*'
|
||||||
|
- '@smithy/*'
|
||||||
|
- '@aws-crypto/*'
|
||||||
|
# Exclude from npm install in zip (CRITICAL!)
|
||||||
|
exclude:
|
||||||
|
- 'aws-sdk'
|
||||||
|
- '@aws-sdk/*'
|
||||||
|
- '@smithy/*'
|
||||||
|
- '@aws-crypto/*'
|
||||||
|
- '@prisma/client'
|
||||||
|
- '@prisma/adapter-pg'
|
||||||
|
- '.prisma'
|
||||||
|
- '.prisma/client'
|
||||||
|
- 'pg'
|
||||||
|
- 'pg-*'
|
||||||
|
- 'postgres-*'
|
||||||
|
- 'pgpass'
|
||||||
|
- 'split2'
|
||||||
|
- 'xtend'
|
||||||
|
|
||||||
|
# Define the Prisma layer
|
||||||
|
layers:
|
||||||
|
prisma:
|
||||||
|
path: layers/prisma
|
||||||
|
name: ${self:service}-prisma-layer-${sls:stage}
|
||||||
|
description: Prisma client with pg driver adapter
|
||||||
|
compatibleRuntimes:
|
||||||
|
- nodejs22.x
|
||||||
|
retain: false
|
||||||
|
|
||||||
|
# Package configuration
|
||||||
|
package:
|
||||||
|
individually: true
|
||||||
|
patterns:
|
||||||
|
- '!node_modules/**'
|
||||||
|
- '!node_modules/@prisma/**'
|
||||||
|
- '!node_modules/.prisma/**'
|
||||||
|
- '!**/*.test.js'
|
||||||
|
- '!**/*.spec.js'
|
||||||
|
- '!**/test/**'
|
||||||
|
- '!**/__tests__/**'
|
||||||
|
- '!package-lock.json'
|
||||||
|
- '!yarn.lock'
|
||||||
|
- '!README.md'
|
||||||
|
- '!.git/**'
|
||||||
|
|
||||||
|
functions:
|
||||||
|
myFunction:
|
||||||
|
handler: src/handlers/myHandler.handler
|
||||||
|
events:
|
||||||
|
- httpApi:
|
||||||
|
path: /my-endpoint
|
||||||
|
method: get
|
||||||
|
|
||||||
|
plugins:
|
||||||
|
- serverless-offline
|
||||||
|
```
|
||||||
|
|
||||||
|
### 5. Build Script for Prisma Layer
|
||||||
|
|
||||||
|
**Windows (PowerShell) - `build-prisma-layer.ps1`**
|
||||||
|
```powershell
|
||||||
|
# Build Prisma Lambda Layer
|
||||||
|
$layerPath = "layers\prisma\nodejs"
|
||||||
|
|
||||||
|
Write-Host "Building Prisma Lambda Layer..." -ForegroundColor Cyan
|
||||||
|
|
||||||
|
# 1. Clean existing node_modules in layer
|
||||||
|
Write-Host "Cleaning layer node_modules..."
|
||||||
|
if (Test-Path "$layerPath\node_modules") {
|
||||||
|
Remove-Item -Recurse -Force "$layerPath\node_modules"
|
||||||
|
}
|
||||||
|
|
||||||
|
# 2. Install dependencies in layer
|
||||||
|
Write-Host "Installing layer dependencies..."
|
||||||
|
Push-Location $layerPath
|
||||||
|
npm install --omit=dev
|
||||||
|
Pop-Location
|
||||||
|
|
||||||
|
# 3. Generate Prisma client
|
||||||
|
Write-Host "Generating Prisma client..."
|
||||||
|
npx prisma generate
|
||||||
|
|
||||||
|
# 4. Copy .prisma/client to layer
|
||||||
|
Write-Host "Copying generated Prisma client to layer..."
|
||||||
|
$sourcePrisma = "node_modules\.prisma"
|
||||||
|
$destPrisma = "$layerPath\node_modules\.prisma"
|
||||||
|
|
||||||
|
if (Test-Path $sourcePrisma) {
|
||||||
|
if (Test-Path $destPrisma) {
|
||||||
|
Remove-Item -Recurse -Force $destPrisma
|
||||||
|
}
|
||||||
|
Copy-Item -Recurse $sourcePrisma $destPrisma
|
||||||
|
Write-Host "Copied .prisma/client successfully!" -ForegroundColor Green
|
||||||
|
} else {
|
||||||
|
Write-Host "ERROR: .prisma folder not found. Run 'npx prisma generate' first." -ForegroundColor Red
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
# 5. Show layer size
|
||||||
|
$layerSize = (Get-ChildItem "$layerPath\node_modules" -Recurse | Measure-Object -Property Length -Sum).Sum / 1MB
|
||||||
|
Write-Host "`nTotal layer size: $([math]::Round($layerSize, 2)) MB" -ForegroundColor Yellow
|
||||||
|
Write-Host "Prisma layer built successfully!" -ForegroundColor Green
|
||||||
|
```
|
||||||
|
|
||||||
|
**Linux/Mac (Bash) - `build-prisma-layer.sh`**
|
||||||
|
```bash
|
||||||
|
#!/bin/bash
|
||||||
|
set -e
|
||||||
|
|
||||||
|
LAYER_PATH="layers/prisma/nodejs"
|
||||||
|
|
||||||
|
echo "Building Prisma Lambda Layer..."
|
||||||
|
|
||||||
|
# 1. Clean existing node_modules in layer
|
||||||
|
echo "Cleaning layer node_modules..."
|
||||||
|
rm -rf "$LAYER_PATH/node_modules"
|
||||||
|
|
||||||
|
# 2. Install dependencies in layer
|
||||||
|
echo "Installing layer dependencies..."
|
||||||
|
cd "$LAYER_PATH"
|
||||||
|
npm install --omit=dev
|
||||||
|
cd -
|
||||||
|
|
||||||
|
# 3. Generate Prisma client
|
||||||
|
echo "Generating Prisma client..."
|
||||||
|
npx prisma generate
|
||||||
|
|
||||||
|
# 4. Copy .prisma/client to layer
|
||||||
|
echo "Copying generated Prisma client to layer..."
|
||||||
|
if [ -d "node_modules/.prisma" ]; then
|
||||||
|
rm -rf "$LAYER_PATH/node_modules/.prisma"
|
||||||
|
cp -r "node_modules/.prisma" "$LAYER_PATH/node_modules/.prisma"
|
||||||
|
echo "Copied .prisma/client successfully!"
|
||||||
|
else
|
||||||
|
echo "ERROR: .prisma folder not found. Run 'npx prisma generate' first."
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 5. Show layer size
|
||||||
|
LAYER_SIZE=$(du -sm "$LAYER_PATH/node_modules" | cut -f1)
|
||||||
|
echo "Total layer size: ${LAYER_SIZE} MB"
|
||||||
|
echo "Prisma layer built successfully!"
|
||||||
|
```
|
||||||
|
|
||||||
|
### 6. Prisma Client Usage
|
||||||
|
|
||||||
|
**`src/common/database/prisma.client.ts`**
|
||||||
|
```typescript
|
||||||
|
import { PrismaClient } from '@prisma/client';
|
||||||
|
import { PrismaPg } from '@prisma/adapter-pg';
|
||||||
|
import { Pool } from 'pg';
|
||||||
|
|
||||||
|
// Connection pool for serverless
|
||||||
|
const pool = new Pool({
|
||||||
|
connectionString: process.env.DATABASE_URL,
|
||||||
|
max: 5, // Limit connections in Lambda
|
||||||
|
});
|
||||||
|
|
||||||
|
const adapter = new PrismaPg(pool);
|
||||||
|
|
||||||
|
// Single instance for Lambda warm starts
|
||||||
|
let prisma: PrismaClient;
|
||||||
|
|
||||||
|
export function getPrismaClient(): PrismaClient {
|
||||||
|
if (!prisma) {
|
||||||
|
prisma = new PrismaClient({
|
||||||
|
adapter,
|
||||||
|
log: process.env.NODE_ENV === 'development' ? ['query', 'error', 'warn'] : ['error'],
|
||||||
|
});
|
||||||
|
}
|
||||||
|
return prisma;
|
||||||
|
}
|
||||||
|
|
||||||
|
export { prisma };
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Deployment Workflow
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 1. Build the Prisma layer (run after schema changes)
|
||||||
|
./build-prisma-layer.ps1 # Windows
|
||||||
|
# or
|
||||||
|
./build-prisma-layer.sh # Linux/Mac
|
||||||
|
|
||||||
|
# 2. Deploy
|
||||||
|
npx serverless deploy --stage=dev
|
||||||
|
|
||||||
|
# 3. Deploy single function (faster, uses existing layer)
|
||||||
|
npx serverless deploy function -f myFunction --stage=dev
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Key Configuration Explained
|
||||||
|
|
||||||
|
### esbuild `external` vs `exclude`
|
||||||
|
|
||||||
|
| Property | Purpose |
|
||||||
|
|----------|---------|
|
||||||
|
| `external` | Tells esbuild NOT to bundle these into the JS file. They become `require()` calls. |
|
||||||
|
| `exclude` | Tells Serverless NOT to `npm install` these packages into the function zip. |
|
||||||
|
|
||||||
|
**Both are required!**
|
||||||
|
- `external` alone = esbuild doesn't bundle, but Serverless still installs to node_modules
|
||||||
|
- `exclude` alone = Serverless doesn't install, but esbuild bundles the code
|
||||||
|
|
||||||
|
### Layer Reference
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
# This creates a CloudFormation reference to the layer defined in the same stack
|
||||||
|
layers:
|
||||||
|
- !Ref PrismaLambdaLayer
|
||||||
|
```
|
||||||
|
|
||||||
|
The `PrismaLambdaLayer` name comes from the layer key (`prisma`) converted to PascalCase + `LambdaLayer`.
|
||||||
|
|
||||||
|
### Why Exclude pg-* packages?
|
||||||
|
|
||||||
|
When `pg` is external, its dependencies still get installed:
|
||||||
|
- `pg-connection-string`
|
||||||
|
- `pg-pool`
|
||||||
|
- `pg-protocol`
|
||||||
|
- `pg-types`
|
||||||
|
- etc.
|
||||||
|
|
||||||
|
These must all be in the `exclude` list to prevent duplication.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Expected Results
|
||||||
|
|
||||||
|
| Function Type | Before | After |
|
||||||
|
|---------------|--------|-------|
|
||||||
|
| Simple handlers | 25+ MB | **50-100 kB** |
|
||||||
|
| With validation (zod/yup) | 25+ MB | **300-500 kB** |
|
||||||
|
| With S3 uploads | 30+ MB | **1-2 MB** |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Troubleshooting
|
||||||
|
|
||||||
|
### 1. "Cannot find module '@prisma/client'"
|
||||||
|
|
||||||
|
**Cause**: Layer doesn't have the generated `.prisma/client`
|
||||||
|
|
||||||
|
**Fix**: Run `build-prisma-layer.ps1` to regenerate the layer
|
||||||
|
|
||||||
|
### 2. Function size still large
|
||||||
|
|
||||||
|
**Debug**: Extract and inspect the zip:
|
||||||
|
```powershell
|
||||||
|
Expand-Archive ".serverless\build\your-function.zip" -DestinationPath "extracted"
|
||||||
|
Get-ChildItem "extracted\node_modules" -Directory
|
||||||
|
```
|
||||||
|
|
||||||
|
If you see `@prisma` or `pg` folders, the `exclude` config isn't working.
|
||||||
|
|
||||||
|
### 3. "Cannot resolve CloudFormation reference"
|
||||||
|
|
||||||
|
**Cause**: Using `${cf:...}` reference before first deploy
|
||||||
|
|
||||||
|
**Fix**: Use `!Ref PrismaLambdaLayer` instead (works on first deploy)
|
||||||
|
|
||||||
|
### 4. Cold starts still slow
|
||||||
|
|
||||||
|
Consider:
|
||||||
|
- **Provisioned Concurrency**: Pre-warm instances
|
||||||
|
- **Reduce memory**: Sometimes lower memory = same speed, lower cost
|
||||||
|
- **Connection pooling**: Use tools like PgBouncer for RDS
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Additional Optimizations
|
||||||
|
|
||||||
|
### 1. Remove duplicate validation libraries
|
||||||
|
|
||||||
|
Pick ONE of: `zod`, `yup`, or `class-validator`. Don't use all three.
|
||||||
|
|
||||||
|
### 2. Tree-shake NestJS
|
||||||
|
|
||||||
|
If not using full NestJS, import only what you need:
|
||||||
|
```typescript
|
||||||
|
// Instead of
|
||||||
|
import { Controller, Get } from '@nestjs/common';
|
||||||
|
|
||||||
|
// For Lambda handlers, you might not need NestJS at all
|
||||||
|
```
|
||||||
|
|
||||||
|
### 3. Use AWS SDK v3 selectively
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
external:
|
||||||
|
- '@aws-sdk/*' # Exclude all
|
||||||
|
```
|
||||||
|
|
||||||
|
Then in code:
|
||||||
|
```typescript
|
||||||
|
// AWS SDK v3 is available in Lambda runtime (Node.js 18+)
|
||||||
|
import { S3Client } from '@aws-sdk/client-s3';
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Quick Reference
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
# Minimal serverless.yml for Prisma + Lambda optimization
|
||||||
|
build:
|
||||||
|
esbuild:
|
||||||
|
bundle: true
|
||||||
|
minify: true
|
||||||
|
external:
|
||||||
|
- '@prisma/client'
|
||||||
|
- '@prisma/adapter-pg'
|
||||||
|
- '.prisma/client'
|
||||||
|
- '.prisma'
|
||||||
|
- 'pg'
|
||||||
|
- '@aws-sdk/*'
|
||||||
|
exclude:
|
||||||
|
- '@prisma/client'
|
||||||
|
- '@prisma/adapter-pg'
|
||||||
|
- '.prisma'
|
||||||
|
- '.prisma/client'
|
||||||
|
- 'pg'
|
||||||
|
- 'pg-*'
|
||||||
|
- 'postgres-*'
|
||||||
|
- 'pgpass'
|
||||||
|
- 'split2'
|
||||||
|
- 'xtend'
|
||||||
|
- '@aws-sdk/*'
|
||||||
|
|
||||||
|
layers:
|
||||||
|
prisma:
|
||||||
|
path: layers/prisma
|
||||||
|
name: ${self:service}-prisma-${sls:stage}
|
||||||
|
compatibleRuntimes:
|
||||||
|
- nodejs22.x
|
||||||
|
|
||||||
|
provider:
|
||||||
|
layers:
|
||||||
|
- !Ref PrismaLambdaLayer
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Version Compatibility
|
||||||
|
|
||||||
|
| Tool | Tested Version |
|
||||||
|
|------|----------------|
|
||||||
|
| Serverless Framework | v4.x |
|
||||||
|
| Prisma | v7.x |
|
||||||
|
| Node.js | 20.x, 22.x |
|
||||||
|
| AWS Lambda Runtime | nodejs20.x, nodejs22.x |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
*Last updated: December 2025*
|
||||||
51
build-prisma-layer.ps1
Normal file
51
build-prisma-layer.ps1
Normal file
@@ -0,0 +1,51 @@
|
|||||||
|
# Build Prisma Lambda Layer
|
||||||
|
# Run this script before deploying to ensure the layer has the generated client
|
||||||
|
|
||||||
|
$layerPath = "layers\prisma\nodejs"
|
||||||
|
|
||||||
|
Write-Host "Building Prisma Lambda Layer..." -ForegroundColor Cyan
|
||||||
|
|
||||||
|
# 1. Clean existing node_modules in layer
|
||||||
|
Write-Host "Cleaning layer node_modules..."
|
||||||
|
if (Test-Path "$layerPath\node_modules") {
|
||||||
|
Remove-Item -Recurse -Force "$layerPath\node_modules"
|
||||||
|
}
|
||||||
|
|
||||||
|
# 2. Install dependencies in layer
|
||||||
|
Write-Host "Installing layer dependencies..."
|
||||||
|
Push-Location $layerPath
|
||||||
|
npm install --omit=dev
|
||||||
|
Pop-Location
|
||||||
|
|
||||||
|
# 3. Generate Prisma client into the layer
|
||||||
|
Write-Host "Generating Prisma client into layer..."
|
||||||
|
# Set the output directory for Prisma client
|
||||||
|
$env:PRISMA_GENERATE_DATAPROXY = "false"
|
||||||
|
|
||||||
|
# Generate client - this creates .prisma/client
|
||||||
|
npx prisma generate
|
||||||
|
|
||||||
|
# 4. Copy .prisma/client to layer
|
||||||
|
Write-Host "Copying generated Prisma client to layer..."
|
||||||
|
$sourcePrisma = "node_modules\.prisma"
|
||||||
|
$destPrisma = "$layerPath\node_modules\.prisma"
|
||||||
|
|
||||||
|
if (Test-Path $sourcePrisma) {
|
||||||
|
if (Test-Path $destPrisma) {
|
||||||
|
Remove-Item -Recurse -Force $destPrisma
|
||||||
|
}
|
||||||
|
Copy-Item -Recurse $sourcePrisma $destPrisma
|
||||||
|
Write-Host "Copied .prisma/client successfully!" -ForegroundColor Green
|
||||||
|
} else {
|
||||||
|
Write-Host "ERROR: .prisma folder not found. Run 'npx prisma generate' first." -ForegroundColor Red
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
# 5. Show layer size
|
||||||
|
Write-Host "`nLayer contents:"
|
||||||
|
Get-ChildItem "$layerPath\node_modules" -Directory | Select-Object Name
|
||||||
|
$layerSize = (Get-ChildItem "$layerPath\node_modules" -Recurse | Measure-Object -Property Length -Sum).Sum / 1MB
|
||||||
|
Write-Host "`nTotal layer size: $([math]::Round($layerSize, 2)) MB" -ForegroundColor Yellow
|
||||||
|
|
||||||
|
Write-Host "`nPrisma layer built successfully!" -ForegroundColor Green
|
||||||
|
Write-Host "Run 'serverless deploy' to deploy with the updated layer."
|
||||||
238
layers/prisma/nodejs/package-lock.json
generated
Normal file
238
layers/prisma/nodejs/package-lock.json
generated
Normal file
@@ -0,0 +1,238 @@
|
|||||||
|
{
|
||||||
|
"name": "prisma-layer",
|
||||||
|
"version": "1.0.0",
|
||||||
|
"lockfileVersion": 3,
|
||||||
|
"requires": true,
|
||||||
|
"packages": {
|
||||||
|
"": {
|
||||||
|
"name": "prisma-layer",
|
||||||
|
"version": "1.0.0",
|
||||||
|
"dependencies": {
|
||||||
|
"@prisma/adapter-pg": "^7.0.1",
|
||||||
|
"@prisma/client": "^7.0.1",
|
||||||
|
"pg": "^8.13.0",
|
||||||
|
"zod": "^4.1.12"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@prisma/adapter-pg": {
|
||||||
|
"version": "7.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/@prisma/adapter-pg/-/adapter-pg-7.0.1.tgz",
|
||||||
|
"integrity": "sha512-01GpPPhLMoDMF4ipgfZz0L87fla/TV/PBQcmHy+9vV1ml6gUoqF8dUIRNI5Yf2YKpOwzQg9sn8C7dYD1Yio9Ug==",
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"dependencies": {
|
||||||
|
"@prisma/driver-adapter-utils": "7.0.1",
|
||||||
|
"pg": "^8.16.3",
|
||||||
|
"postgres-array": "3.0.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@prisma/client": {
|
||||||
|
"version": "7.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/@prisma/client/-/client-7.0.1.tgz",
|
||||||
|
"integrity": "sha512-O74T6xcfaGAq5gXwCAvfTLvI6fmC3and2g5yLRMkNjri1K8mSpEgclDNuUWs9xj5AwNEMQ88NeD3asI+sovm1g==",
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"dependencies": {
|
||||||
|
"@prisma/client-runtime-utils": "7.0.1"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": "^20.19 || ^22.12 || >=24.0"
|
||||||
|
},
|
||||||
|
"peerDependencies": {
|
||||||
|
"prisma": "*",
|
||||||
|
"typescript": ">=5.4.0"
|
||||||
|
},
|
||||||
|
"peerDependenciesMeta": {
|
||||||
|
"prisma": {
|
||||||
|
"optional": true
|
||||||
|
},
|
||||||
|
"typescript": {
|
||||||
|
"optional": true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@prisma/client-runtime-utils": {
|
||||||
|
"version": "7.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/@prisma/client-runtime-utils/-/client-runtime-utils-7.0.1.tgz",
|
||||||
|
"integrity": "sha512-R26BVX9D/iw4toUmZKZf3jniM/9pMGHHdZN5LVP2L7HNiCQKNQQx/9LuMtjepbgRqSqQO3oHN0yzojHLnKTGEw==",
|
||||||
|
"license": "Apache-2.0"
|
||||||
|
},
|
||||||
|
"node_modules/@prisma/debug": {
|
||||||
|
"version": "7.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/@prisma/debug/-/debug-7.0.1.tgz",
|
||||||
|
"integrity": "sha512-5+25XokVeAK2Z2C9W457AFw7Hk032Q3QI3G58KYKXPlpgxy+9FvV1+S1jqfJ2d4Nmq9LP/uACrM6OVhpJMSr8w==",
|
||||||
|
"license": "Apache-2.0"
|
||||||
|
},
|
||||||
|
"node_modules/@prisma/driver-adapter-utils": {
|
||||||
|
"version": "7.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/@prisma/driver-adapter-utils/-/driver-adapter-utils-7.0.1.tgz",
|
||||||
|
"integrity": "sha512-sBbxm/yysHLLF2iMAB+qcX/nn3WFgsiC4DQNz0uM6BwGSIs8lIvgo0u8nR9nxe5gvFgKiIH8f4z2fgOEMeXc8w==",
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"dependencies": {
|
||||||
|
"@prisma/debug": "7.0.1"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/pg": {
|
||||||
|
"version": "8.16.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/pg/-/pg-8.16.3.tgz",
|
||||||
|
"integrity": "sha512-enxc1h0jA/aq5oSDMvqyW3q89ra6XIIDZgCX9vkMrnz5DFTw/Ny3Li2lFQ+pt3L6MCgm/5o2o8HW9hiJji+xvw==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"pg-connection-string": "^2.9.1",
|
||||||
|
"pg-pool": "^3.10.1",
|
||||||
|
"pg-protocol": "^1.10.3",
|
||||||
|
"pg-types": "2.2.0",
|
||||||
|
"pgpass": "1.0.5"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">= 16.0.0"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"pg-cloudflare": "^1.2.7"
|
||||||
|
},
|
||||||
|
"peerDependencies": {
|
||||||
|
"pg-native": ">=3.0.1"
|
||||||
|
},
|
||||||
|
"peerDependenciesMeta": {
|
||||||
|
"pg-native": {
|
||||||
|
"optional": true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/pg-cloudflare": {
|
||||||
|
"version": "1.2.7",
|
||||||
|
"resolved": "https://registry.npmjs.org/pg-cloudflare/-/pg-cloudflare-1.2.7.tgz",
|
||||||
|
"integrity": "sha512-YgCtzMH0ptvZJslLM1ffsY4EuGaU0cx4XSdXLRFae8bPP4dS5xL1tNB3k2o/N64cHJpwU7dxKli/nZ2lUa5fLg==",
|
||||||
|
"license": "MIT",
|
||||||
|
"optional": true
|
||||||
|
},
|
||||||
|
"node_modules/pg-connection-string": {
|
||||||
|
"version": "2.9.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/pg-connection-string/-/pg-connection-string-2.9.1.tgz",
|
||||||
|
"integrity": "sha512-nkc6NpDcvPVpZXxrreI/FOtX3XemeLl8E0qFr6F2Lrm/I8WOnaWNhIPK2Z7OHpw7gh5XJThi6j6ppgNoaT1w4w==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
|
"node_modules/pg-int8": {
|
||||||
|
"version": "1.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/pg-int8/-/pg-int8-1.0.1.tgz",
|
||||||
|
"integrity": "sha512-WCtabS6t3c8SkpDBUlb1kjOs7l66xsGdKpIPZsg4wR+B3+u9UAum2odSsF9tnvxg80h4ZxLWMy4pRjOsFIqQpw==",
|
||||||
|
"license": "ISC",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=4.0.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/pg-pool": {
|
||||||
|
"version": "3.10.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/pg-pool/-/pg-pool-3.10.1.tgz",
|
||||||
|
"integrity": "sha512-Tu8jMlcX+9d8+QVzKIvM/uJtp07PKr82IUOYEphaWcoBhIYkoHpLXN3qO59nAI11ripznDsEzEv8nUxBVWajGg==",
|
||||||
|
"license": "MIT",
|
||||||
|
"peerDependencies": {
|
||||||
|
"pg": ">=8.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/pg-protocol": {
|
||||||
|
"version": "1.10.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/pg-protocol/-/pg-protocol-1.10.3.tgz",
|
||||||
|
"integrity": "sha512-6DIBgBQaTKDJyxnXaLiLR8wBpQQcGWuAESkRBX/t6OwA8YsqP+iVSiond2EDy6Y/dsGk8rh/jtax3js5NeV7JQ==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
|
"node_modules/pg-types": {
|
||||||
|
"version": "2.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/pg-types/-/pg-types-2.2.0.tgz",
|
||||||
|
"integrity": "sha512-qTAAlrEsl8s4OiEQY69wDvcMIdQN6wdz5ojQiOy6YRMuynxenON0O5oCpJI6lshc6scgAY8qvJ2On/p+CXY0GA==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"pg-int8": "1.0.1",
|
||||||
|
"postgres-array": "~2.0.0",
|
||||||
|
"postgres-bytea": "~1.0.0",
|
||||||
|
"postgres-date": "~1.0.4",
|
||||||
|
"postgres-interval": "^1.1.0"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/pg-types/node_modules/postgres-array": {
|
||||||
|
"version": "2.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/postgres-array/-/postgres-array-2.0.0.tgz",
|
||||||
|
"integrity": "sha512-VpZrUqU5A69eQyW2c5CA1jtLecCsN2U/bD6VilrFDWq5+5UIEVO7nazS3TEcHf1zuPYO/sqGvUvW62g86RXZuA==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/pgpass": {
|
||||||
|
"version": "1.0.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/pgpass/-/pgpass-1.0.5.tgz",
|
||||||
|
"integrity": "sha512-FdW9r/jQZhSeohs1Z3sI1yxFQNFvMcnmfuj4WBMUTxOrAyLMaTcE1aAMBiTlbMNaXvBCQuVi0R7hd8udDSP7ug==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"split2": "^4.1.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/postgres-array": {
|
||||||
|
"version": "3.0.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/postgres-array/-/postgres-array-3.0.4.tgz",
|
||||||
|
"integrity": "sha512-nAUSGfSDGOaOAEGwqsRY27GPOea7CNipJPOA7lPbdEpx5Kg3qzdP0AaWC5MlhTWV9s4hFX39nomVZ+C4tnGOJQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=12"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/postgres-bytea": {
|
||||||
|
"version": "1.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/postgres-bytea/-/postgres-bytea-1.0.0.tgz",
|
||||||
|
"integrity": "sha512-xy3pmLuQqRBZBXDULy7KbaitYqLcmxigw14Q5sj8QBVLqEwXfeybIKVWiqAXTlcvdvb0+xkOtDbfQMOf4lST1w==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=0.10.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/postgres-date": {
|
||||||
|
"version": "1.0.7",
|
||||||
|
"resolved": "https://registry.npmjs.org/postgres-date/-/postgres-date-1.0.7.tgz",
|
||||||
|
"integrity": "sha512-suDmjLVQg78nMK2UZ454hAG+OAW+HQPZ6n++TNDUX+L0+uUlLywnoxJKDou51Zm+zTCjrCl0Nq6J9C5hP9vK/Q==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=0.10.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/postgres-interval": {
|
||||||
|
"version": "1.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/postgres-interval/-/postgres-interval-1.2.0.tgz",
|
||||||
|
"integrity": "sha512-9ZhXKM/rw350N1ovuWHbGxnGh/SNJ4cnxHiM0rxE4VN41wsg8P8zWn9hv/buK00RP4WvlOyr/RBDiptyxVbkZQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"xtend": "^4.0.0"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=0.10.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/split2": {
|
||||||
|
"version": "4.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/split2/-/split2-4.2.0.tgz",
|
||||||
|
"integrity": "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==",
|
||||||
|
"license": "ISC",
|
||||||
|
"engines": {
|
||||||
|
"node": ">= 10.x"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/xtend": {
|
||||||
|
"version": "4.0.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz",
|
||||||
|
"integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=0.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/zod": {
|
||||||
|
"version": "4.1.13",
|
||||||
|
"resolved": "https://registry.npmjs.org/zod/-/zod-4.1.13.tgz",
|
||||||
|
"integrity": "sha512-AvvthqfqrAhNH9dnfmrfKzX5upOdjUVJYFqNSlkmGf64gRaTzlPwz99IHYnVs28qYAybvAlBV+H7pn0saFY4Ig==",
|
||||||
|
"license": "MIT",
|
||||||
|
"funding": {
|
||||||
|
"url": "https://github.com/sponsors/colinhacks"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
11
layers/prisma/nodejs/package.json
Normal file
11
layers/prisma/nodejs/package.json
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
{
|
||||||
|
"name": "prisma-layer",
|
||||||
|
"version": "1.0.0",
|
||||||
|
"description": "Lambda layer for Prisma 7 with pg driver adapter and zod",
|
||||||
|
"dependencies": {
|
||||||
|
"@prisma/client": "^7.0.1",
|
||||||
|
"@prisma/adapter-pg": "^7.0.1",
|
||||||
|
"pg": "^8.13.0",
|
||||||
|
"zod": "^4.1.12"
|
||||||
|
}
|
||||||
|
}
|
||||||
10
package-lock.json
generated
10
package-lock.json
generated
@@ -46,7 +46,7 @@
|
|||||||
"prisma": "^7.0.1",
|
"prisma": "^7.0.1",
|
||||||
"reflect-metadata": "^0.1.13",
|
"reflect-metadata": "^0.1.13",
|
||||||
"rxjs": "^7.8.1",
|
"rxjs": "^7.8.1",
|
||||||
"serverless": "4.17.0",
|
"serverless": "4.24.0",
|
||||||
"swagger-ui-express": "^5.0.0",
|
"swagger-ui-express": "^5.0.0",
|
||||||
"tslib": "^2.8.1",
|
"tslib": "^2.8.1",
|
||||||
"uuid": "^13.0.0",
|
"uuid": "^13.0.0",
|
||||||
@@ -14467,12 +14467,12 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/serverless": {
|
"node_modules/serverless": {
|
||||||
"version": "4.17.0",
|
"version": "4.24.0",
|
||||||
"resolved": "https://registry.npmjs.org/serverless/-/serverless-4.17.0.tgz",
|
"resolved": "https://registry.npmjs.org/serverless/-/serverless-4.24.0.tgz",
|
||||||
"integrity": "sha512-hoZmipwyN/h7y9HwkWGlJ0YT06RFq7WNOD7fFEiPfnSnnUMVTzeNHq2BRrUlpHhf5s9srCHDc2wx5I06acfq1Q==",
|
"integrity": "sha512-bgxFQ6QyOGJC9IZjZIXo4m6bdWMl9I7HNZ4jrmwSpdePdsRd46igGRpSnhdYFOc71GNplhSOeoCibL94yCHfrg==",
|
||||||
"hasInstallScript": true,
|
"hasInstallScript": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"axios": "^1.8.3",
|
"axios": "^1.12.1",
|
||||||
"axios-proxy-builder": "^0.1.2",
|
"axios-proxy-builder": "^0.1.2",
|
||||||
"rimraf": "^5.0.5",
|
"rimraf": "^5.0.5",
|
||||||
"xml2js": "0.6.2"
|
"xml2js": "0.6.2"
|
||||||
|
|||||||
@@ -63,7 +63,7 @@
|
|||||||
"prisma": "^7.0.1",
|
"prisma": "^7.0.1",
|
||||||
"reflect-metadata": "^0.1.13",
|
"reflect-metadata": "^0.1.13",
|
||||||
"rxjs": "^7.8.1",
|
"rxjs": "^7.8.1",
|
||||||
"serverless": "4.17.0",
|
"serverless": "4.24.0",
|
||||||
"swagger-ui-express": "^5.0.0",
|
"swagger-ui-express": "^5.0.0",
|
||||||
"tslib": "^2.8.1",
|
"tslib": "^2.8.1",
|
||||||
"uuid": "^13.0.0",
|
"uuid": "^13.0.0",
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
// prisma.ts
|
// prisma.ts
|
||||||
import { PrismaClient } from '@prisma/client';
|
// Re-export from the main singleton for consistency
|
||||||
|
import { prisma } from '../src/common/database/prisma.client';
|
||||||
|
|
||||||
// The DATABASE_URL environment variable will be automatically used
|
export { prisma };
|
||||||
export const prisma = new PrismaClient();
|
|
||||||
|
|
||||||
process.on('SIGINT', async () => {
|
process.on('SIGINT', async () => {
|
||||||
await prisma.$disconnect();
|
await prisma.$disconnect();
|
||||||
|
|||||||
@@ -33,11 +33,46 @@ async function main() {
|
|||||||
update: {},
|
update: {},
|
||||||
create: { countryXid: india.id, stateName: 'Maharashtra' },
|
create: { countryXid: india.id, stateName: 'Maharashtra' },
|
||||||
});
|
});
|
||||||
|
const uttarpradesh = await prisma.states.upsert({
|
||||||
|
where: { stateName: 'Uttar-Pradesh' },
|
||||||
|
update: {},
|
||||||
|
create: { countryXid: india.id, stateName: 'Uttar-Pradesh' },
|
||||||
|
});
|
||||||
|
const Rajasthan = await prisma.states.upsert({
|
||||||
|
where: { stateName: 'Rajasthan' },
|
||||||
|
update: {},
|
||||||
|
create: { countryXid: india.id, stateName: 'Rajasthan' },
|
||||||
|
});
|
||||||
|
const Uttarakhand = await prisma.states.upsert({
|
||||||
|
where: { stateName: 'Uttarakhand' },
|
||||||
|
update: {},
|
||||||
|
create: { countryXid: india.id, stateName: 'Uttarakhand' },
|
||||||
|
});
|
||||||
|
const HimachalPradesh = await prisma.states.upsert({
|
||||||
|
where: { stateName: 'Himachal Pradesh' },
|
||||||
|
update: {},
|
||||||
|
create: { countryXid: india.id, stateName: 'Himachal Pradesh' },
|
||||||
|
});
|
||||||
|
const Gujrat = await prisma.states.upsert({
|
||||||
|
where: { stateName: 'Gujrat' },
|
||||||
|
update: {},
|
||||||
|
create: { countryXid: india.id, stateName: 'Gujrat' },
|
||||||
|
});
|
||||||
|
|
||||||
// ✅ Cities
|
// ✅ Cities
|
||||||
await prisma.cities.createMany({
|
await prisma.cities.createMany({
|
||||||
data: [
|
data: [
|
||||||
{ stateXid: maharashtra.id, cityName: 'Mumbai' },
|
{ stateXid: maharashtra.id, cityName: 'Mumbai' },
|
||||||
|
{ stateXid: uttarpradesh.id, cityName: 'Azamgarh' },
|
||||||
|
{ stateXid: uttarpradesh.id, cityName: 'Lucknow' },
|
||||||
|
{ stateXid: uttarpradesh.id, cityName: 'Prayagraj' },
|
||||||
|
{ stateXid: Rajasthan.id, cityName: 'Jaipur' },
|
||||||
|
{ stateXid: Rajasthan.id, cityName: 'Jaisalmer' },
|
||||||
|
{ stateXid: Uttarakhand.id, cityName: 'Haridwar' },
|
||||||
|
{ stateXid: HimachalPradesh.id, cityName: 'Manali' },
|
||||||
|
{ stateXid: Gujrat.id, cityName: 'Surat' },
|
||||||
|
{ stateXid: Gujrat.id, cityName: 'Ahemdabad' },
|
||||||
|
{ stateXid: Gujrat.id, cityName: 'Rajkot' },
|
||||||
],
|
],
|
||||||
skipDuplicates: true,
|
skipDuplicates: true,
|
||||||
});
|
});
|
||||||
@@ -56,6 +91,21 @@ async function main() {
|
|||||||
update: {},
|
update: {},
|
||||||
create: { countryXid: india.id, bankName: 'HDFC Bank' },
|
create: { countryXid: india.id, bankName: 'HDFC Bank' },
|
||||||
});
|
});
|
||||||
|
const indianBank = await prisma.banks.upsert({
|
||||||
|
where: { bankName: 'Indian Bank' },
|
||||||
|
update: {},
|
||||||
|
create: { countryXid: india.id, bankName: 'Indian Bank' },
|
||||||
|
});
|
||||||
|
const Kotak = await prisma.banks.upsert({
|
||||||
|
where: { bankName: 'Kotak Bank' },
|
||||||
|
update: {},
|
||||||
|
create: { countryXid: india.id, bankName: 'Kotak Bank' },
|
||||||
|
});
|
||||||
|
const BOI = await prisma.banks.upsert({
|
||||||
|
where: { bankName: 'Bank of India' },
|
||||||
|
update: {},
|
||||||
|
create: { countryXid: india.id, bankName: 'Bank of India' },
|
||||||
|
});
|
||||||
|
|
||||||
// ✅ Bank Branches
|
// ✅ Bank Branches
|
||||||
await prisma.bankBranches.createMany({
|
await prisma.bankBranches.createMany({
|
||||||
@@ -67,6 +117,27 @@ async function main() {
|
|||||||
branchAddress: 'HDFC Fort Branch, Mumbai',
|
branchAddress: 'HDFC Fort Branch, Mumbai',
|
||||||
ifscCode: 'HDFC0001234',
|
ifscCode: 'HDFC0001234',
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
bankXid: indianBank.id,
|
||||||
|
stateXid: maharashtra.id,
|
||||||
|
cityXid: (await prisma.cities.findFirst({ where: { cityName: 'Mumbai' } }))!.id,
|
||||||
|
branchAddress: 'Indian Bank Fort Branch, Mumbai',
|
||||||
|
ifscCode: 'IDIB0001234',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
bankXid: Kotak.id,
|
||||||
|
stateXid: Uttarakhand.id,
|
||||||
|
cityXid: (await prisma.cities.findFirst({ where: { cityName: 'Haridwar' } }))!.id,
|
||||||
|
branchAddress: 'Kotak Fort Branch, Mumbai',
|
||||||
|
ifscCode: 'KTB0001234',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
bankXid: BOI.id,
|
||||||
|
stateXid: uttarpradesh.id,
|
||||||
|
cityXid: (await prisma.cities.findFirst({ where: { cityName: 'Azamgarh' } }))!.id,
|
||||||
|
branchAddress: 'Bank of India Fort Branch, Mumbai',
|
||||||
|
ifscCode: 'BOI0001234',
|
||||||
|
},
|
||||||
],
|
],
|
||||||
skipDuplicates: true,
|
skipDuplicates: true,
|
||||||
});
|
});
|
||||||
@@ -179,9 +250,9 @@ async function main() {
|
|||||||
});
|
});
|
||||||
|
|
||||||
await prisma.companyTypes.upsert({
|
await prisma.companyTypes.upsert({
|
||||||
where: { companyTypeName: 'Private Limited, Public Limited' },
|
where: { companyTypeName: 'Private Limited' },
|
||||||
update: {},
|
update: {},
|
||||||
create: { companyTypeName: 'Private Limited, Public Limited', displayOrder: 5 },
|
create: { companyTypeName: 'Private Limited', displayOrder: 5 },
|
||||||
});
|
});
|
||||||
|
|
||||||
await prisma.companyTypes.upsert({
|
await prisma.companyTypes.upsert({
|
||||||
@@ -189,6 +260,12 @@ async function main() {
|
|||||||
update: {},
|
update: {},
|
||||||
create: { companyTypeName: 'Non-Profit Organisation', displayOrder: 6 },
|
create: { companyTypeName: 'Non-Profit Organisation', displayOrder: 6 },
|
||||||
});
|
});
|
||||||
|
|
||||||
|
await prisma.companyTypes.upsert({
|
||||||
|
where: { companyTypeName: 'Public Limited' },
|
||||||
|
update: {},
|
||||||
|
create: { companyTypeName: 'Public Limited', displayOrder: 7 },
|
||||||
|
});
|
||||||
|
|
||||||
// ✅ Food Types
|
// ✅ Food Types
|
||||||
await prisma.foodTypes.createMany({
|
await prisma.foodTypes.createMany({
|
||||||
|
|||||||
@@ -1,16 +1,32 @@
|
|||||||
service: minglarDev
|
service: minglar
|
||||||
|
|
||||||
|
useDotenv: true
|
||||||
|
|
||||||
|
params:
|
||||||
|
dev:
|
||||||
|
stage: dev
|
||||||
|
test:
|
||||||
|
stage: test
|
||||||
|
uat:
|
||||||
|
stage: uat
|
||||||
|
|
||||||
provider:
|
provider:
|
||||||
name: aws
|
name: aws
|
||||||
runtime: nodejs22.x
|
runtime: nodejs22.x
|
||||||
region: ap-south-1
|
region: ap-south-1
|
||||||
|
stage: ${opt:stage, 'dev'}
|
||||||
versionFunctions: false
|
versionFunctions: false
|
||||||
memorySize: 512
|
memorySize: 512
|
||||||
|
# Apply Prisma layer to all functions
|
||||||
|
# Reference the layer defined in this stack using CloudFormation Ref
|
||||||
|
layers:
|
||||||
|
# Use the exported stack output so deploy function works (expects a string ARN)
|
||||||
|
- ${cf:${self:service}-${sls:stage}.PrismaLambdaLayerQualifiedArn}
|
||||||
apiGateway:
|
apiGateway:
|
||||||
binaryMediaTypes:
|
binaryMediaTypes:
|
||||||
- '*/*'
|
- '*/*'
|
||||||
minimumCompressionSize: 1024
|
minimumCompressionSize: 1024
|
||||||
|
|
||||||
environment:
|
environment:
|
||||||
DATABASE_URL: ${env:DATABASE_URL}
|
DATABASE_URL: ${env:DATABASE_URL}
|
||||||
DB_USERNAME: ${env:DB_USERNAME}
|
DB_USERNAME: ${env:DB_USERNAME}
|
||||||
@@ -38,7 +54,9 @@ provider:
|
|||||||
S3_BUCKET_NAME: ${env:S3_BUCKET_NAME}
|
S3_BUCKET_NAME: ${env:S3_BUCKET_NAME}
|
||||||
MINGLAR_ADMIN_NAME: ${env:MINGLAR_ADMIN_NAME}
|
MINGLAR_ADMIN_NAME: ${env:MINGLAR_ADMIN_NAME}
|
||||||
MINGLAR_ADMIN_EMAIL: ${env:MINGLAR_ADMIN_EMAIL}
|
MINGLAR_ADMIN_EMAIL: ${env:MINGLAR_ADMIN_EMAIL}
|
||||||
|
AM_INVITATION_LINK: ${env:AM_INVITATION_LINK}
|
||||||
|
HOST_LINK: ${env:HOST_LINK}
|
||||||
|
|
||||||
iam:
|
iam:
|
||||||
role:
|
role:
|
||||||
statements:
|
statements:
|
||||||
@@ -51,27 +69,63 @@ provider:
|
|||||||
Resource:
|
Resource:
|
||||||
- 'arn:aws:s3:::${env:S3_BUCKET_NAME}'
|
- 'arn:aws:s3:::${env:S3_BUCKET_NAME}'
|
||||||
- 'arn:aws:s3:::${env:S3_BUCKET_NAME}/*'
|
- 'arn:aws:s3:::${env:S3_BUCKET_NAME}/*'
|
||||||
|
|
||||||
custom:
|
custom:
|
||||||
|
serverless-offline:
|
||||||
|
reloadHandler: true
|
||||||
|
|
||||||
|
build:
|
||||||
esbuild:
|
esbuild:
|
||||||
bundle: true
|
bundle: true
|
||||||
minify: true
|
minify: true
|
||||||
sourcemap: false
|
sourcemap: false
|
||||||
target: node20
|
target: node20
|
||||||
platform: node
|
platform: node
|
||||||
concurrency: 5
|
# Mark as external so they're not bundled into the JS
|
||||||
external:
|
external:
|
||||||
- '@prisma/client'
|
- '@prisma/client'
|
||||||
|
- '.prisma/client'
|
||||||
- '.prisma'
|
- '.prisma'
|
||||||
|
- '@prisma/adapter-pg'
|
||||||
|
- 'pg'
|
||||||
|
- 'zod'
|
||||||
|
- '@aws-sdk/*'
|
||||||
|
- '@smithy/*'
|
||||||
|
- '@aws-crypto/*'
|
||||||
|
# Exclude prevents npm install of these packages in the zip
|
||||||
exclude:
|
exclude:
|
||||||
- 'aws-sdk'
|
- 'aws-sdk'
|
||||||
serverless-offline:
|
- '@aws-sdk/*'
|
||||||
reloadHandler: true
|
- '@smithy/*'
|
||||||
|
- '@aws-crypto/*'
|
||||||
|
- '@prisma/adapter-pg'
|
||||||
|
- '@prisma/client'
|
||||||
|
- '.prisma'
|
||||||
|
- '.prisma/client'
|
||||||
|
- 'pg'
|
||||||
|
- 'zod'
|
||||||
|
- 'pg-*'
|
||||||
|
- 'postgres-*'
|
||||||
|
- 'pgpass'
|
||||||
|
- 'split2'
|
||||||
|
- 'xtend'
|
||||||
|
|
||||||
|
# Define layers
|
||||||
|
layers:
|
||||||
|
prisma:
|
||||||
|
path: layers/prisma
|
||||||
|
name: ${self:service}-prisma-layer-${sls:stage}
|
||||||
|
description: Prisma 7 client with pg driver adapter (no binary engines)
|
||||||
|
compatibleRuntimes:
|
||||||
|
- nodejs22.x
|
||||||
|
retain: false
|
||||||
|
|
||||||
package:
|
package:
|
||||||
individually: true
|
individually: true
|
||||||
patterns:
|
patterns:
|
||||||
- '!node_modules/**'
|
- '!node_modules/**'
|
||||||
|
- '!node_modules/@prisma/**'
|
||||||
|
- '!node_modules/.prisma/**'
|
||||||
- '!**/*.test.js'
|
- '!**/*.test.js'
|
||||||
- '!**/*.spec.js'
|
- '!**/*.spec.js'
|
||||||
- '!**/test/**'
|
- '!**/test/**'
|
||||||
@@ -82,13 +136,13 @@ package:
|
|||||||
- '!*.config.js'
|
- '!*.config.js'
|
||||||
- '!.git/**'
|
- '!.git/**'
|
||||||
- '!.github/**'
|
- '!.github/**'
|
||||||
|
|
||||||
# Import function definitions from separate files organized by module
|
# Import function definitions from separate files organized by module
|
||||||
functions:
|
functions:
|
||||||
- ${file(./serverless/functions/host.yml)}
|
- ${file(./serverless/functions/host.yml)}
|
||||||
- ${file(./serverless/functions/minglaradmin.yml)}
|
- ${file(./serverless/functions/minglaradmin.yml)}
|
||||||
- ${file(./serverless/functions/prepopulate.yml)}
|
- ${file(./serverless/functions/prepopulate.yml)}
|
||||||
- ${file(./serverless/functions/pqq.yml)}
|
- ${file(./serverless/functions/pqq.yml)}
|
||||||
|
|
||||||
plugins:
|
plugins:
|
||||||
- serverless-offline
|
- serverless-offline
|
||||||
@@ -253,28 +253,6 @@ submitCompanyDetails:
|
|||||||
- 'src/modules/host/handlers/addCompanyDetails.*'
|
- 'src/modules/host/handlers/addCompanyDetails.*'
|
||||||
- 'src/modules/host/services/**'
|
- 'src/modules/host/services/**'
|
||||||
- 'src/common/**'
|
- 'src/common/**'
|
||||||
- 'node_modules/@prisma/client/**'
|
|
||||||
- 'node_modules/.prisma/client/libquery_engine-rhel-openssl-3.0.x.so.node'
|
|
||||||
# Only include specific AWS SDK modules needed for S3
|
|
||||||
- 'node_modules/@aws-sdk/client-s3/**'
|
|
||||||
- 'node_modules/@aws-sdk/s3-request-presigner/**'
|
|
||||||
- 'node_modules/@aws-sdk/types/**'
|
|
||||||
- 'node_modules/@aws-sdk/middleware-logger/**'
|
|
||||||
- 'node_modules/@aws-sdk/util-utf8-node/**'
|
|
||||||
- 'node_modules/@aws-sdk/util-utf8-browser/**'
|
|
||||||
- 'node_modules/@smithy/**'
|
|
||||||
- 'node_modules/tslib/**'
|
|
||||||
# Remove these large/unnecessary packages:
|
|
||||||
- 'node_modules/fast-xml-parser/**' # Remove if not used
|
|
||||||
- 'node_modules/lambda-multipart-parser/**' # You're using busboy directly
|
|
||||||
- 'node_modules/busboy/**'
|
|
||||||
# Remove these AWS utility packages (included in main SDK):
|
|
||||||
- 'node_modules/@aws-crypto/**'
|
|
||||||
# - 'node_modules/uuid/**' # AWS SDK includes its own
|
|
||||||
# - 'node_modules/@aws/util-uri-escape/**'
|
|
||||||
# - 'node_modules/@aws/util-middleware/**'
|
|
||||||
- 'node_modules/@aws/smithy-client/**'
|
|
||||||
# - 'node_modules/@aws/lambda-invoke-store/**'
|
|
||||||
events:
|
events:
|
||||||
- httpApi:
|
- httpApi:
|
||||||
path: /host/Host_Admin/onboarding/add-company-details
|
path: /host/Host_Admin/onboarding/add-company-details
|
||||||
@@ -291,24 +269,6 @@ submitPQQ_Answer:
|
|||||||
- ${file(./serverless/patterns/base.yml):pattern2}
|
- ${file(./serverless/patterns/base.yml):pattern2}
|
||||||
- ${file(./serverless/patterns/base.yml):pattern3}
|
- ${file(./serverless/patterns/base.yml):pattern3}
|
||||||
- ${file(./serverless/patterns/base.yml):pattern4}
|
- ${file(./serverless/patterns/base.yml):pattern4}
|
||||||
- 'node_modules/@aws-sdk/client-s3/**'
|
|
||||||
- 'node_modules/@aws-sdk/s3-request-presigner/**'
|
|
||||||
- 'node_modules/@aws-sdk/types/**'
|
|
||||||
- 'node_modules/@aws-sdk/middleware-logger/**'
|
|
||||||
- 'node_modules/@aws-sdk/util-utf8-node/**'
|
|
||||||
- 'node_modules/@aws-sdk/util-utf8-browser/**'
|
|
||||||
- 'node_modules/@smithy/**'
|
|
||||||
- 'node_modules/tslib/**'
|
|
||||||
# Remove these large/unnecessary packages:
|
|
||||||
- 'node_modules/fast-xml-parser/**' # Remove if not used
|
|
||||||
- 'node_modules/lambda-multipart-parser/**' # You're using busboy directly
|
|
||||||
- 'node_modules/busboy/**'
|
|
||||||
# Remove these AWS utility packages (included in main SDK):
|
|
||||||
- 'node_modules/@aws-crypto/**'
|
|
||||||
# - 'node_modules/uuid/**' # AWS SDK includes its own
|
|
||||||
# - 'node_modules/@aws/util-uri-escape/**'
|
|
||||||
# - 'node_modules/@aws/util-middleware/**'
|
|
||||||
- 'node_modules/@aws/smithy-client/**'
|
|
||||||
events:
|
events:
|
||||||
- httpApi:
|
- httpApi:
|
||||||
path: /host/Activity_Hub/OnBoarding/submit-pqq-answer
|
path: /host/Activity_Hub/OnBoarding/submit-pqq-answer
|
||||||
|
|||||||
@@ -58,22 +58,6 @@ updateMinglarProfile:
|
|||||||
- ${file(./serverless/patterns/base.yml):pattern2}
|
- ${file(./serverless/patterns/base.yml):pattern2}
|
||||||
- ${file(./serverless/patterns/base.yml):pattern3}
|
- ${file(./serverless/patterns/base.yml):pattern3}
|
||||||
- ${file(./serverless/patterns/base.yml):pattern4}
|
- ${file(./serverless/patterns/base.yml):pattern4}
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern1}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern2}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern3}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern4}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern5}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern6}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern7}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern8}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern9}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern10}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern11}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern12}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern13}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern14}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern15}
|
|
||||||
- ${file(./serverless/patterns/aws-s3.yml):pattern16}
|
|
||||||
events:
|
events:
|
||||||
- httpApi:
|
- httpApi:
|
||||||
path: /minglaradmin/update-profile
|
path: /minglaradmin/update-profile
|
||||||
@@ -422,3 +406,20 @@ getAllPQPDetailsForAM:
|
|||||||
- httpApi:
|
- httpApi:
|
||||||
path: /minglaradmin/hosthub/pqp/pqp-details-for-am/{activityXid}
|
path: /minglaradmin/hosthub/pqp/pqp-details-for-am/{activityXid}
|
||||||
method: get
|
method: get
|
||||||
|
|
||||||
|
|
||||||
|
getSuggestionsForAM:
|
||||||
|
handler: src/modules/minglaradmin/handlers/hosthub/onboarding/showSuggestionToAM.handler
|
||||||
|
memorySize: 384
|
||||||
|
package:
|
||||||
|
patterns:
|
||||||
|
- 'src/modules/minglaradmin/handlers/hosthub/onboarding/showSuggestionToAM**'
|
||||||
|
- 'src/modules/minglaradmin/services/**'
|
||||||
|
- ${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: /minglaradmin/hosthub/onboarding/show-suggestion-to-am/{hostXid}
|
||||||
|
method: get
|
||||||
|
|||||||
@@ -91,4 +91,19 @@ getFrequenciesOfActivity:
|
|||||||
events:
|
events:
|
||||||
- httpApi:
|
- httpApi:
|
||||||
path: /prepopulate/get-all-Frequencies
|
path: /prepopulate/get-all-Frequencies
|
||||||
method: get
|
method: get
|
||||||
|
|
||||||
|
getAddActivityPrePopulate:
|
||||||
|
handler: src/modules/prepopulate/handlers/getAddActivityPrePopulate.handler
|
||||||
|
memorySize: 384
|
||||||
|
package:
|
||||||
|
patterns:
|
||||||
|
- 'src/modules/prepopulate/**'
|
||||||
|
- ${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: /prepopulate/get-add-activity-prepopulate
|
||||||
|
method: get
|
||||||
|
|||||||
@@ -1,6 +1,9 @@
|
|||||||
# Base packaging patterns shared across all functions
|
# Base packaging patterns shared across all functions
|
||||||
pattern1: 'src/common/**'
|
pattern1: 'src/common/**'
|
||||||
pattern2: 'common/**'
|
pattern2: 'common/**'
|
||||||
pattern3: 'node_modules/@prisma/client/**'
|
# REMOVED: Prisma is now provided by Lambda layer - DO NOT include in function packages
|
||||||
pattern4: 'node_modules/.prisma/client/libquery_engine-rhel-openssl-3.0.x.so.node'
|
# pattern3: 'node_modules/@prisma/client/**'
|
||||||
|
# pattern4: 'node_modules/.prisma/client/libquery_engine-rhel-openssl-3.0.x.so.node'
|
||||||
|
pattern3: '!node_modules/@prisma/**'
|
||||||
|
pattern4: '!node_modules/.prisma/**'
|
||||||
pattern5: '!node_modules/.prisma/client/libquery_engine*'
|
pattern5: '!node_modules/.prisma/client/libquery_engine*'
|
||||||
@@ -1,11 +1,29 @@
|
|||||||
import { PrismaClient } from '@prisma/client';
|
import { PrismaClient } from '@prisma/client';
|
||||||
import { PrismaPg } from '@prisma/adapter-pg';
|
import { PrismaPg } from '@prisma/adapter-pg';
|
||||||
|
|
||||||
const adapter = new PrismaPg({ connectionString: process.env.DATABASE_URL });
|
// Singleton pattern for Prisma client - prevents "Too many database connections" error
|
||||||
|
const globalForPrisma = globalThis as unknown as {
|
||||||
|
prisma: PrismaClient | undefined;
|
||||||
|
};
|
||||||
|
|
||||||
export const prisma = new PrismaClient({
|
function createPrismaClient() {
|
||||||
adapter,
|
const adapter = new PrismaPg({ connectionString: process.env.DATABASE_URL });
|
||||||
log: process.env.NODE_ENV === 'dev' ? ['query', 'info', 'warn', 'error'] : ['error'],
|
|
||||||
});
|
return new PrismaClient({
|
||||||
|
adapter,
|
||||||
|
log: process.env.NODE_ENV === 'dev' ? ['query', 'info', 'warn', 'error'] : ['error'],
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
export const prisma = globalForPrisma.prisma ?? createPrismaClient();
|
||||||
|
|
||||||
|
if (process.env.NODE_ENV !== 'production') {
|
||||||
|
globalForPrisma.prisma = prisma;
|
||||||
|
}
|
||||||
|
|
||||||
|
// For serverless environments, always cache the client
|
||||||
|
if (process.env.IS_OFFLINE || process.env.AWS_LAMBDA_FUNCTION_NAME) {
|
||||||
|
globalForPrisma.prisma = prisma;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
5
src/common/database/prisma.lambda.service.ts
Normal file
5
src/common/database/prisma.lambda.service.ts
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
// Re-export the singleton prisma client for Lambda handlers
|
||||||
|
// This ensures all Lambda functions use the same cached connection
|
||||||
|
import { prisma } from './prisma.client';
|
||||||
|
|
||||||
|
export const prismaClient = prisma;
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
import { Global, Module } from '@nestjs/common';
|
import { Global, Module } from '@nestjs/common';
|
||||||
import { PrismaService } from './prisma.service';
|
import { PrismaService } from './prisma.lambda.service';
|
||||||
|
|
||||||
@Global()
|
@Global()
|
||||||
@Module({
|
@Module({
|
||||||
|
|||||||
@@ -1,15 +1,13 @@
|
|||||||
import { Injectable, OnModuleInit, OnModuleDestroy, INestApplication } from '@nestjs/common';
|
import { Injectable, OnModuleInit, OnModuleDestroy } from '@nestjs/common';
|
||||||
import { PrismaClient } from '@prisma/client';
|
import { PrismaClient } from '@prisma/client';
|
||||||
import { PrismaPg } from '@prisma/adapter-pg';
|
import { prisma } from './prisma.client';
|
||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class PrismaService extends PrismaClient implements OnModuleInit, OnModuleDestroy {
|
export class PrismaService extends PrismaClient implements OnModuleInit, OnModuleDestroy {
|
||||||
constructor() {
|
constructor() {
|
||||||
const adapter = new PrismaPg({ connectionString: process.env.DATABASE_URL });
|
super();
|
||||||
super({
|
// Use the singleton instance
|
||||||
adapter,
|
Object.assign(this, prisma);
|
||||||
log: process.env.NODE_ENV === 'dev' ? ['query', 'info', 'warn', 'error'] : ['error'],
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async onModuleInit() {
|
async onModuleInit() {
|
||||||
@@ -19,10 +17,4 @@ export class PrismaService extends PrismaClient implements OnModuleInit, OnModul
|
|||||||
async onModuleDestroy() {
|
async onModuleDestroy() {
|
||||||
await this.$disconnect();
|
await this.$disconnect();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
async enableShutdownHooks(app: INestApplication) {
|
|
||||||
process.on('beforeExit', async () => {
|
|
||||||
await app.close();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|||||||
@@ -49,6 +49,17 @@ export async function verifyHostToken(token: string): Promise<{ id: number; role
|
|||||||
include: { role: true },
|
include: { role: true },
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const latestToken = await prisma.token.findFirst({
|
||||||
|
where: {
|
||||||
|
userXid: userId
|
||||||
|
},
|
||||||
|
orderBy: { id: 'desc' }
|
||||||
|
})
|
||||||
|
|
||||||
|
if (latestToken.isBlackListed == true) {
|
||||||
|
throw new ApiError(401, "This session is expired. Please login.")
|
||||||
|
}
|
||||||
|
|
||||||
if (!user) {
|
if (!user) {
|
||||||
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
||||||
}
|
}
|
||||||
@@ -89,7 +100,7 @@ const verifyCallback = async (
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
const userInfo = await verifyHostToken(token);
|
const userInfo = await verifyHostToken(token);
|
||||||
|
|
||||||
// Attach user to request
|
// Attach user to request
|
||||||
req.user = { id: userInfo.id.toString(), role: userInfo.role };
|
req.user = { id: userInfo.id.toString(), role: userInfo.role };
|
||||||
|
|
||||||
@@ -104,12 +115,12 @@ const verifyCallback = async (
|
|||||||
*/
|
*/
|
||||||
const authForHost =
|
const authForHost =
|
||||||
() =>
|
() =>
|
||||||
async (req: Request, res: Response, next: NextFunction) => {
|
async (req: Request, res: Response, next: NextFunction) => {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
verifyCallback(req, resolve, reject);
|
verifyCallback(req, resolve, reject);
|
||||||
})
|
})
|
||||||
.then(() => next())
|
.then(() => next())
|
||||||
.catch((err) => next(err));
|
.catch((err) => next(err));
|
||||||
};
|
};
|
||||||
|
|
||||||
export default authForHost;
|
export default authForHost;
|
||||||
|
|||||||
@@ -49,6 +49,17 @@ export async function verifyMinglarAdminToken(token: string): Promise<{ id: numb
|
|||||||
include: { role: true },
|
include: { role: true },
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const latestToken = await prisma.token.findFirst({
|
||||||
|
where: {
|
||||||
|
userXid: userId
|
||||||
|
},
|
||||||
|
orderBy: { id: 'desc' }
|
||||||
|
})
|
||||||
|
|
||||||
|
if (latestToken.isBlackListed == true) {
|
||||||
|
throw new ApiError(401, "This session is expired. Please login.")
|
||||||
|
}
|
||||||
|
|
||||||
if (!user) {
|
if (!user) {
|
||||||
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
||||||
}
|
}
|
||||||
@@ -62,7 +73,7 @@ export async function verifyMinglarAdminToken(token: string): Promise<{ id: numb
|
|||||||
if (![ROLE.MINGLAR_ADMIN, ROLE.CO_ADMIN, ROLE.ACCOUNT_MANAGER].includes(user.roleXid)) {
|
if (![ROLE.MINGLAR_ADMIN, ROLE.CO_ADMIN, ROLE.ACCOUNT_MANAGER].includes(user.roleXid)) {
|
||||||
throw new ApiError(httpStatus.FORBIDDEN, 'Access denied.');
|
throw new ApiError(httpStatus.FORBIDDEN, 'Access denied.');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
return { id: user.id, role: user.role?.roleName };
|
return { id: user.id, role: user.role?.roleName };
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
@@ -90,7 +101,7 @@ const verifyCallback = async (
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
const userInfo = await verifyMinglarAdminToken(token);
|
const userInfo = await verifyMinglarAdminToken(token);
|
||||||
|
|
||||||
// Attach user to request
|
// Attach user to request
|
||||||
req.user = { id: userInfo.id.toString(), role: userInfo.role };
|
req.user = { id: userInfo.id.toString(), role: userInfo.role };
|
||||||
|
|
||||||
@@ -105,12 +116,12 @@ const verifyCallback = async (
|
|||||||
*/
|
*/
|
||||||
const authForHost =
|
const authForHost =
|
||||||
() =>
|
() =>
|
||||||
async (req: Request, res: Response, next: NextFunction) => {
|
async (req: Request, res: Response, next: NextFunction) => {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
verifyCallback(req, resolve, reject);
|
verifyCallback(req, resolve, reject);
|
||||||
})
|
})
|
||||||
.then(() => next())
|
.then(() => next())
|
||||||
.catch((err) => next(err));
|
.catch((err) => next(err));
|
||||||
};
|
};
|
||||||
|
|
||||||
export default authForHost;
|
export default authForHost;
|
||||||
|
|||||||
@@ -51,6 +51,17 @@ export async function verifyMinglarAdminHostToken(token: string): Promise<{ id:
|
|||||||
include: { role: true },
|
include: { role: true },
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const latestToken = await prisma.token.findFirst({
|
||||||
|
where: {
|
||||||
|
userXid: userId
|
||||||
|
},
|
||||||
|
orderBy: { id: 'desc' }
|
||||||
|
})
|
||||||
|
|
||||||
|
if (latestToken.isBlackListed == true) {
|
||||||
|
throw new ApiError(401, "This session is expired. Please login.")
|
||||||
|
}
|
||||||
|
|
||||||
if (!user) {
|
if (!user) {
|
||||||
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -49,6 +49,17 @@ export async function verifyOnlyMinglarAdminToken(token: string): Promise<{ id:
|
|||||||
include: { role: true },
|
include: { role: true },
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const latestToken = await prisma.token.findFirst({
|
||||||
|
where: {
|
||||||
|
userXid: userId
|
||||||
|
},
|
||||||
|
orderBy: { id: 'desc' }
|
||||||
|
})
|
||||||
|
|
||||||
|
if (latestToken.isBlackListed == true) {
|
||||||
|
throw new ApiError(401, "This session is expired. Please login.")
|
||||||
|
}
|
||||||
|
|
||||||
if (!user) {
|
if (!user) {
|
||||||
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
||||||
}
|
}
|
||||||
@@ -62,7 +73,7 @@ export async function verifyOnlyMinglarAdminToken(token: string): Promise<{ id:
|
|||||||
if (user.roleXid !== ROLE.MINGLAR_ADMIN) {
|
if (user.roleXid !== ROLE.MINGLAR_ADMIN) {
|
||||||
throw new ApiError(httpStatus.FORBIDDEN, 'Access denied.');
|
throw new ApiError(httpStatus.FORBIDDEN, 'Access denied.');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
return { id: user.id, role: user.role?.roleName };
|
return { id: user.id, role: user.role?.roleName };
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
@@ -90,7 +101,7 @@ const verifyCallback = async (
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
||||||
|
|
||||||
// Attach user to request
|
// Attach user to request
|
||||||
req.user = { id: userInfo.id.toString(), role: userInfo.role };
|
req.user = { id: userInfo.id.toString(), role: userInfo.role };
|
||||||
|
|
||||||
@@ -105,12 +116,12 @@ const verifyCallback = async (
|
|||||||
*/
|
*/
|
||||||
const authForHost =
|
const authForHost =
|
||||||
() =>
|
() =>
|
||||||
async (req: Request, res: Response, next: NextFunction) => {
|
async (req: Request, res: Response, next: NextFunction) => {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
verifyCallback(req, resolve, reject);
|
verifyCallback(req, resolve, reject);
|
||||||
})
|
})
|
||||||
.then(() => next())
|
.then(() => next())
|
||||||
.catch((err) => next(err));
|
.catch((err) => next(err));
|
||||||
};
|
};
|
||||||
|
|
||||||
export default authForHost;
|
export default authForHost;
|
||||||
|
|||||||
@@ -50,6 +50,17 @@ export async function verifyUserToken(token: string): Promise<{ id: number; role
|
|||||||
include: { role: true },
|
include: { role: true },
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const latestToken = await prisma.token.findFirst({
|
||||||
|
where: {
|
||||||
|
userXid: userId
|
||||||
|
},
|
||||||
|
orderBy: { id: 'desc' }
|
||||||
|
})
|
||||||
|
|
||||||
|
if (latestToken.isBlackListed == true) {
|
||||||
|
throw new ApiError(401, "This session is expired. Please login.")
|
||||||
|
}
|
||||||
|
|
||||||
if (!user) {
|
if (!user) {
|
||||||
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
throw new ApiError(httpStatus.UNAUTHORIZED, 'User not found');
|
||||||
}
|
}
|
||||||
@@ -90,7 +101,7 @@ const verifyCallback = async (
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
const userInfo = await verifyUserToken(token);
|
const userInfo = await verifyUserToken(token);
|
||||||
|
|
||||||
// Attach user to request
|
// Attach user to request
|
||||||
req.user = { id: userInfo.id.toString(), role: userInfo.role };
|
req.user = { id: userInfo.id.toString(), role: userInfo.role };
|
||||||
|
|
||||||
@@ -105,12 +116,12 @@ const verifyCallback = async (
|
|||||||
*/
|
*/
|
||||||
const authForHost =
|
const authForHost =
|
||||||
() =>
|
() =>
|
||||||
async (req: Request, res: Response, next: NextFunction) => {
|
async (req: Request, res: Response, next: NextFunction) => {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
verifyCallback(req, resolve, reject);
|
verifyCallback(req, resolve, reject);
|
||||||
})
|
})
|
||||||
.then(() => next())
|
.then(() => next())
|
||||||
.catch((err) => next(err));
|
.catch((err) => next(err));
|
||||||
};
|
};
|
||||||
|
|
||||||
export default authForHost;
|
export default authForHost;
|
||||||
|
|||||||
@@ -12,7 +12,6 @@ export interface OtpResult {
|
|||||||
export async function resendOtpHelper(
|
export async function resendOtpHelper(
|
||||||
prisma: any,
|
prisma: any,
|
||||||
userId: number,
|
userId: number,
|
||||||
email: string,
|
|
||||||
emailPurpose: "Register" | "Login" | "ForgotPassword",
|
emailPurpose: "Register" | "Login" | "ForgotPassword",
|
||||||
otpLength: 4 | 6 = 4,
|
otpLength: 4 | 6 = 4,
|
||||||
expiryMinutes: number = 5
|
expiryMinutes: number = 5
|
||||||
|
|||||||
@@ -2,8 +2,8 @@ import { z } from "zod";
|
|||||||
|
|
||||||
export const parentCompanySchema = z.object({
|
export const parentCompanySchema = z.object({
|
||||||
companyName: z.string()
|
companyName: z.string()
|
||||||
.min(1, "Parent company name is required")
|
.max(100, "Parent company name cannot exceed 100 characters")
|
||||||
.max(100, "Parent company name cannot exceed 100 characters"),
|
.optional(),
|
||||||
|
|
||||||
address1: z.string()
|
address1: z.string()
|
||||||
.max(150, "Address1 cannot exceed 150 characters")
|
.max(150, "Address1 cannot exceed 150 characters")
|
||||||
@@ -25,8 +25,6 @@ export const parentCompanySchema = z.object({
|
|||||||
.max(400, "Logo path cannot exceed 400 characters")
|
.max(400, "Logo path cannot exceed 400 characters")
|
||||||
.optional(),
|
.optional(),
|
||||||
|
|
||||||
isSubsidairy: z.boolean().optional(),
|
|
||||||
|
|
||||||
registrationNumber: z.string()
|
registrationNumber: z.string()
|
||||||
.max(30, "Registration number cannot exceed 30 characters")
|
.max(30, "Registration number cannot exceed 30 characters")
|
||||||
.optional(),
|
.optional(),
|
||||||
@@ -46,7 +44,7 @@ export const parentCompanySchema = z.object({
|
|||||||
}),
|
}),
|
||||||
|
|
||||||
companyTypeXid: z.number()
|
companyTypeXid: z.number()
|
||||||
.min(1, "Company type XID is required"),
|
.optional(),
|
||||||
|
|
||||||
websiteUrl: z.string().nullable().optional(),
|
websiteUrl: z.string().nullable().optional(),
|
||||||
instagramUrl: z.string().nullable().optional(),
|
instagramUrl: z.string().nullable().optional(),
|
||||||
|
|||||||
@@ -81,6 +81,9 @@ const envVarsSchema = yup
|
|||||||
DB_PORT: yup.number().default(3306).required('DB Port is required'),
|
DB_PORT: yup.number().default(3306).required('DB Port is required'),
|
||||||
//OTP Bypass
|
//OTP Bypass
|
||||||
BYPASS_OTP: yup.boolean().default(false).required('Bypass OTP is required'),
|
BYPASS_OTP: yup.boolean().default(false).required('Bypass OTP is required'),
|
||||||
|
// Email links
|
||||||
|
AM_INVITATION_LINK: yup.string().required('Link to send in AM invitation mail is required'),
|
||||||
|
HOST_LINK: yup.string().required('Link to host panel is required')
|
||||||
})
|
})
|
||||||
.noUnknown(true);
|
.noUnknown(true);
|
||||||
|
|
||||||
@@ -158,6 +161,8 @@ function getConfig() {
|
|||||||
//Minglar admin
|
//Minglar admin
|
||||||
MinglarAdminEmail: envVars.MINGLAR_ADMIN_EMAIL,
|
MinglarAdminEmail: envVars.MINGLAR_ADMIN_EMAIL,
|
||||||
MinglarAdminName: envVars.MINGLAR_ADMIN_NAME,
|
MinglarAdminName: envVars.MINGLAR_ADMIN_NAME,
|
||||||
|
AM_INVITATION_LINK: envVars.AM_INVITATION_LINK,
|
||||||
|
HOST_LINK: envVars.HOST_LINK,
|
||||||
// oneSignal: {
|
// oneSignal: {
|
||||||
// appID: envVars.ONESIGNAL_APPID,
|
// appID: envVars.ONESIGNAL_APPID,
|
||||||
// restApiKey: envVars.ONESIGNAL_REST_APIKEY,
|
// restApiKey: envVars.ONESIGNAL_REST_APIKEY,
|
||||||
|
|||||||
@@ -4,13 +4,12 @@ import {
|
|||||||
APIGatewayProxyResult,
|
APIGatewayProxyResult,
|
||||||
Context,
|
Context,
|
||||||
} from 'aws-lambda';
|
} from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(
|
export const handler = safeHandler(
|
||||||
async (
|
async (
|
||||||
|
|||||||
@@ -1,14 +1,13 @@
|
|||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
import { PrePopulateService } from '../../../../prepopulate/services/prepopulate.service';
|
import { PrePopulateService } from '../../../../prepopulate/services/prepopulate.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
const prePopulateService = new PrePopulateService(prismaClient);
|
||||||
const prePopulateService = new PrePopulateService(prismaService);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add suggestion handler for host applications
|
* Add suggestion handler for host applications
|
||||||
|
|||||||
@@ -1,14 +1,13 @@
|
|||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
||||||
|
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
import { verifyMinglarAdminHostToken } from '../../../../../common/middlewares/jwt/authForMinglarAdminHost';
|
import { verifyMinglarAdminHostToken } from '../../../../../common/middlewares/jwt/authForMinglarAdminHost';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -3,14 +3,13 @@ import { APIGatewayProxyEvent, APIGatewayProxyResult } from 'aws-lambda';
|
|||||||
import AWS from 'aws-sdk';
|
import AWS from 'aws-sdk';
|
||||||
import Busboy from 'busboy';
|
import Busboy from 'busboy';
|
||||||
import crypto from 'crypto';
|
import crypto from 'crypto';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
|
||||||
const prisma = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prisma);
|
|
||||||
|
|
||||||
const s3 = new AWS.S3({ region: config.aws.region });
|
const s3 = new AWS.S3({ region: config.aws.region });
|
||||||
|
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyMinglarAdminHostToken } from '../../../../../common/middlewares/jwt/authForMinglarAdminHost';
|
import { verifyMinglarAdminHostToken } from '../../../../../common/middlewares/jwt/authForMinglarAdminHost';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
context?: Context
|
context?: Context
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
context?: Context
|
context?: Context
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -3,14 +3,13 @@ import { APIGatewayProxyEvent, APIGatewayProxyResult } from 'aws-lambda';
|
|||||||
import AWS from 'aws-sdk';
|
import AWS from 'aws-sdk';
|
||||||
import Busboy from 'busboy';
|
import Busboy from 'busboy';
|
||||||
import crypto from 'crypto';
|
import crypto from 'crypto';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
|
||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
|
|
||||||
const prisma = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prisma);
|
|
||||||
|
|
||||||
const s3 = new AWS.S3({ region: config.aws.region });
|
const s3 = new AWS.S3({ region: config.aws.region });
|
||||||
|
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
|
||||||
const prisma = new PrismaService();
|
const pqqService = new HostService(prismaClient);
|
||||||
const pqqService = new HostService(prisma);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (event: APIGatewayProxyEvent): Promise<APIGatewayProxyResult> => {
|
export const handler = safeHandler(async (event: APIGatewayProxyEvent): Promise<APIGatewayProxyResult> => {
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -3,14 +3,13 @@ import { APIGatewayProxyEvent, APIGatewayProxyResult } from 'aws-lambda';
|
|||||||
import AWS from 'aws-sdk';
|
import AWS from 'aws-sdk';
|
||||||
import Busboy from 'busboy';
|
import Busboy from 'busboy';
|
||||||
import crypto from 'crypto';
|
import crypto from 'crypto';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
|
||||||
const prisma = new PrismaService();
|
const pqqService = new HostService(prismaClient);
|
||||||
const pqqService = new HostService(prisma);
|
|
||||||
|
|
||||||
const s3 = new AWS.S3({ region: config.aws.region });
|
const s3 = new AWS.S3({ region: config.aws.region });
|
||||||
|
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add suggestion handler for host applications
|
* Add suggestion handler for host applications
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,15 +1,13 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
import { TokenService } from '../../../services/token.service';
|
import { TokenService } from '../../../services/token.service';
|
||||||
import { GetHostLoginResponseDTO } from '../../../dto/host.dto';
|
import { GetHostLoginResponseDTO } from '../../../dto/host.dto';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import * as bcrypt from 'bcryptjs';
|
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
const tokenService = new TokenService(prismaClient);
|
||||||
const tokenService = new TokenService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
@@ -17,7 +15,7 @@ export const handler = safeHandler(async (
|
|||||||
): Promise<APIGatewayProxyResult> => {
|
): Promise<APIGatewayProxyResult> => {
|
||||||
// Parse request body
|
// Parse request body
|
||||||
let body: { emailAddress?: string; userPassword?: string };
|
let body: { emailAddress?: string; userPassword?: string };
|
||||||
|
|
||||||
try {
|
try {
|
||||||
body = event.body ? JSON.parse(event.body) : {};
|
body = event.body ? JSON.parse(event.body) : {};
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
@@ -30,7 +28,9 @@ export const handler = safeHandler(async (
|
|||||||
throw new ApiError(400, 'Email and password are required');
|
throw new ApiError(400, 'Email and password are required');
|
||||||
}
|
}
|
||||||
|
|
||||||
const loginForHost = await hostService.loginForHost(emailAddress, userPassword);
|
const emailToLowerCase = emailAddress.toLowerCase()
|
||||||
|
|
||||||
|
const loginForHost = await hostService.loginForHost(emailToLowerCase, userPassword);
|
||||||
|
|
||||||
if (!loginForHost) {
|
if (!loginForHost) {
|
||||||
throw new ApiError(400, 'Failed to login');
|
throw new ApiError(400, 'Failed to login');
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { MinglarService } from '../../../../minglaradmin/services/minglar.service';
|
import { MinglarService } from '../../../../minglaradmin/services/minglar.service';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get suggestions handler
|
* Get suggestions handler
|
||||||
|
|||||||
@@ -1,15 +1,15 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import * as bcrypt from 'bcryptjs';
|
import * as bcrypt from 'bcryptjs';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { ROLE } from '../../../../../common/utils/constants/common.constant';
|
import { ROLE } from '../../../../../common/utils/constants/common.constant';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { encryptUserId } from '../../../../../common/utils/helper/CodeGenerator';
|
import { encryptUserId } from '../../../../../common/utils/helper/CodeGenerator';
|
||||||
import { OtpGeneratorSixDigit } from '../../../../../common/utils/helper/OtpGenerator';
|
import { OtpGeneratorSixDigit } from '../../../../../common/utils/helper/OtpGenerator';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
|
import { sendOtpEmailForHost } from '@/modules/host/services/sendOTPEmail.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
export async function generateHostRefNumber(tx: any) {
|
export async function generateHostRefNumber(tx: any) {
|
||||||
const lastrecord = await tx.user.findFirst({
|
const lastrecord = await tx.user.findFirst({
|
||||||
@@ -45,10 +45,12 @@ export const handler = safeHandler(async (
|
|||||||
throw new ApiError(400, 'Email is required');
|
throw new ApiError(400, 'Email is required');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const emailToLowerCase = email.toLowerCase()
|
||||||
|
|
||||||
// Use a single transaction for user creation/lookup and OTP storage
|
// Use a single transaction for user creation/lookup and OTP storage
|
||||||
const transactionResult = await prismaService.$transaction(async (tx) => {
|
const transactionResult = await prismaClient.$transaction(async (tx) => {
|
||||||
const user = await tx.user.findUnique({
|
const user = await tx.user.findUnique({
|
||||||
where: { emailAddress: email },
|
where: { emailAddress: emailToLowerCase },
|
||||||
select: { emailAddress: true, id: true, userPassword: true },
|
select: { emailAddress: true, id: true, userPassword: true },
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -66,7 +68,7 @@ export const handler = safeHandler(async (
|
|||||||
} else {
|
} else {
|
||||||
// create new user record within the transaction
|
// create new user record within the transaction
|
||||||
newUserLocal = await tx.user.create({
|
newUserLocal = await tx.user.create({
|
||||||
data: { emailAddress: email, roleXid: ROLE.HOST, userRefNumber: referenceNumber },
|
data: { emailAddress: emailToLowerCase, roleXid: ROLE.HOST, userRefNumber: referenceNumber },
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -101,7 +103,7 @@ export const handler = safeHandler(async (
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Send OTP email outside the DB transaction
|
// Send OTP email outside the DB transaction
|
||||||
// await sendOtpEmailForHost(transactionResult.newUser.emailAddress, transactionResult.otp);
|
await sendOtpEmailForHost(transactionResult.newUser.emailAddress, transactionResult.otp);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
statusCode: 200,
|
statusCode: 200,
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ import config from '../../../../../config/config';
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult } from 'aws-lambda';
|
||||||
import AWS from 'aws-sdk';
|
import AWS from 'aws-sdk';
|
||||||
import Busboy from 'busboy';
|
import Busboy from 'busboy';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
@@ -15,8 +15,17 @@ import {
|
|||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
import { sendEmailToAM, sendEmailToMinglarAdmin } from '../../../services/sendHostResubmitEmailToAM.service';
|
import { sendEmailToAM, sendEmailToMinglarAdmin } from '../../../services/sendHostResubmitEmailToAM.service';
|
||||||
|
|
||||||
const prisma = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prisma);
|
|
||||||
|
function getExtensionFromMime(mimeType: string) {
|
||||||
|
const map: Record<string, string> = {
|
||||||
|
'image/jpeg': 'jpg',
|
||||||
|
'image/png': 'png',
|
||||||
|
'application/pdf': 'pdf',
|
||||||
|
'image/webp': 'webp',
|
||||||
|
};
|
||||||
|
return map[mimeType] || 'bin';
|
||||||
|
}
|
||||||
|
|
||||||
const s3 = new AWS.S3({
|
const s3 = new AWS.S3({
|
||||||
region: config.aws.region,
|
region: config.aws.region,
|
||||||
@@ -150,13 +159,22 @@ export const handler = safeHandler(async (event: APIGatewayProxyEvent): Promise<
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (
|
||||||
|
companyDetailsRaw.parentCompany &&
|
||||||
|
Object.values(companyDetailsRaw.parentCompany).every(
|
||||||
|
(v) => v === undefined || v === null
|
||||||
|
)
|
||||||
|
) {
|
||||||
|
companyDetailsRaw.parentCompany = null;
|
||||||
|
}
|
||||||
|
|
||||||
/** 6) Profile update if provided */
|
/** 6) Profile update if provided */
|
||||||
if (fields.userProfile) {
|
if (fields.userProfile) {
|
||||||
const userProfileRaw = normalizeJsonField(fields, 'userProfile');
|
const userProfileRaw = normalizeJsonField(fields, 'userProfile');
|
||||||
if (userProfileRaw) {
|
if (userProfileRaw) {
|
||||||
const { firstName, lastName, mobileNumber } = userProfileRaw;
|
const { firstName, lastName, mobileNumber } = userProfileRaw;
|
||||||
|
|
||||||
await prisma.user.update({
|
await prismaClient.user.update({
|
||||||
where: { id: userInfo.id },
|
where: { id: userInfo.id },
|
||||||
data: {
|
data: {
|
||||||
...(firstName && { firstName }),
|
...(firstName && { firstName }),
|
||||||
@@ -250,7 +268,7 @@ export const handler = safeHandler(async (event: APIGatewayProxyEvent): Promise<
|
|||||||
await deleteFromS3(s3Key);
|
await deleteFromS3(s3Key);
|
||||||
|
|
||||||
// Delete from DB
|
// Delete from DB
|
||||||
await prisma.hostDocuments.delete({
|
await prismaClient.hostDocuments.delete({
|
||||||
where: { id }
|
where: { id }
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -277,7 +295,7 @@ export const handler = safeHandler(async (event: APIGatewayProxyEvent): Promise<
|
|||||||
await deleteFromS3(s3Key);
|
await deleteFromS3(s3Key);
|
||||||
|
|
||||||
// Delete DB
|
// Delete DB
|
||||||
await prisma.hostParenetDocuments.delete({
|
await prismaClient.hostParenetDocuments.delete({
|
||||||
where: { id }
|
where: { id }
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -285,11 +303,10 @@ export const handler = safeHandler(async (event: APIGatewayProxyEvent): Promise<
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/** 11) UPLOAD DOCUMENTS */
|
/** 11) UPLOAD DOCUMENTS */
|
||||||
async function uploadToS3(buffer, mimeType, originalName, folderType, documentTypeXid?, fieldName?) {
|
async function uploadToS3(buffer, mimeType, originalName, folderType, documentTypeXid?, fieldName?) {
|
||||||
const ext = originalName.split('.').pop() || 'jpg';
|
// const ext = originalName.split('.').pop() || 'jpg';
|
||||||
|
const ext = getExtensionFromMime(mimeType);
|
||||||
|
|
||||||
let s3Key = '';
|
let s3Key = '';
|
||||||
|
|
||||||
@@ -363,31 +380,67 @@ export const handler = safeHandler(async (event: APIGatewayProxyEvent): Promise<
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** UPLOAD LOGO (if provided) */
|
/** UPLOAD LOGO (if provided) */
|
||||||
const logoFile = files.find((f) => f.fieldName === 'companyLogo' || f.fieldName === 'companyLogoFile');
|
const logoFile = files.find(
|
||||||
if (logoFile) {
|
(f) => f.fieldName === 'companyLogo' || f.fieldName === 'companyLogoFile'
|
||||||
const logoUrl = await uploadToS3(logoFile.buffer, logoFile.mimeType, logoFile.fileName, 'logo');
|
);
|
||||||
|
|
||||||
|
if (logoFile && logoFile.buffer && logoFile.fileName) {
|
||||||
|
const logoUrl = await uploadToS3(
|
||||||
|
logoFile.buffer,
|
||||||
|
logoFile.mimeType,
|
||||||
|
logoFile.fileName,
|
||||||
|
'logo'
|
||||||
|
);
|
||||||
parsedCompany.logoPath = logoUrl;
|
parsedCompany.logoPath = logoUrl;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** UPLOAD PARENT COMPANY LOGO (if provided) */
|
/** UPLOAD PARENT COMPANY LOGO (if provided) */
|
||||||
const parentLogoFile = files.find((f) => f.fieldName === 'parentCompanyLogo');
|
const parentLogoFile = files.find(
|
||||||
if (parentLogoFile) {
|
(f) => f.fieldName === 'parentCompanyLogo'
|
||||||
|
);
|
||||||
|
|
||||||
|
if (parentLogoFile && parentLogoFile.buffer && parentLogoFile.mimeType) {
|
||||||
|
// 🔒 Only upload when an actual file is present
|
||||||
const parentLogoUrl = await uploadToS3(
|
const parentLogoUrl = await uploadToS3(
|
||||||
parentLogoFile.buffer,
|
parentLogoFile.buffer,
|
||||||
parentLogoFile.mimeType,
|
parentLogoFile.mimeType,
|
||||||
parentLogoFile.fileName,
|
parentLogoFile.fileName, // safe here because it's a real file
|
||||||
'parent_company_logo',
|
'parent_company_logo',
|
||||||
);
|
);
|
||||||
|
|
||||||
if (parsedParentCompany) {
|
if (parsedParentCompany) {
|
||||||
parsedParentCompany.logoPath = parentLogoUrl;
|
parsedParentCompany.logoPath = parentLogoUrl;
|
||||||
} else {
|
} else {
|
||||||
// if no parent object exists yet (drafts or other flows), attach it safely
|
parsedParentCompany = {
|
||||||
parsedParentCompany = parsedParentCompany || {};
|
logoPath: parentLogoUrl,
|
||||||
parsedParentCompany.logoPath = parentLogoUrl;
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (parsedCompany.cityXid) {
|
||||||
|
const city = await prismaClient.cities.findUnique({
|
||||||
|
where: { id: Number(parsedCompany.cityXid) }
|
||||||
|
});
|
||||||
|
if (!city) {
|
||||||
|
throw new ApiError(400, `City with ID ${parsedCompany.cityXid} not found`);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!parsedCompany.isSubsidairy) {
|
||||||
|
const parentDocuments = await hostService.getParentDocumentsByHostId(userInfo.id);
|
||||||
|
if (parentDocuments.length > 0) {
|
||||||
|
for (const doc of parentDocuments) {
|
||||||
|
try {
|
||||||
|
const s3Key = getS3KeyFromUrl(doc.filePath);
|
||||||
|
await deleteFromS3(s3Key);
|
||||||
|
} catch (e) {
|
||||||
|
console.error("S3 delete failed:", doc.filePath, e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
await hostService.deleteExistingParentRecords(userInfo.id)
|
||||||
|
}
|
||||||
|
|
||||||
/** 12) SAVE / UPDATE HOST ENTRY */
|
/** 12) SAVE / UPDATE HOST ENTRY */
|
||||||
const createdOrUpdated = await hostService.addOrUpdateCompanyDetails(
|
const createdOrUpdated = await hostService.addOrUpdateCompanyDetails(
|
||||||
userInfo.id,
|
userInfo.id,
|
||||||
|
|||||||
@@ -1,13 +1,12 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../../../common/middlewares/jwt/authForHost';
|
||||||
import { hostBankDetailsSchema } from '../../../../../common/utils/validation/host/addPaymentDetails.validation';
|
import { hostBankDetailsSchema } from '../../../../../common/utils/validation/host/addPaymentDetails.validation';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
@@ -44,7 +43,7 @@ export const handler = safeHandler(async (
|
|||||||
// ✅ Validate payload using Zod
|
// ✅ Validate payload using Zod
|
||||||
const validationResult = hostBankDetailsSchema.safeParse({
|
const validationResult = hostBankDetailsSchema.safeParse({
|
||||||
...(body as object),
|
...(body as object),
|
||||||
hostXid: host.id, // inject hostId from token (not from user input)
|
hostXid: host.host.id, // inject hostId from token (not from user input)
|
||||||
});
|
});
|
||||||
|
|
||||||
if (!validationResult.success) {
|
if (!validationResult.success) {
|
||||||
|
|||||||
@@ -1,13 +1,12 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { HostService } from '../../../services/host.service';
|
import { HostService } from '../../../services/host.service';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { TokenService } from '../../../services/token.service';
|
import { TokenService } from '../../../services/token.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
const tokenService = new TokenService(prismaClient);
|
||||||
const tokenService = new TokenService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
@@ -28,8 +27,10 @@ export const handler = safeHandler(async (
|
|||||||
throw new ApiError(400, 'Email and OTP are required');
|
throw new ApiError(400, 'Email and OTP are required');
|
||||||
}
|
}
|
||||||
|
|
||||||
await hostService.verifyHostOtp(email, otp);
|
const emailToLowerCase = email.toLowerCase();
|
||||||
const user = await hostService.getHostByEmail(email);
|
|
||||||
|
await hostService.verifyHostOtp(emailToLowerCase, otp);
|
||||||
|
const user = await hostService.getHostByEmail(emailToLowerCase);
|
||||||
const generateTokenForHost = await tokenService.generateAuthToken(
|
const generateTokenForHost = await tokenService.generateAuthToken(
|
||||||
user.id
|
user.id
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { verifyHostToken } from '../../../common/middlewares/jwt/authForHost';
|
import { verifyHostToken } from '../../../common/middlewares/jwt/authForHost';
|
||||||
import { HostService } from '../services/host.service';
|
import { HostService } from '../services/host.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
context?: Context
|
context?: Context
|
||||||
@@ -28,10 +27,6 @@ export const handler = safeHandler(async (
|
|||||||
// Fetch user with their HostHeader stepper info
|
// Fetch user with their HostHeader stepper info
|
||||||
const host = await hostService.getHostIdByUserXid(userId);
|
const host = await hostService.getHostIdByUserXid(userId);
|
||||||
|
|
||||||
if (!host) {
|
|
||||||
throw new ApiError(404, 'Host record not found');
|
|
||||||
}
|
|
||||||
|
|
||||||
return {
|
return {
|
||||||
statusCode: 200,
|
statusCode: 200,
|
||||||
headers: {
|
headers: {
|
||||||
@@ -42,7 +37,8 @@ export const handler = safeHandler(async (
|
|||||||
success: true,
|
success: true,
|
||||||
message: 'Stepper information retrieved successfully',
|
message: 'Stepper information retrieved successfully',
|
||||||
data: {
|
data: {
|
||||||
stepper: host.stepper,
|
stepper: host?.host?.stepper || null,
|
||||||
|
emailAddress: host.user?.emailAddress || null,
|
||||||
},
|
},
|
||||||
}),
|
}),
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { HostService } from '../services/host.service';
|
import { HostService } from '../services/host.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const hostService = new HostService(prismaClient);
|
||||||
const hostService = new HostService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
@@ -14,7 +13,7 @@ export const handler = safeHandler(async (
|
|||||||
): Promise<APIGatewayProxyResult> => {
|
): Promise<APIGatewayProxyResult> => {
|
||||||
// Get host ID from path parameters
|
// Get host ID from path parameters
|
||||||
const token = event.headers['x-auth-token'] || event.headers['X-Auth-Token']
|
const token = event.headers['x-auth-token'] || event.headers['X-Auth-Token']
|
||||||
if(!token) {
|
if (!token) {
|
||||||
throw new ApiError(400, 'This is a protected route. Please provide a valid token.');
|
throw new ApiError(400, 'This is a protected route. Please provide a valid token.');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaClient } from '@prisma/client';
|
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
|
|
||||||
const prisma = new PrismaClient();
|
const prisma = prismaClient;
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent
|
event: APIGatewayProxyEvent
|
||||||
@@ -11,7 +11,6 @@ export const handler = safeHandler(async (
|
|||||||
const result = await prisma.hostHeader.findMany({
|
const result = await prisma.hostHeader.findMany({
|
||||||
select: {
|
select: {
|
||||||
hostParent: true,
|
hostParent: true,
|
||||||
hostRefNumber: true,
|
|
||||||
hostStatusDisplay: true,
|
hostStatusDisplay: true,
|
||||||
accountManager: true,
|
accountManager: true,
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -1,11 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult } from "aws-lambda";
|
import { APIGatewayProxyEvent, APIGatewayProxyResult } from "aws-lambda";
|
||||||
import { PrismaService } from "../../../common/database/prisma.service";
|
import { prismaClient } from "../../../common/database/prisma.lambda.service";
|
||||||
import { safeHandler } from "../../../common/utils/handlers/safeHandler";
|
import { safeHandler } from "../../../common/utils/handlers/safeHandler";
|
||||||
import ApiError from "../../../common/utils/helper/ApiError";
|
import ApiError from "../../../common/utils/helper/ApiError";
|
||||||
import { resendOtpHelper } from "../../../common/utils/helper/resendOtpHelper";
|
import { resendOtpHelper } from "../../../common/utils/helper/resendOtpHelper";
|
||||||
import { resendOtpEmail } from "../services/resendOTPEmail.service";
|
import { resendOtpEmail } from "../services/resendOTPEmail.service";
|
||||||
|
|
||||||
const prisma = new PrismaService();
|
const prisma = prismaClient;
|
||||||
|
|
||||||
// allowed purposes
|
// allowed purposes
|
||||||
const ALLOWED_PURPOSES = ["Register", "Login", "ForgotPassword"] as const;
|
const ALLOWED_PURPOSES = ["Register", "Login", "ForgotPassword"] as const;
|
||||||
@@ -41,9 +41,11 @@ export const handler = safeHandler(
|
|||||||
const email = (body.email || "").trim();
|
const email = (body.email || "").trim();
|
||||||
if (!email) throw new ApiError(400, "Email is required");
|
if (!email) throw new ApiError(400, "Email is required");
|
||||||
|
|
||||||
|
const emailToLowerCase = email.toLowerCase();
|
||||||
|
|
||||||
// find user (you can adapt the isActive / userStatus checks per your rules)
|
// find user (you can adapt the isActive / userStatus checks per your rules)
|
||||||
const user = await prisma.user.findUnique({
|
const user = await prisma.user.findUnique({
|
||||||
where: { emailAddress: email, isActive: true },
|
where: { emailAddress: emailToLowerCase, isActive: true },
|
||||||
select: { id: true, emailAddress: true, role: true },
|
select: { id: true, emailAddress: true, role: true },
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -56,7 +58,6 @@ export const handler = safeHandler(
|
|||||||
const otpResult = await resendOtpHelper(
|
const otpResult = await resendOtpHelper(
|
||||||
prisma,
|
prisma,
|
||||||
user.id,
|
user.id,
|
||||||
user.emailAddress,
|
|
||||||
purpose,
|
purpose,
|
||||||
6, // 6-digit OTP
|
6, // 6-digit OTP
|
||||||
5 // expires in 5 minutes
|
5 // expires in 5 minutes
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
// src/modules/host/services/host.service.ts
|
// src/modules/host/services/host.service.ts
|
||||||
import { Injectable } from '@nestjs/common';
|
import { Injectable } from '@nestjs/common';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
|
||||||
import {
|
import {
|
||||||
AddPaymentDetailsDTO,
|
AddPaymentDetailsDTO,
|
||||||
CreateHostDto,
|
CreateHostDto,
|
||||||
@@ -9,28 +8,38 @@ import {
|
|||||||
import * as bcrypt from 'bcryptjs';
|
import * as bcrypt from 'bcryptjs';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { User } from '@prisma/client';
|
import { User } from '@prisma/client';
|
||||||
|
import { PrismaClient } from '@prisma/client';
|
||||||
import { z } from 'zod';
|
import { z } from 'zod';
|
||||||
import { hostCompanyDetailsSchema } from '@/common/utils/validation/host/hostCompanyDetails.validation';
|
import { hostCompanyDetailsSchema } from '../../../common/utils/validation/host/hostCompanyDetails.validation';
|
||||||
import {
|
import {
|
||||||
ACTIVITY_AM_DISPLAY_STATUS,
|
ACTIVITY_AM_DISPLAY_STATUS,
|
||||||
ACTIVITY_AM_INTERNAL_STATUS,
|
ACTIVITY_AM_INTERNAL_STATUS,
|
||||||
ACTIVITY_DISPLAY_STATUS, ACTIVITY_INTERNAL_STATUS, HOST_STATUS_DISPLAY,
|
ACTIVITY_DISPLAY_STATUS, ACTIVITY_INTERNAL_STATUS, HOST_STATUS_DISPLAY,
|
||||||
HOST_STATUS_INTERNAL,
|
HOST_STATUS_INTERNAL,
|
||||||
STEPPER,
|
STEPPER,
|
||||||
} from '@/common/utils/constants/host.constant';
|
} from '../../../common/utils/constants/host.constant';
|
||||||
import {
|
import {
|
||||||
ACTIVITY_TRACK_STATUS,
|
ACTIVITY_TRACK_STATUS,
|
||||||
ACTIVITY_TRACK_TYPE,
|
ACTIVITY_TRACK_TYPE,
|
||||||
MINGLAR_STATUS_DISPLAY,
|
MINGLAR_STATUS_DISPLAY,
|
||||||
MINGLAR_STATUS_INTERNAL,
|
MINGLAR_STATUS_INTERNAL,
|
||||||
} from '@/common/utils/constants/minglar.constant';
|
} from '../../../common/utils/constants/minglar.constant';
|
||||||
import {
|
import {
|
||||||
ROLE,
|
ROLE,
|
||||||
ROLE_NAME,
|
ROLE_NAME,
|
||||||
USER_STATUS,
|
USER_STATUS,
|
||||||
} from '@/common/utils/constants/common.constant';
|
} from '../../../common/utils/constants/common.constant';
|
||||||
import { getPresignedUrl } from '@/common/middlewares/aws/getPreSignedUrl';
|
import { getPresignedUrl } from '../../../common/middlewares/aws/getPreSignedUrl';
|
||||||
import config from '@/config/config';
|
import config from '../../../config/config';
|
||||||
|
|
||||||
|
function sanitizeDocumentName(name?: string) {
|
||||||
|
if (!name) return null;
|
||||||
|
|
||||||
|
return name
|
||||||
|
.replace(/[^a-zA-Z0-9 _-]/g, '') // remove / .
|
||||||
|
.substring(0, 100);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
type HostCompanyDetailsInput = z.infer<typeof hostCompanyDetailsSchema>;
|
type HostCompanyDetailsInput = z.infer<typeof hostCompanyDetailsSchema>;
|
||||||
|
|
||||||
@@ -63,7 +72,7 @@ const bucket = config.aws.bucketName;
|
|||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class HostService {
|
export class HostService {
|
||||||
constructor(private prisma: PrismaService) { }
|
constructor(private prisma: PrismaClient) { }
|
||||||
|
|
||||||
async createHost(data: CreateHostDto) {
|
async createHost(data: CreateHostDto) {
|
||||||
return this.prisma.user.create({ data });
|
return this.prisma.user.create({ data });
|
||||||
@@ -76,9 +85,14 @@ export class HostService {
|
|||||||
async getHostIdByUserXid(user_xid: number) {
|
async getHostIdByUserXid(user_xid: number) {
|
||||||
const host = await this.prisma.hostHeader.findFirst({
|
const host = await this.prisma.hostHeader.findFirst({
|
||||||
where: { userXid: user_xid },
|
where: { userXid: user_xid },
|
||||||
select: { id: true, companyName: true, countryXid: true, stepper: true },
|
select: { id: true, stepper: true },
|
||||||
});
|
});
|
||||||
return host;
|
|
||||||
|
const user = await this.prisma.user.findUnique({
|
||||||
|
where: { id: user_xid },
|
||||||
|
select: { id: true, emailAddress: true },
|
||||||
|
})
|
||||||
|
return { host, user };
|
||||||
}
|
}
|
||||||
|
|
||||||
async getHostById(id: number) {
|
async getHostById(id: number) {
|
||||||
@@ -294,6 +308,10 @@ export class HostService {
|
|||||||
select: {
|
select: {
|
||||||
id: true,
|
id: true,
|
||||||
roleXid: true,
|
roleXid: true,
|
||||||
|
firstName: true,
|
||||||
|
lastName: true,
|
||||||
|
emailAddress: true,
|
||||||
|
mobileNumber: true,
|
||||||
userPassword: true,
|
userPassword: true,
|
||||||
userStatus: true
|
userStatus: true
|
||||||
}
|
}
|
||||||
@@ -377,6 +395,19 @@ export class HostService {
|
|||||||
|
|
||||||
async addPaymentDetails(data: AddPaymentDetailsDTO) {
|
async addPaymentDetails(data: AddPaymentDetailsDTO) {
|
||||||
return await this.prisma.$transaction(async (tx) => {
|
return await this.prisma.$transaction(async (tx) => {
|
||||||
|
const existingAccount = await tx.hostBankDetails.findFirst({
|
||||||
|
where: {
|
||||||
|
accountNumber: data.accountNumber,
|
||||||
|
isActive: true,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
if (existingAccount) {
|
||||||
|
throw new ApiError(
|
||||||
|
400,
|
||||||
|
'Host account with this account number already exists.'
|
||||||
|
);
|
||||||
|
}
|
||||||
const addedPaymentDetails = await tx.hostBankDetails.create({
|
const addedPaymentDetails = await tx.hostBankDetails.create({
|
||||||
data,
|
data,
|
||||||
});
|
});
|
||||||
@@ -601,6 +632,52 @@ export class HostService {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async getParentDocumentsByHostId(userId: number) {
|
||||||
|
const host = await this.prisma.hostHeader.findFirst({
|
||||||
|
where: { userXid: userId },
|
||||||
|
select: { id: true },
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!host) return [];
|
||||||
|
|
||||||
|
const parents = await this.prisma.hostParent.findMany({
|
||||||
|
where: { hostXid: host.id },
|
||||||
|
include: { HostParenetDocuments: true },
|
||||||
|
});
|
||||||
|
|
||||||
|
return parents.flatMap(p => p.HostParenetDocuments);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
async deleteExistingParentRecords(userId: number) {
|
||||||
|
const host = await this.prisma.hostHeader.findFirst({
|
||||||
|
where: { userXid: userId },
|
||||||
|
select: { id: true },
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!host) return;
|
||||||
|
|
||||||
|
const parents = await this.prisma.hostParent.findMany({
|
||||||
|
where: { hostXid: host.id },
|
||||||
|
select: { id: true },
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!parents.length) return;
|
||||||
|
|
||||||
|
const parentIds = parents.map(p => p.id);
|
||||||
|
|
||||||
|
// 1️⃣ Delete documents first
|
||||||
|
await this.prisma.hostParenetDocuments.deleteMany({
|
||||||
|
where: { hostParentXid: { in: parentIds } },
|
||||||
|
});
|
||||||
|
|
||||||
|
// 2️⃣ Then delete parent records
|
||||||
|
await this.prisma.hostParent.deleteMany({
|
||||||
|
where: { id: { in: parentIds } },
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
async addOrUpdateCompanyDetails(
|
async addOrUpdateCompanyDetails(
|
||||||
user_xid: number,
|
user_xid: number,
|
||||||
companyData: HostCompanyDetailsInput,
|
companyData: HostCompanyDetailsInput,
|
||||||
@@ -615,6 +692,19 @@ export class HostService {
|
|||||||
where: { userXid: user_xid },
|
where: { userXid: user_xid },
|
||||||
include: { hostParent: true },
|
include: { hostParent: true },
|
||||||
});
|
});
|
||||||
|
console.log(existingHostCompany, "-: Existing hai")
|
||||||
|
|
||||||
|
let existingParentCompany;
|
||||||
|
|
||||||
|
if (existingHostCompany) {
|
||||||
|
existingParentCompany = await tx.hostParent.findFirst({
|
||||||
|
where: { hostXid: existingHostCompany.id },
|
||||||
|
select: {
|
||||||
|
id: true,
|
||||||
|
logoPath: true
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
let hostStatusInternal;
|
let hostStatusInternal;
|
||||||
let hostStatusDisplay;
|
let hostStatusDisplay;
|
||||||
@@ -678,12 +768,14 @@ export class HostService {
|
|||||||
// -------------------------------------------------------
|
// -------------------------------------------------------
|
||||||
if (!existingHostCompany) {
|
if (!existingHostCompany) {
|
||||||
if (!isDraft) {
|
if (!isDraft) {
|
||||||
|
console.log("First time direct final submit.")
|
||||||
const existingByPan = await tx.hostHeader.findFirst({
|
const existingByPan = await tx.hostHeader.findFirst({
|
||||||
where: { panNumber: companyData.panNumber },
|
where: { panNumber: companyData.panNumber },
|
||||||
});
|
});
|
||||||
if (existingByPan)
|
if (existingByPan)
|
||||||
throw new ApiError(400, 'Company already exists with this pan/bin number');
|
throw new ApiError(400, 'Company already exists with this pan/bin number');
|
||||||
}
|
}
|
||||||
|
console.log("First Time Aaya hai")
|
||||||
|
|
||||||
const createdHost = await tx.hostHeader.create({
|
const createdHost = await tx.hostHeader.create({
|
||||||
data: {
|
data: {
|
||||||
@@ -725,7 +817,7 @@ export class HostService {
|
|||||||
const docsData = documents.map((doc) => ({
|
const docsData = documents.map((doc) => ({
|
||||||
hostXid: createdHost.id,
|
hostXid: createdHost.id,
|
||||||
documentTypeXid: doc.documentTypeXid,
|
documentTypeXid: doc.documentTypeXid,
|
||||||
documentName: doc.documentName,
|
documentName: sanitizeDocumentName(doc.documentName),
|
||||||
filePath: doc.filePath,
|
filePath: doc.filePath,
|
||||||
}));
|
}));
|
||||||
await tx.hostDocuments.createMany({ data: docsData });
|
await tx.hostDocuments.createMany({ data: docsData });
|
||||||
@@ -733,20 +825,24 @@ export class HostService {
|
|||||||
|
|
||||||
// parent create
|
// parent create
|
||||||
if (companyData.isSubsidairy && parentCompanyData) {
|
if (companyData.isSubsidairy && parentCompanyData) {
|
||||||
|
console.log("Parent ke saath aaya hai first time.")
|
||||||
const createdParent = await tx.hostParent.create({
|
const createdParent = await tx.hostParent.create({
|
||||||
data: {
|
data: {
|
||||||
host: { connect: { id: createdHost.id } },
|
host: { connect: { id: createdHost.id } },
|
||||||
companyName: parentCompanyData.companyName,
|
companyName: parentCompanyData.companyName || null,
|
||||||
address1: parentCompanyData.address1 || null,
|
address1: parentCompanyData.address1 || null,
|
||||||
address2: parentCompanyData.address2 || null,
|
address2: parentCompanyData.address2 || null,
|
||||||
cities: parentCompanyData.cityXid
|
// Safely handle city connection - only connect if valid ID exists
|
||||||
? { connect: { id: parentCompanyData.cityXid } }
|
cities: parentCompanyData?.cityXid && !isNaN(Number(parentCompanyData.cityXid))
|
||||||
|
? { connect: { id: Number(parentCompanyData.cityXid) } }
|
||||||
: undefined,
|
: undefined,
|
||||||
states: parentCompanyData.stateXid
|
|
||||||
? { connect: { id: parentCompanyData.stateXid } }
|
states: parentCompanyData?.stateXid && !isNaN(Number(parentCompanyData.stateXid))
|
||||||
|
? { connect: { id: Number(parentCompanyData.stateXid) } }
|
||||||
: undefined,
|
: undefined,
|
||||||
countries: parentCompanyData.countryXid
|
|
||||||
? { connect: { id: parentCompanyData.countryXid } }
|
countries: parentCompanyData?.countryXid && !isNaN(Number(parentCompanyData.countryXid))
|
||||||
|
? { connect: { id: Number(parentCompanyData.countryXid) } }
|
||||||
: undefined,
|
: undefined,
|
||||||
pinCode: parentCompanyData.pinCode || null,
|
pinCode: parentCompanyData.pinCode || null,
|
||||||
logoPath: parentCompanyData.logoPath || null,
|
logoPath: parentCompanyData.logoPath || null,
|
||||||
@@ -772,7 +868,7 @@ export class HostService {
|
|||||||
const parentDocsData = parentDocuments.map((doc) => ({
|
const parentDocsData = parentDocuments.map((doc) => ({
|
||||||
hostParentXid: createdParent.id,
|
hostParentXid: createdParent.id,
|
||||||
documentTypeXid: doc.documentTypeXid,
|
documentTypeXid: doc.documentTypeXid,
|
||||||
documentName: doc.documentName,
|
documentName: sanitizeDocumentName(doc.documentName),
|
||||||
filePath: doc.filePath,
|
filePath: doc.filePath,
|
||||||
}));
|
}));
|
||||||
await tx.hostParenetDocuments.createMany({ data: parentDocsData });
|
await tx.hostParenetDocuments.createMany({ data: parentDocsData });
|
||||||
@@ -801,11 +897,22 @@ export class HostService {
|
|||||||
companyName: companyData.companyName,
|
companyName: companyData.companyName,
|
||||||
address1: companyData.address1,
|
address1: companyData.address1,
|
||||||
address2: companyData.address2,
|
address2: companyData.address2,
|
||||||
cities: companyData.cityXid ? { connect: { id: companyData.cityXid } } : undefined,
|
// Safely handle city connection - only connect if valid ID exists
|
||||||
states: companyData.stateXid ? { connect: { id: companyData.stateXid } } : undefined,
|
cities: companyData.cityXid && !isNaN(Number(companyData.cityXid))
|
||||||
countries: companyData.countryXid ? { connect: { id: companyData.countryXid } } : undefined,
|
? { connect: { id: Number(companyData.cityXid) } }
|
||||||
|
: undefined, // Don't change if not provided
|
||||||
|
|
||||||
|
// Same for state
|
||||||
|
states: companyData.stateXid && !isNaN(Number(companyData.stateXid))
|
||||||
|
? { connect: { id: Number(companyData.stateXid) } }
|
||||||
|
: undefined,
|
||||||
|
|
||||||
|
// Same for country
|
||||||
|
countries: companyData.countryXid && !isNaN(Number(companyData.countryXid))
|
||||||
|
? { connect: { id: Number(companyData.countryXid) } }
|
||||||
|
: undefined,
|
||||||
pinCode: companyData.pinCode,
|
pinCode: companyData.pinCode,
|
||||||
logoPath: companyData.logoPath || null,
|
logoPath: companyData.logoPath || existingHostCompany.logoPath,
|
||||||
isSubsidairy: companyData.isSubsidairy,
|
isSubsidairy: companyData.isSubsidairy,
|
||||||
registrationNumber: companyData.registrationNumber,
|
registrationNumber: companyData.registrationNumber,
|
||||||
panNumber: companyData.panNumber,
|
panNumber: companyData.panNumber,
|
||||||
@@ -833,6 +940,7 @@ export class HostService {
|
|||||||
// documents UPSERT
|
// documents UPSERT
|
||||||
if (documents?.length) {
|
if (documents?.length) {
|
||||||
for (const doc of documents) {
|
for (const doc of documents) {
|
||||||
|
if (!doc.filePath) continue;
|
||||||
const existingDoc = await tx.hostDocuments.findFirst({
|
const existingDoc = await tx.hostDocuments.findFirst({
|
||||||
where: {
|
where: {
|
||||||
hostXid: updatedHost.id,
|
hostXid: updatedHost.id,
|
||||||
@@ -845,7 +953,7 @@ export class HostService {
|
|||||||
where: { id: existingDoc.id },
|
where: { id: existingDoc.id },
|
||||||
data: {
|
data: {
|
||||||
filePath: doc.filePath,
|
filePath: doc.filePath,
|
||||||
documentName: doc.documentName || existingDoc.documentName,
|
documentName: sanitizeDocumentName(doc.documentName) || existingDoc.documentName,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
@@ -853,7 +961,7 @@ export class HostService {
|
|||||||
data: {
|
data: {
|
||||||
hostXid: updatedHost.id,
|
hostXid: updatedHost.id,
|
||||||
documentTypeXid: doc.documentTypeXid,
|
documentTypeXid: doc.documentTypeXid,
|
||||||
documentName: doc.documentName,
|
documentName: sanitizeDocumentName(doc.documentName),
|
||||||
filePath: doc.filePath,
|
filePath: doc.filePath,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
@@ -865,25 +973,28 @@ export class HostService {
|
|||||||
if (companyData.isSubsidairy) {
|
if (companyData.isSubsidairy) {
|
||||||
const parentRecords = existingHostCompany.hostParent;
|
const parentRecords = existingHostCompany.hostParent;
|
||||||
const parentRecord = Array.isArray(parentRecords) ? parentRecords[0] : parentRecords;
|
const parentRecord = Array.isArray(parentRecords) ? parentRecords[0] : parentRecords;
|
||||||
|
console.log("Yaha aaya update in the apretn me")
|
||||||
if (!parentRecord) {
|
if (!parentRecord) {
|
||||||
|
console.log("Parent record nahi mila to create kar raha hai.")
|
||||||
const createdParent = await tx.hostParent.create({
|
const createdParent = await tx.hostParent.create({
|
||||||
data: {
|
data: {
|
||||||
host: { connect: { id: updatedHost.id } },
|
host: { connect: { id: updatedHost.id } },
|
||||||
companyName: parentCompanyData.companyName,
|
companyName: parentCompanyData.companyName || null,
|
||||||
address1: parentCompanyData.address1 || null,
|
address1: parentCompanyData.address1 || null,
|
||||||
address2: parentCompanyData.address2 || null,
|
address2: parentCompanyData.address2 || null,
|
||||||
cities: parentCompanyData.cityXid
|
cities: parentCompanyData?.cityXid && !isNaN(Number(parentCompanyData.cityXid))
|
||||||
? { connect: { id: parentCompanyData.cityXid } }
|
? { connect: { id: Number(parentCompanyData.cityXid) } }
|
||||||
: undefined,
|
: undefined,
|
||||||
states: parentCompanyData.stateXid
|
|
||||||
? { connect: { id: parentCompanyData.stateXid } }
|
states: parentCompanyData?.stateXid && !isNaN(Number(parentCompanyData.stateXid))
|
||||||
|
? { connect: { id: Number(parentCompanyData.stateXid) } }
|
||||||
: undefined,
|
: undefined,
|
||||||
countries: parentCompanyData.countryXid
|
|
||||||
? { connect: { id: parentCompanyData.countryXid } }
|
countries: parentCompanyData?.countryXid && !isNaN(Number(parentCompanyData.countryXid))
|
||||||
|
? { connect: { id: Number(parentCompanyData.countryXid) } }
|
||||||
: undefined,
|
: undefined,
|
||||||
pinCode: parentCompanyData.pinCode || null,
|
pinCode: parentCompanyData.pinCode || null,
|
||||||
logoPath: parentCompanyData.logoPath || null,
|
logoPath: parentCompanyData?.logoPath || existingParentCompany?.logoPath || null,
|
||||||
registrationNumber: parentCompanyData.registrationNumber || null,
|
registrationNumber: parentCompanyData.registrationNumber || null,
|
||||||
panNumber: parentCompanyData.panNumber || null,
|
panNumber: parentCompanyData.panNumber || null,
|
||||||
gstNumber: parentCompanyData.gstNumber || null,
|
gstNumber: parentCompanyData.gstNumber || null,
|
||||||
@@ -907,7 +1018,7 @@ export class HostService {
|
|||||||
data: {
|
data: {
|
||||||
hostParentXid: createdParent.id,
|
hostParentXid: createdParent.id,
|
||||||
documentTypeXid: doc.documentTypeXid,
|
documentTypeXid: doc.documentTypeXid,
|
||||||
documentName: doc.documentName,
|
documentName: sanitizeDocumentName(doc.documentName),
|
||||||
filePath: doc.filePath,
|
filePath: doc.filePath,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
@@ -917,20 +1028,22 @@ export class HostService {
|
|||||||
await tx.hostParent.update({
|
await tx.hostParent.update({
|
||||||
where: { id: parentRecord.id },
|
where: { id: parentRecord.id },
|
||||||
data: {
|
data: {
|
||||||
companyName: parentCompanyData.companyName,
|
companyName: parentCompanyData.companyName || null,
|
||||||
address1: parentCompanyData.address1 || null,
|
address1: parentCompanyData.address1 || null,
|
||||||
address2: parentCompanyData.address2 || null,
|
address2: parentCompanyData.address2 || null,
|
||||||
cities: parentCompanyData.cityXid
|
cities: parentCompanyData?.cityXid && !isNaN(Number(parentCompanyData.cityXid))
|
||||||
? { connect: { id: parentCompanyData.cityXid } }
|
? { connect: { id: Number(parentCompanyData.cityXid) } }
|
||||||
: undefined,
|
: undefined,
|
||||||
states: parentCompanyData.stateXid
|
|
||||||
? { connect: { id: parentCompanyData.stateXid } }
|
states: parentCompanyData?.stateXid && !isNaN(Number(parentCompanyData.stateXid))
|
||||||
|
? { connect: { id: Number(parentCompanyData.stateXid) } }
|
||||||
: undefined,
|
: undefined,
|
||||||
countries: parentCompanyData.countryXid
|
|
||||||
? { connect: { id: parentCompanyData.countryXid } }
|
countries: parentCompanyData?.countryXid && !isNaN(Number(parentCompanyData.countryXid))
|
||||||
|
? { connect: { id: Number(parentCompanyData.countryXid) } }
|
||||||
: undefined,
|
: undefined,
|
||||||
pinCode: parentCompanyData.pinCode || null,
|
pinCode: parentCompanyData.pinCode || null,
|
||||||
logoPath: parentCompanyData.logoPath || null,
|
logoPath: parentCompanyData?.logoPath || existingParentCompany?.logoPath || null,
|
||||||
registrationNumber: parentCompanyData.registrationNumber || null,
|
registrationNumber: parentCompanyData.registrationNumber || null,
|
||||||
panNumber: parentCompanyData.panNumber || null,
|
panNumber: parentCompanyData.panNumber || null,
|
||||||
gstNumber: parentCompanyData.gstNumber || null,
|
gstNumber: parentCompanyData.gstNumber || null,
|
||||||
@@ -962,7 +1075,7 @@ export class HostService {
|
|||||||
where: { id: existingParentDoc.id },
|
where: { id: existingParentDoc.id },
|
||||||
data: {
|
data: {
|
||||||
filePath: doc.filePath,
|
filePath: doc.filePath,
|
||||||
documentName: doc.documentName || existingParentDoc.documentName,
|
documentName: sanitizeDocumentName(doc.documentName) || existingParentDoc.documentName,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
@@ -970,7 +1083,7 @@ export class HostService {
|
|||||||
data: {
|
data: {
|
||||||
hostParentXid: parentRecord.id,
|
hostParentXid: parentRecord.id,
|
||||||
documentTypeXid: doc.documentTypeXid,
|
documentTypeXid: doc.documentTypeXid,
|
||||||
documentName: doc.documentName,
|
documentName: sanitizeDocumentName(doc.documentName),
|
||||||
filePath: doc.filePath,
|
filePath: doc.filePath,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
@@ -979,6 +1092,7 @@ export class HostService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
console.log("Last ke else block me aaya hai")
|
||||||
const previousParent = existingHostCompany.hostParent;
|
const previousParent = existingHostCompany.hostParent;
|
||||||
let prevParentId = null;
|
let prevParentId = null;
|
||||||
|
|
||||||
@@ -1761,6 +1875,7 @@ export class HostService {
|
|||||||
isActive: true,
|
isActive: true,
|
||||||
},
|
},
|
||||||
select: {
|
select: {
|
||||||
|
id: true,
|
||||||
comments: true,
|
comments: true,
|
||||||
pqqAnswerXid: true,
|
pqqAnswerXid: true,
|
||||||
pqqQuestions: {
|
pqqQuestions: {
|
||||||
@@ -1826,15 +1941,20 @@ export class HostService {
|
|||||||
const sub = q.pqqSubCategories;
|
const sub = q.pqqSubCategories;
|
||||||
const cat = sub.category;
|
const cat = sub.category;
|
||||||
|
|
||||||
|
// 1️⃣ Category level
|
||||||
// 1️⃣ Category level
|
// 1️⃣ Category level
|
||||||
if (!grouped[cat.id]) {
|
if (!grouped[cat.id]) {
|
||||||
grouped[cat.id] = {
|
grouped[cat.id] = {
|
||||||
id: cat.id,
|
id: cat.id,
|
||||||
categoryName: cat.categoryName,
|
categoryName: cat.categoryName,
|
||||||
displayOrder: cat.displayOrder,
|
displayOrder: cat.displayOrder,
|
||||||
|
activityPqqHeaderId: item.id, // ✅ Added to match AM response
|
||||||
pqqsubCategories: []
|
pqqsubCategories: []
|
||||||
};
|
};
|
||||||
|
} else if (!grouped[cat.id].activityPqqHeaderId) {
|
||||||
|
grouped[cat.id].activityPqqHeaderId = item.id; // Ensures it's set if missing
|
||||||
}
|
}
|
||||||
|
|
||||||
const category = grouped[cat.id];
|
const category = grouped[cat.id];
|
||||||
|
|
||||||
// 2️⃣ Subcategory level
|
// 2️⃣ Subcategory level
|
||||||
|
|||||||
@@ -15,8 +15,8 @@ export async function resendOtpEmail(
|
|||||||
const htmlContent = `
|
const htmlContent = `
|
||||||
<p>Dear ${role},</p>
|
<p>Dear ${role},</p>
|
||||||
<p>Your new OTP is: <strong>${otp}</strong></p>
|
<p>Your new OTP is: <strong>${otp}</strong></p>
|
||||||
<p>This code is valid for 5 minutes. Please do not share it with anyone.</p>
|
<p>This code will be valid for the next 5 minutes.</p>
|
||||||
<p>Best regards,<br/>Minglar Team</p>
|
<p>Warm regards,<br/>Minglar Team</p>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -13,9 +13,10 @@ export async function sendOtpEmailForHost(
|
|||||||
|
|
||||||
const htmlContent = `
|
const htmlContent = `
|
||||||
<p>Dear Host,</p>
|
<p>Dear Host,</p>
|
||||||
<p>Your OTP for registration is: <strong>${otp}</strong></p>
|
<p>You’re almost all set! 🎉</p>
|
||||||
<p>This code is valid for 5 minutes. Please do not share it with anyone.</p>
|
<p>Enter <strong>${otp}</strong> to wrap your registration.</p>
|
||||||
<p>Best regards,<br/>Minglar Team</p>
|
<p>This code will be valid for the next 5 minutes.</p>
|
||||||
|
<p>Warm regards,<br/>Minglar Team</p>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
import { PrismaService } from "../../../common/database/prisma.service";
|
import { PrismaClient } from '@prisma/client';
|
||||||
import jwt, { JwtPayload } from "jsonwebtoken";
|
import jwt, { JwtPayload } from "jsonwebtoken";
|
||||||
import moment from "moment";
|
import moment from "moment";
|
||||||
import config from "../../../config/config";
|
import config from "../../../config/config";
|
||||||
|
|
||||||
export class TokenService {
|
export class TokenService {
|
||||||
constructor(private readonly prisma: PrismaService = new PrismaService()) {}
|
constructor(private prisma: PrismaClient) { }
|
||||||
|
|
||||||
private generateToken(
|
private generateToken(
|
||||||
user_xid: number,
|
user_xid: number,
|
||||||
@@ -53,6 +53,10 @@ export class TokenService {
|
|||||||
config.jwt.secret
|
config.jwt.secret
|
||||||
);
|
);
|
||||||
|
|
||||||
|
await this.prisma.token.deleteMany({
|
||||||
|
where: { userXid: user_xid }
|
||||||
|
})
|
||||||
|
|
||||||
await this.prisma.token.create({
|
await this.prisma.token.create({
|
||||||
data: {
|
data: {
|
||||||
token: refreshToken.token,
|
token: refreshToken.token,
|
||||||
@@ -100,6 +104,10 @@ export class TokenService {
|
|||||||
config.jwt.secret
|
config.jwt.secret
|
||||||
);
|
);
|
||||||
|
|
||||||
|
await this.prisma.token.deleteMany({
|
||||||
|
where: { userXid: user_xid }
|
||||||
|
})
|
||||||
|
|
||||||
await this.prisma.token.create({
|
await this.prisma.token.create({
|
||||||
data: {
|
data: {
|
||||||
token: refreshToken.token,
|
token: refreshToken.token,
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyMinglarAdminToken } from '../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../services/minglar.service';
|
import { MinglarService } from '../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -3,14 +3,13 @@ import {
|
|||||||
APIGatewayProxyResult,
|
APIGatewayProxyResult,
|
||||||
Context,
|
Context,
|
||||||
} from 'aws-lambda';
|
} from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminToken } from '../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../services/minglar.service';
|
import { MinglarService } from '../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get all host applications handler
|
* Get all host applications handler
|
||||||
|
|||||||
@@ -1,13 +1,12 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { sendEmailToHostForApprovedApplication } from '../../../services/approvalMailtoHost.service';
|
import { sendEmailToHostForApprovedApplication } from '../../../services/approvalMailtoHost.service';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
interface AddSuggestionBody {
|
interface AddSuggestionBody {
|
||||||
hostXid: number;
|
hostXid: number;
|
||||||
@@ -47,8 +46,8 @@ export const handler = safeHandler(async (
|
|||||||
|
|
||||||
// Add suggestion using service
|
// Add suggestion using service
|
||||||
await minglarService.acceptHostApplication(hostXid, userInfo.id);
|
await minglarService.acceptHostApplication(hostXid, userInfo.id);
|
||||||
const hostDetails = await minglarService.getUserDetails(userInfo.id)
|
const hostDetails = await minglarService.getUserDetails(hostXid)
|
||||||
await sendEmailToHostForApprovedApplication(hostDetails.emailAddress)
|
await sendEmailToHostForApprovedApplication(hostDetails.emailAddress, hostDetails.firstName)
|
||||||
|
|
||||||
return {
|
return {
|
||||||
statusCode: 200,
|
statusCode: 200,
|
||||||
|
|||||||
@@ -1,12 +1,16 @@
|
|||||||
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
|
import { sendAMPQQAcceptanceMailtoHost } from '../../../../minglaradmin/services/approvalMailtoHost.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
interface Body {
|
||||||
|
activityId: number;
|
||||||
|
}
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
@@ -17,7 +21,16 @@ export const handler = safeHandler(async (
|
|||||||
|
|
||||||
const userInfo = await verifyMinglarAdminToken(token);
|
const userInfo = await verifyMinglarAdminToken(token);
|
||||||
|
|
||||||
const activityId = event.pathParameters?.activityId;
|
// Parse request body
|
||||||
|
let body: Body;
|
||||||
|
|
||||||
|
try {
|
||||||
|
body = event.body ? JSON.parse(event.body) : {};
|
||||||
|
} catch (error) {
|
||||||
|
throw new ApiError(400, 'Invalid JSON in request body');
|
||||||
|
}
|
||||||
|
|
||||||
|
const { activityId } = body;
|
||||||
|
|
||||||
if (!activityId) {
|
if (!activityId) {
|
||||||
throw new ApiError(400, 'activityId is required');
|
throw new ApiError(400, 'activityId is required');
|
||||||
@@ -27,6 +40,9 @@ export const handler = safeHandler(async (
|
|||||||
Number(activityId),
|
Number(activityId),
|
||||||
Number(userInfo.id)
|
Number(userInfo.id)
|
||||||
);
|
);
|
||||||
|
const hostXid = await minglarService.getHostXidByActivityId(activityId)
|
||||||
|
const hostDetails = await minglarService.getUserDetails(hostXid)
|
||||||
|
await sendAMPQQAcceptanceMailtoHost(hostDetails.emailAddress, hostDetails.firstName)
|
||||||
|
|
||||||
return {
|
return {
|
||||||
statusCode: 201,
|
statusCode: 201,
|
||||||
|
|||||||
@@ -1,13 +1,12 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
// import { HOST_SUGGESTION_TITLES } from '../../../../../common/utils/constants/minglar.constant';
|
// import { HOST_SUGGESTION_TITLES } from '../../../../../common/utils/constants/minglar.constant';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
interface AddSuggestionBody {
|
interface AddSuggestionBody {
|
||||||
title: string;
|
title: string;
|
||||||
@@ -34,7 +33,7 @@ export const handler = safeHandler(async (
|
|||||||
const userInfo = await verifyMinglarAdminToken(token);
|
const userInfo = await verifyMinglarAdminToken(token);
|
||||||
|
|
||||||
// Get user details
|
// Get user details
|
||||||
const user = await prismaService.user.findUnique({
|
const user = await prismaClient.user.findUnique({
|
||||||
where: { id: userInfo.id },
|
where: { id: userInfo.id },
|
||||||
select: { id: true, roleXid: true }
|
select: { id: true, roleXid: true }
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
interface AddSuggestionBody {
|
interface AddSuggestionBody {
|
||||||
hostXid: number;
|
hostXid: number;
|
||||||
@@ -34,7 +33,7 @@ export const handler = safeHandler(async (
|
|||||||
const userInfo = await verifyMinglarAdminToken(token);
|
const userInfo = await verifyMinglarAdminToken(token);
|
||||||
|
|
||||||
// Get user details
|
// Get user details
|
||||||
const user = await prismaService.user.findUnique({
|
const user = await prismaClient.user.findUnique({
|
||||||
where: { id: userInfo.id },
|
where: { id: userInfo.id },
|
||||||
select: { id: true, roleXid: true }
|
select: { id: true, roleXid: true }
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,13 +1,12 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get all host applications handler with pagination
|
* Get all host applications handler with pagination
|
||||||
@@ -26,7 +25,7 @@ export const handler = safeHandler(async (
|
|||||||
const userInfo = await verifyMinglarAdminToken(token);
|
const userInfo = await verifyMinglarAdminToken(token);
|
||||||
|
|
||||||
// Get user details including role
|
// Get user details including role
|
||||||
const user = await prismaService.user.findUnique({
|
const user = await prismaClient.user.findUnique({
|
||||||
where: { id: userInfo.id },
|
where: { id: userInfo.id },
|
||||||
select: { id: true, roleXid: true }
|
select: { id: true, roleXid: true }
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,13 +1,12 @@
|
|||||||
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
import { sendAMRejectionMailtoHost } from '../../../services/rejectionMailtoHost.service';
|
import { sendAMRejectionMailtoHost } from '../../../services/rejectionMailtoHost.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
interface AddSuggestionBody {
|
interface AddSuggestionBody {
|
||||||
hostXid: number;
|
hostXid: number;
|
||||||
@@ -47,8 +46,8 @@ export const handler = safeHandler(async (
|
|||||||
|
|
||||||
// Add suggestion using service
|
// Add suggestion using service
|
||||||
await minglarService.rejectHostApplicationAM(hostXid, userInfo.id);
|
await minglarService.rejectHostApplicationAM(hostXid, userInfo.id);
|
||||||
const hostDetails = await minglarService.getUserDetails(userInfo.id)
|
const hostDetails = await minglarService.getUserDetails(hostXid)
|
||||||
await sendAMRejectionMailtoHost(hostDetails.emailAddress)
|
await sendAMRejectionMailtoHost(hostDetails.emailAddress, hostDetails.firstName)
|
||||||
|
|
||||||
return {
|
return {
|
||||||
statusCode: 200,
|
statusCode: 200,
|
||||||
|
|||||||
@@ -1,12 +1,16 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
import { sendAMPQQRejectionMailtoHost } from '../../../../minglaradmin/services/rejectionMailtoHost.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
interface Body {
|
||||||
|
activityId: number;
|
||||||
|
}
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
@@ -17,7 +21,16 @@ export const handler = safeHandler(async (
|
|||||||
|
|
||||||
const userInfo = await verifyMinglarAdminToken(token);
|
const userInfo = await verifyMinglarAdminToken(token);
|
||||||
|
|
||||||
const activityId = event.pathParameters?.activityId;
|
// Parse request body
|
||||||
|
let body: Body;
|
||||||
|
|
||||||
|
try {
|
||||||
|
body = event.body ? JSON.parse(event.body) : {};
|
||||||
|
} catch (error) {
|
||||||
|
throw new ApiError(400, 'Invalid JSON in request body');
|
||||||
|
}
|
||||||
|
|
||||||
|
const { activityId } = body;
|
||||||
|
|
||||||
if (!activityId) {
|
if (!activityId) {
|
||||||
throw new ApiError(400, 'activityId is required');
|
throw new ApiError(400, 'activityId is required');
|
||||||
@@ -27,6 +40,9 @@ export const handler = safeHandler(async (
|
|||||||
Number(activityId),
|
Number(activityId),
|
||||||
Number(userInfo.id)
|
Number(userInfo.id)
|
||||||
);
|
);
|
||||||
|
const hostXid = await minglarService.getHostXidByActivityId(activityId)
|
||||||
|
const hostDetails = await minglarService.getUserDetails(hostXid)
|
||||||
|
await sendAMPQQRejectionMailtoHost(hostDetails.emailAddress, hostDetails.firstName)
|
||||||
|
|
||||||
return {
|
return {
|
||||||
statusCode: 201,
|
statusCode: 201,
|
||||||
|
|||||||
@@ -3,14 +3,13 @@ import {
|
|||||||
APIGatewayProxyResult,
|
APIGatewayProxyResult,
|
||||||
Context,
|
Context,
|
||||||
} from 'aws-lambda';
|
} from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
interface assignAMToHostBody {
|
interface assignAMToHostBody {
|
||||||
host_xid: number;
|
host_xid: number;
|
||||||
@@ -40,7 +39,7 @@ export const handler = safeHandler(
|
|||||||
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
||||||
|
|
||||||
// Get user details including role
|
// Get user details including role
|
||||||
const user = await prismaService.user.findUnique({
|
const user = await prismaClient.user.findUnique({
|
||||||
where: { id: userInfo.id },
|
where: { id: userInfo.id },
|
||||||
select: { id: true, roleXid: true },
|
select: { id: true, roleXid: true },
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
interface assignAMToHostBody {
|
interface assignAMToHostBody {
|
||||||
host_xid: number,
|
host_xid: number,
|
||||||
@@ -34,7 +33,7 @@ export const handler = safeHandler(async (
|
|||||||
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
||||||
|
|
||||||
// Get user details including role
|
// Get user details including role
|
||||||
const user = await prismaService.user.findUnique({
|
const user = await prismaClient.user.findUnique({
|
||||||
where: { id: userInfo.id },
|
where: { id: userInfo.id },
|
||||||
select: { id: true, roleXid: true }
|
select: { id: true, roleXid: true }
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,15 +1,14 @@
|
|||||||
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { PrePopulateService } from '../../../../prepopulate/services/prepopulate.service';
|
import { PrePopulateService } from '../../../../prepopulate/services/prepopulate.service';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
const prePopulateService = new PrePopulateService(prismaClient);
|
||||||
const prePopulateService = new PrePopulateService(prismaService);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add suggestion handler for host applications
|
* Add suggestion handler for host applications
|
||||||
|
|||||||
@@ -4,14 +4,13 @@ import {
|
|||||||
APIGatewayProxyResult,
|
APIGatewayProxyResult,
|
||||||
Context,
|
Context,
|
||||||
} from 'aws-lambda';
|
} from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get all host applications handler
|
* Get all host applications handler
|
||||||
@@ -36,7 +35,7 @@ export const handler = safeHandler(
|
|||||||
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
||||||
|
|
||||||
// Get user details including role
|
// Get user details including role
|
||||||
const user = await prismaService.user.findUnique({
|
const user = await prismaClient.user.findUnique({
|
||||||
where: { id: userInfo.id },
|
where: { id: userInfo.id },
|
||||||
select: { id: true, roleXid: true },
|
select: { id: true, roleXid: true },
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -3,15 +3,14 @@ import {
|
|||||||
APIGatewayProxyResult,
|
APIGatewayProxyResult,
|
||||||
Context,
|
Context,
|
||||||
} from 'aws-lambda';
|
} from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get all NEW host applications handler
|
* Get all NEW host applications handler
|
||||||
@@ -36,7 +35,7 @@ export const handler = safeHandler(
|
|||||||
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
const userInfo = await verifyOnlyMinglarAdminToken(token);
|
||||||
|
|
||||||
// Get user details including role
|
// Get user details including role
|
||||||
const user = await prismaService.user.findUnique({
|
const user = await prismaClient.user.findUnique({
|
||||||
where: { id: userInfo.id },
|
where: { id: userInfo.id },
|
||||||
select: { id: true, roleXid: true },
|
select: { id: true, roleXid: true },
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,13 +1,12 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
import { sendEmailToHostForRejectedApplication } from '../../../services/rejectionMailtoHost.service';
|
import { sendEmailToHostForRejectedApplication } from '../../../services/rejectionMailtoHost.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
interface AddSuggestionBody {
|
interface AddSuggestionBody {
|
||||||
hostXid: number;
|
hostXid: number;
|
||||||
@@ -47,7 +46,7 @@ export const handler = safeHandler(async (
|
|||||||
|
|
||||||
// Add suggestion using service
|
// Add suggestion using service
|
||||||
await minglarService.rejectHostApplication(hostXid, userInfo.id);
|
await minglarService.rejectHostApplication(hostXid, userInfo.id);
|
||||||
const hostDetails = await minglarService.getUserDetails(userInfo.id)
|
const hostDetails = await minglarService.getUserDetails(hostXid)
|
||||||
if (!hostDetails?.emailAddress) {
|
if (!hostDetails?.emailAddress) {
|
||||||
throw new ApiError(404, 'Host details or email address not found');
|
throw new ApiError(404, 'Host details or email address not found');
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,51 @@
|
|||||||
|
import { verifyMinglarAdminToken } from '@/common/middlewares/jwt/authForMinglarAdmin';
|
||||||
|
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 { MinglarService } from '../../../../minglaradmin/services/minglar.service';
|
||||||
|
|
||||||
|
const minglarService = new MinglarService(prismaClient);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get suggestions handler
|
||||||
|
* Retrieves suggestions based on user's role and host assignments
|
||||||
|
*/
|
||||||
|
export const handler = safeHandler(async (
|
||||||
|
event: APIGatewayProxyEvent,
|
||||||
|
context?: Context
|
||||||
|
): Promise<APIGatewayProxyResult> => {
|
||||||
|
// Verify authentication token
|
||||||
|
const token = event.headers['x-auth-token'] || event.headers['X-Auth-Token'];
|
||||||
|
if (!token) {
|
||||||
|
throw new ApiError(401, 'This is a protected route. Please provide a valid token.');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Verify token and get user info
|
||||||
|
await verifyMinglarAdminToken(token);
|
||||||
|
|
||||||
|
const hostXid = Number(event.pathParameters?.hostXid)
|
||||||
|
|
||||||
|
if (!hostXid) {
|
||||||
|
throw new ApiError(
|
||||||
|
400,
|
||||||
|
'Host ID is required in path parameters.',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get suggestions using service
|
||||||
|
const suggestions = await minglarService.getSuggestionsForAM(hostXid);
|
||||||
|
|
||||||
|
return {
|
||||||
|
statusCode: 200,
|
||||||
|
headers: {
|
||||||
|
'Content-Type': 'application/json',
|
||||||
|
'Access-Control-Allow-Origin': '*',
|
||||||
|
},
|
||||||
|
body: JSON.stringify({
|
||||||
|
success: true,
|
||||||
|
message: 'Suggestions retrieved successfully',
|
||||||
|
data: suggestions,
|
||||||
|
}),
|
||||||
|
};
|
||||||
|
});
|
||||||
@@ -1,12 +1,11 @@
|
|||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
import { verifyMinglarAdminHostToken } from '../../../../../common/middlewares/jwt/authForMinglarAdminHost';
|
import { verifyMinglarAdminHostToken } from '../../../../../common/middlewares/jwt/authForMinglarAdminHost';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,14 +1,13 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { GetMinglarLoginResponseDTO } from '../dto/minglar.dto';
|
import { GetMinglarLoginResponseDTO } from '../dto/minglar.dto';
|
||||||
import { MinglarService } from '../services/minglar.service';
|
import { MinglarService } from '../services/minglar.service';
|
||||||
import { TokenService } from "../services/token.service";
|
import { TokenService } from "../services/token.service";
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarSerivce = new MinglarService(prismaClient);
|
||||||
const minglarSerivce = new MinglarService(prismaService);
|
const tokenService = new TokenService(prismaClient);
|
||||||
const tokenService = new TokenService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
@@ -16,20 +15,22 @@ export const handler = safeHandler(async (
|
|||||||
): Promise<APIGatewayProxyResult> => {
|
): Promise<APIGatewayProxyResult> => {
|
||||||
// Parse request body
|
// Parse request body
|
||||||
let body: { emailAddress?: string; userPassword?: string };
|
let body: { emailAddress?: string; userPassword?: string };
|
||||||
|
|
||||||
try {
|
try {
|
||||||
body = event.body ? JSON.parse(event.body) : {};
|
body = event.body ? JSON.parse(event.body) : {};
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
throw new ApiError(400, 'Invalid JSON in request body');
|
throw new ApiError(400, 'Invalid JSON in request body');
|
||||||
}
|
}
|
||||||
|
|
||||||
const { emailAddress ,userPassword} = body;
|
const { emailAddress, userPassword } = body;
|
||||||
|
|
||||||
if (!emailAddress) {
|
if (!emailAddress) {
|
||||||
throw new ApiError(400, 'Email is required');
|
throw new ApiError(400, 'Email is required');
|
||||||
}
|
}
|
||||||
|
|
||||||
const loginForMinglar = await minglarSerivce.loginForMinglar(emailAddress ,userPassword);
|
const emailToLowerCase = emailAddress.toLowerCase()
|
||||||
|
|
||||||
|
const loginForMinglar = await minglarSerivce.loginForMinglar(emailToLowerCase, userPassword);
|
||||||
|
|
||||||
if (!loginForMinglar) {
|
if (!loginForMinglar) {
|
||||||
throw new ApiError(400, 'Failed to login');
|
throw new ApiError(400, 'Failed to login');
|
||||||
|
|||||||
@@ -3,13 +3,13 @@ import {
|
|||||||
APIGatewayProxyResult,
|
APIGatewayProxyResult,
|
||||||
Context,
|
Context,
|
||||||
} from 'aws-lambda';
|
} from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminToken } from '../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { ROLE } from '../../../common/utils/constants/common.constant';
|
import { ROLE } from '../../../common/utils/constants/common.constant';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const prismaService = prismaClient;
|
||||||
export const handler = safeHandler(
|
export const handler = safeHandler(
|
||||||
async (
|
async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,13 +1,13 @@
|
|||||||
import { ROLE, USER_STATUS } from '../../../common/utils/constants/common.constant';
|
import { ROLE, USER_STATUS } from '../../../common/utils/constants/common.constant';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { generateOtpHelper } from '../../../common/utils/helper/sendOtp';
|
import { generateOtpHelper } from '../../../common/utils/helper/sendOtp';
|
||||||
import { MinglarService } from './../services/minglar.service';
|
import { MinglarService } from './../services/minglar.service';
|
||||||
|
import { sendOtpEmailForMinglarAdmin } from '../services/sendOTPEmail.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
@@ -27,11 +27,15 @@ export const handler = safeHandler(async (
|
|||||||
if (!email) {
|
if (!email) {
|
||||||
throw new ApiError(400, 'Email is required');
|
throw new ApiError(400, 'Email is required');
|
||||||
}
|
}
|
||||||
|
console.log(email, " -: Email")
|
||||||
|
|
||||||
const user = await prismaService.user.findUnique({
|
const emailToLowerCase = email.toLowerCase()
|
||||||
where: { emailAddress: email, isActive: true, userStatus: USER_STATUS.INVITED },
|
|
||||||
|
const user = await prismaClient.user.findUnique({
|
||||||
|
where: { emailAddress: emailToLowerCase, isActive: true, userStatus: USER_STATUS.INVITED },
|
||||||
select: { emailAddress: true, id: true, userPassword: true, roleXid: true },
|
select: { emailAddress: true, id: true, userPassword: true, roleXid: true },
|
||||||
});
|
});
|
||||||
|
console.log(user, "sljdfjdf")
|
||||||
|
|
||||||
if (!user) {
|
if (!user) {
|
||||||
throw new ApiError(403, 'You are not allowed to register directly. Please contact minglar admin.');
|
throw new ApiError(403, 'You are not allowed to register directly. Please contact minglar admin.');
|
||||||
@@ -54,7 +58,7 @@ export const handler = safeHandler(async (
|
|||||||
}
|
}
|
||||||
|
|
||||||
const otpResult = await generateOtpHelper(
|
const otpResult = await generateOtpHelper(
|
||||||
prismaService, // ⭐ pass Prisma from here
|
prismaClient, // ⭐ pass Prisma from here
|
||||||
Number(newUser?.id),
|
Number(newUser?.id),
|
||||||
newUser?.emailAddress,
|
newUser?.emailAddress,
|
||||||
'Register',
|
'Register',
|
||||||
@@ -67,7 +71,7 @@ export const handler = safeHandler(async (
|
|||||||
throw new ApiError(500, 'Failed to send OTP');
|
throw new ApiError(500, 'Failed to send OTP');
|
||||||
}
|
}
|
||||||
|
|
||||||
// await sendOtpEmailForMinglarAdmin(newUser?.emailAddress, otpResult.otp);
|
await sendOtpEmailForMinglarAdmin(newUser?.emailAddress, otpResult.otp);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
statusCode: 200,
|
statusCode: 200,
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -4,14 +4,13 @@ import {
|
|||||||
APIGatewayProxyResult,
|
APIGatewayProxyResult,
|
||||||
Context,
|
Context,
|
||||||
} from 'aws-lambda';
|
} from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(
|
export const handler = safeHandler(
|
||||||
async (
|
async (
|
||||||
|
|||||||
@@ -4,14 +4,13 @@ import {
|
|||||||
APIGatewayProxyResult,
|
APIGatewayProxyResult,
|
||||||
Context,
|
Context,
|
||||||
} from 'aws-lambda';
|
} from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
import { paginationService } from '../../../../../common/utils/pagination/pagination.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(
|
export const handler = safeHandler(
|
||||||
async (
|
async (
|
||||||
|
|||||||
@@ -1,14 +1,14 @@
|
|||||||
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
import { verifyOnlyMinglarAdminToken } from '../../../../../common/middlewares/jwt/authForOnlyMinglarAdmin';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../../../common/database/prisma.service';
|
import { prismaClient } from '../../../../../common/database/prisma.lambda.service';
|
||||||
import { ROLE } from '../../../../../common/utils/constants/common.constant';
|
import { ROLE } from '../../../../../common/utils/constants/common.constant';
|
||||||
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../../../common/utils/helper/ApiError';
|
import ApiError from '../../../../../common/utils/helper/ApiError';
|
||||||
import { sendInvitationEmailForMinglarAdmin } from '../../../services/inviteTeammatesEmail.service';
|
import { sendInvitationEmailForMinglarAdmin } from '../../../services/inviteTeammatesEmail.service';
|
||||||
import { MinglarService } from '../../../services/minglar.service';
|
import { MinglarService } from '../../../services/minglar.service';
|
||||||
|
import config from '../../../../../config/config';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
interface InviteTeammateBody {
|
interface InviteTeammateBody {
|
||||||
emailAddress: string;
|
emailAddress: string;
|
||||||
@@ -61,6 +61,8 @@ export const handler = safeHandler(async (
|
|||||||
throw new ApiError(400, 'Role is required');
|
throw new ApiError(400, 'Role is required');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const emailToLowerCase = emailAddress.toLowerCase()
|
||||||
|
|
||||||
// Validate role is either Co_Admin or Account_Manager
|
// Validate role is either Co_Admin or Account_Manager
|
||||||
if (![ROLE.CO_ADMIN, ROLE.ACCOUNT_MANAGER].includes(roleXid)) {
|
if (![ROLE.CO_ADMIN, ROLE.ACCOUNT_MANAGER].includes(roleXid)) {
|
||||||
throw new ApiError(400, 'Invalid role. Only Co_Admin and Account_Manager roles can be assigned.');
|
throw new ApiError(400, 'Invalid role. Only Co_Admin and Account_Manager roles can be assigned.');
|
||||||
@@ -79,7 +81,7 @@ export const handler = safeHandler(async (
|
|||||||
|
|
||||||
// Use single service method that encapsulates the transaction
|
// Use single service method that encapsulates the transaction
|
||||||
await minglarService.inviteTeammate(
|
await minglarService.inviteTeammate(
|
||||||
emailAddress,
|
emailToLowerCase,
|
||||||
roleXid,
|
roleXid,
|
||||||
isFixedSalary,
|
isFixedSalary,
|
||||||
perValue || 0,
|
perValue || 0,
|
||||||
@@ -87,7 +89,7 @@ export const handler = safeHandler(async (
|
|||||||
);
|
);
|
||||||
|
|
||||||
// send email after transaction commits
|
// send email after transaction commits
|
||||||
await sendInvitationEmailForMinglarAdmin(emailAddress);
|
await sendInvitationEmailForMinglarAdmin(emailToLowerCase, config.AM_INVITATION_LINK);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
statusCode: 200,
|
statusCode: 200,
|
||||||
|
|||||||
@@ -2,15 +2,14 @@
|
|||||||
import config from '../../../config/config';
|
import config from '../../../config/config';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import AWS from 'aws-sdk';
|
import AWS from 'aws-sdk';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminToken } from '../../../common/middlewares/jwt/authForMinglarAdmin';
|
import { verifyMinglarAdminToken } from '../../../common/middlewares/jwt/authForMinglarAdmin';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { parseJsonField, parseMultipartFormData } from '../../../common/utils/helper/parseMultipartFormData';
|
import { parseJsonField, parseMultipartFormData } from '../../../common/utils/helper/parseMultipartFormData';
|
||||||
import { MinglarService } from '../services/minglar.service';
|
import { MinglarService } from '../services/minglar.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const minglarService = new MinglarService(prismaClient);
|
||||||
const minglarService = new MinglarService(prismaService);
|
|
||||||
|
|
||||||
const s3 = new AWS.S3({
|
const s3 = new AWS.S3({
|
||||||
region: config.aws.region,
|
region: config.aws.region,
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
import { Injectable } from '@nestjs/common';
|
import { Injectable } from '@nestjs/common';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { sendAMEmailForHostAssign } from './AMEmail.service';
|
import { sendAMEmailForHostAssign } from './AMEmail.service';
|
||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class AMNotificationService {
|
export class AMNotificationService {
|
||||||
constructor(private prisma: PrismaService) {}
|
private prisma = prismaClient;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Fetch account manager email by id and send assignment email.
|
* Fetch account manager email by id and send assignment email.
|
||||||
|
|||||||
@@ -1,8 +1,10 @@
|
|||||||
import { brevoService } from "@/common/email/brevoApi";
|
import { brevoService } from "../../../common/email/brevoApi";
|
||||||
import ApiError from "@/common/utils/helper/ApiError";
|
import ApiError from "../../../common/utils/helper/ApiError";
|
||||||
|
import config from "../../../config/config";
|
||||||
|
|
||||||
export async function sendEmailToHostForApprovedApplication(
|
export async function sendEmailToHostForApprovedApplication(
|
||||||
emailAddress: string,
|
emailAddress: string,
|
||||||
|
name: string
|
||||||
): Promise<{
|
): Promise<{
|
||||||
sent: boolean;
|
sent: boolean;
|
||||||
// messageId: string
|
// messageId: string
|
||||||
@@ -11,9 +13,11 @@ export async function sendEmailToHostForApprovedApplication(
|
|||||||
const subject = "Approval for your application";
|
const subject = "Approval for your application";
|
||||||
|
|
||||||
const htmlContent = `
|
const htmlContent = `
|
||||||
<p>Dear Host,</p>
|
<p>Dear ${name},</p>
|
||||||
<p>Congratulations, Your application to minglar admin has been approved.</p>
|
<p>Congratulations, Your application to minglar admin has been approved.</p>
|
||||||
<p>You can start onboarding your activities through the host panel.</p>
|
<p>You can start onboarding your activities through the host panel.</p>
|
||||||
|
<p> You can login to your account using the link below:<br/>
|
||||||
|
<strong>Link:</strong> ${config.HOST_LINK} </p>
|
||||||
<p>Best regards,<br/>Minglar Team</p>
|
<p>Best regards,<br/>Minglar Team</p>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
@@ -70,3 +74,41 @@ export async function sendEmailToHostForMinglarApproval(
|
|||||||
throw new ApiError(500, "Failed to send OTP to minglar admin via email.");
|
throw new ApiError(500, "Failed to send OTP to minglar admin via email.");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export async function sendAMPQQAcceptanceMailtoHost(
|
||||||
|
emailAddress: string,
|
||||||
|
name: string
|
||||||
|
): Promise<{
|
||||||
|
sent: boolean;
|
||||||
|
// messageId: string
|
||||||
|
}> {
|
||||||
|
|
||||||
|
const subject = "Approval for your activity onboarding application";
|
||||||
|
|
||||||
|
const htmlContent = `
|
||||||
|
<p>Dear ${name},</p>
|
||||||
|
<p>Congratulations, Your activity onboarding application to minglar admin has been approved.</p>
|
||||||
|
<p>You can start adding other details of your activity through the host panel.</p>
|
||||||
|
<p> You can login to your account using the link below:<br/>
|
||||||
|
<strong>Link:</strong> ${config.HOST_LINK} </p>
|
||||||
|
<p>Best regards,<br/>Minglar Team</p>
|
||||||
|
`;
|
||||||
|
|
||||||
|
try {
|
||||||
|
const result = await brevoService.sendEmail({
|
||||||
|
recipients: [{ email: emailAddress }],
|
||||||
|
subject,
|
||||||
|
htmlContent,
|
||||||
|
});
|
||||||
|
|
||||||
|
console.log("📧 Email sent successfully:", result);
|
||||||
|
|
||||||
|
return {
|
||||||
|
sent: true,
|
||||||
|
// messageId: result.messageId
|
||||||
|
};
|
||||||
|
} catch (err) {
|
||||||
|
console.error("Brevo email send failed:", err);
|
||||||
|
throw new ApiError(500, "Failed to send OTP to minglar admin via email.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ import ApiError from "@/common/utils/helper/ApiError";
|
|||||||
|
|
||||||
export async function sendInvitationEmailForMinglarAdmin(
|
export async function sendInvitationEmailForMinglarAdmin(
|
||||||
emailAddress: string,
|
emailAddress: string,
|
||||||
|
link: string
|
||||||
): Promise<{
|
): Promise<{
|
||||||
sent: boolean;
|
sent: boolean;
|
||||||
// messageId: string
|
// messageId: string
|
||||||
@@ -11,9 +12,19 @@ export async function sendInvitationEmailForMinglarAdmin(
|
|||||||
const subject = "Minglar Admin: Your Team Invitation";
|
const subject = "Minglar Admin: Your Team Invitation";
|
||||||
|
|
||||||
const htmlContent = `
|
const htmlContent = `
|
||||||
<p>Dear,</p>
|
<p>Hi there,</p>
|
||||||
<p>You are invited to join the Minglar Admin team. Please click the link below to create your account.</p>
|
<p>We're excited to invite you to join the <strong>Minglar Admin Team</strong>!<br/>
|
||||||
<p>Best regards,<br/>Minglar Admin Team</p>
|
Please use the link below to set up your account and get started.</p>
|
||||||
|
|
||||||
|
<p><strong>Access Your Invitation:</strong><br/>
|
||||||
|
<a href="${link}">${link}</a></p>
|
||||||
|
|
||||||
|
<p>If you have any questions or need assistance, feel free to reach out — we’re here to help.<br/>
|
||||||
|
We look forward to having you on board!</p>
|
||||||
|
|
||||||
|
<p>Welcome aboard!<br/>
|
||||||
|
<strong>The Minglar Admin Team</strong></p>
|
||||||
|
|
||||||
`;
|
`;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -26,6 +26,7 @@ import { Injectable } from '@nestjs/common';
|
|||||||
import { User } from '@prisma/client';
|
import { User } from '@prisma/client';
|
||||||
import * as bcrypt from 'bcryptjs';
|
import * as bcrypt from 'bcryptjs';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { PrismaService } from '../../../common/database/prisma.service';
|
||||||
|
import { PrismaClient } from '@prisma/client';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { CreateMinglarDto, UpdateMinglarDto } from '../dto/minglar.dto';
|
import { CreateMinglarDto, UpdateMinglarDto } from '../dto/minglar.dto';
|
||||||
import { sendAMEmailForHostAssign } from './AMEmail.service';
|
import { sendAMEmailForHostAssign } from './AMEmail.service';
|
||||||
@@ -34,7 +35,7 @@ const bucket = config.aws.bucketName;
|
|||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class MinglarService {
|
export class MinglarService {
|
||||||
constructor(private prisma: PrismaService) { }
|
constructor(private prisma: PrismaService | PrismaClient) { }
|
||||||
|
|
||||||
async createPassword(user_xid: number, password: string): Promise<boolean> {
|
async createPassword(user_xid: number, password: string): Promise<boolean> {
|
||||||
// Find user by id
|
// Find user by id
|
||||||
@@ -135,10 +136,21 @@ export class MinglarService {
|
|||||||
return this.prisma.user.findUnique({ where: { emailAddress: email } });
|
return this.prisma.user.findUnique({ where: { emailAddress: email } });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async getHostXidByActivityId(activityId: number) {
|
||||||
|
const activityDetails = await this.prisma.activities.findFirst({
|
||||||
|
where: { id: activityId }
|
||||||
|
})
|
||||||
|
return activityDetails.hostXid;
|
||||||
|
}
|
||||||
|
|
||||||
async getUserDetails(id: number) {
|
async getUserDetails(id: number) {
|
||||||
return await this.prisma.user.findUnique({
|
const hostDetail = await this.prisma.hostHeader.findFirst({
|
||||||
where: { id: id },
|
where: { id: id }
|
||||||
|
})
|
||||||
|
const userDetails = await this.prisma.user.findUnique({
|
||||||
|
where: { id: hostDetail.userXid },
|
||||||
});
|
});
|
||||||
|
return userDetails;
|
||||||
}
|
}
|
||||||
|
|
||||||
async verifyHostOtp(email: string, otp: string): Promise<boolean> {
|
async verifyHostOtp(email: string, otp: string): Promise<boolean> {
|
||||||
@@ -260,6 +272,7 @@ export class MinglarService {
|
|||||||
async getAllHostActivityForMinglar(search?: string, hostXid?: number, paginationOptions?: { page: number; limit: number; skip: number }) {
|
async getAllHostActivityForMinglar(search?: string, hostXid?: number, paginationOptions?: { page: number; limit: number; skip: number }) {
|
||||||
const whereClause: any = {
|
const whereClause: any = {
|
||||||
isActive: true,
|
isActive: true,
|
||||||
|
activityInternalStatus: { notIn: [ACTIVITY_INTERNAL_STATUS.DRAFT_PQ] },
|
||||||
...(hostXid ? { hostXid } : {}),
|
...(hostXid ? { hostXid } : {}),
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -600,6 +613,7 @@ export class MinglarService {
|
|||||||
mobileNumber: true,
|
mobileNumber: true,
|
||||||
dateOfBirth: true,
|
dateOfBirth: true,
|
||||||
profileImage: true,
|
profileImage: true,
|
||||||
|
roleXid: true,
|
||||||
userAddressDetails: {
|
userAddressDetails: {
|
||||||
where: { isActive: true },
|
where: { isActive: true },
|
||||||
take: 1,
|
take: 1,
|
||||||
@@ -628,51 +642,10 @@ export class MinglarService {
|
|||||||
throw new ApiError(404, 'User not found after update');
|
throw new ApiError(404, 'User not found after update');
|
||||||
}
|
}
|
||||||
|
|
||||||
// 5. Calculate profile completion percentage
|
|
||||||
// let percentage = 0;
|
|
||||||
|
|
||||||
// // Profile Image: 15%
|
|
||||||
// if (updatedUser.profileImage) percentage += 15;
|
|
||||||
|
|
||||||
// // Name and Phone Number: 15%
|
|
||||||
// if (
|
|
||||||
// updatedUser.firstName &&
|
|
||||||
// updatedUser.lastName &&
|
|
||||||
// updatedUser.mobileNumber
|
|
||||||
// ) {
|
|
||||||
// percentage += 15;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// // Location Info: 25%
|
|
||||||
// if (updatedUser.userAddressDetails.length > 0) {
|
|
||||||
// const address = updatedUser.userAddressDetails[0];
|
|
||||||
// if (
|
|
||||||
// address.address1 &&
|
|
||||||
// address.stateXid &&
|
|
||||||
// address.countryXid &&
|
|
||||||
// address.cityXid &&
|
|
||||||
// address.pinCode
|
|
||||||
// ) {
|
|
||||||
// percentage += 25;
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
|
|
||||||
// // Documents: 45%
|
|
||||||
// if (updatedUser.userDocuments.length >= 2) {
|
|
||||||
// percentage += 45;
|
|
||||||
// } else if (updatedUser.userDocuments.length === 1) {
|
|
||||||
// percentage += 22.5;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// const profilePercentage = Math.min(percentage, 100);
|
|
||||||
|
|
||||||
// Update profile completion status
|
|
||||||
// if (profilePercentage > 75) {
|
|
||||||
await tx.user.update({
|
await tx.user.update({
|
||||||
where: { id: userId },
|
where: { id: userId },
|
||||||
data: { isProfileUpdated: true },
|
data: { isProfileUpdated: true },
|
||||||
});
|
});
|
||||||
// }
|
|
||||||
|
|
||||||
console.log('Transaction completed successfully');
|
console.log('Transaction completed successfully');
|
||||||
|
|
||||||
@@ -684,6 +657,7 @@ export class MinglarService {
|
|||||||
mobileNumber: updatedUser.mobileNumber,
|
mobileNumber: updatedUser.mobileNumber,
|
||||||
dateOfBirth: updatedUser.dateOfBirth,
|
dateOfBirth: updatedUser.dateOfBirth,
|
||||||
profileImage: updatedUser.profileImage,
|
profileImage: updatedUser.profileImage,
|
||||||
|
roleXid: updatedUser.roleXid,
|
||||||
},
|
},
|
||||||
address: updatedUser.userAddressDetails[0] || null,
|
address: updatedUser.userAddressDetails[0] || null,
|
||||||
documents: updatedUser.userDocuments,
|
documents: updatedUser.userDocuments,
|
||||||
@@ -1449,6 +1423,25 @@ export class MinglarService {
|
|||||||
return suggestions;
|
return suggestions;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async getSuggestionsForAM(hostXid: number) {
|
||||||
|
const suggestions = await this.prisma.hostSuggestion.findMany({
|
||||||
|
where: { hostXid: hostXid, isreviewed: false, isActive: true },
|
||||||
|
select: {
|
||||||
|
id: true,
|
||||||
|
title: true,
|
||||||
|
comments: true,
|
||||||
|
isparent: true,
|
||||||
|
isreviewed: true,
|
||||||
|
reviewOn: true,
|
||||||
|
},
|
||||||
|
orderBy: {
|
||||||
|
id: 'asc',
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
return suggestions;
|
||||||
|
}
|
||||||
|
|
||||||
async acceptHostApplication(host_xid: number, user_xid: number) {
|
async acceptHostApplication(host_xid: number, user_xid: number) {
|
||||||
return await this.prisma.$transaction(async (tx) => {
|
return await this.prisma.$transaction(async (tx) => {
|
||||||
await this.prisma.hostHeader.update({
|
await this.prisma.hostHeader.update({
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
import { brevoService } from "@/common/email/brevoApi";
|
import { brevoService } from "../../../common/email/brevoApi";
|
||||||
import ApiError from "@/common/utils/helper/ApiError";
|
import ApiError from "../../../common/utils/helper/ApiError";
|
||||||
|
import config from "../../../config/config";
|
||||||
|
|
||||||
export async function sendEmailToHostForRejectedApplication(
|
export async function sendEmailToHostForRejectedApplication(
|
||||||
emailAddress: string,
|
emailAddress: string,
|
||||||
@@ -38,6 +39,7 @@ export async function sendEmailToHostForRejectedApplication(
|
|||||||
|
|
||||||
export async function sendAMRejectionMailtoHost(
|
export async function sendAMRejectionMailtoHost(
|
||||||
emailAddress: string,
|
emailAddress: string,
|
||||||
|
name: string
|
||||||
): Promise<{
|
): Promise<{
|
||||||
sent: boolean;
|
sent: boolean;
|
||||||
// messageId: string
|
// messageId: string
|
||||||
@@ -46,11 +48,60 @@ export async function sendAMRejectionMailtoHost(
|
|||||||
const subject = "Improvement of your application";
|
const subject = "Improvement of your application";
|
||||||
|
|
||||||
const htmlContent = `
|
const htmlContent = `
|
||||||
<p>Dear Host,</p>
|
<p>Dear ${name},</p>
|
||||||
<p>Your account manager has made some suggestions on your application.<br/>
|
<p> Your account manager has reviewed your application and provided some suggestions. <br/>
|
||||||
Please improve it and re-submit the application to onboard on minglar.</p>
|
Please make the necessary improvements and re-submit your application to proceed with the onboarding process on Minglar.</p>
|
||||||
<p>If you have any questions please contact to minglar admin.</p>
|
<p> You may access your application using the link below:<br/>
|
||||||
<p>Best regards,<br/>Minglar Team</p>
|
<strong>Link:</strong> ${config.HOST_LINK} </p>
|
||||||
|
<p> If you have any questions, please feel free to contact the Minglar Support Team. </p>
|
||||||
|
<p> Best regards,<br/>
|
||||||
|
<strong>Minglar Team</strong> </p>
|
||||||
|
`;
|
||||||
|
|
||||||
|
try {
|
||||||
|
const result = await brevoService.sendEmail({
|
||||||
|
recipients: [{ email: emailAddress }],
|
||||||
|
subject,
|
||||||
|
htmlContent,
|
||||||
|
});
|
||||||
|
|
||||||
|
console.log("📧 Email sent successfully:", result);
|
||||||
|
|
||||||
|
return {
|
||||||
|
sent: true,
|
||||||
|
// messageId: result.messageId
|
||||||
|
};
|
||||||
|
} catch (err) {
|
||||||
|
console.error("Brevo email send failed:", err);
|
||||||
|
throw new ApiError(500, "Failed to send OTP to minglar admin via email.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
export async function sendAMPQQRejectionMailtoHost(
|
||||||
|
emailAddress: string,
|
||||||
|
name: string
|
||||||
|
): Promise<{
|
||||||
|
sent: boolean;
|
||||||
|
// messageId: string
|
||||||
|
}> {
|
||||||
|
|
||||||
|
const subject = "Improvement of your activity onboarding application";
|
||||||
|
|
||||||
|
const htmlContent = `
|
||||||
|
<p>Dear ${name},</p>
|
||||||
|
|
||||||
|
<p>Your account manager has reviewed your activity application and provided some suggestions.<br/>
|
||||||
|
Please make the necessary improvements and re-submit your activity application along with the pre-qualification answers to proceed with the onboarding process on Minglar.</p>
|
||||||
|
|
||||||
|
<p>You may access your activity onboarding application using the link below:<br/>
|
||||||
|
<strong>Link:</strong> ${config.HOST_LINK}</p>
|
||||||
|
|
||||||
|
<p>If you have any questions, please feel free to contact the Minglar Support Team.</p>
|
||||||
|
|
||||||
|
<p>Best regards,<br/>
|
||||||
|
<strong>Minglar Team</strong></p>
|
||||||
|
|
||||||
`;
|
`;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
import { PrismaService } from "../../../common/database/prisma.service";
|
import { PrismaClient } from '@prisma/client';
|
||||||
import jwt, { JwtPayload } from "jsonwebtoken";
|
import jwt, { JwtPayload } from "jsonwebtoken";
|
||||||
import moment from "moment";
|
import moment from "moment";
|
||||||
import config from "../../../config/config";
|
import config from "../../../config/config";
|
||||||
|
|
||||||
export class TokenService {
|
export class TokenService {
|
||||||
constructor(private readonly prisma: PrismaService = new PrismaService()) {}
|
constructor(private prisma: PrismaClient) { }
|
||||||
|
|
||||||
private generateToken(
|
private generateToken(
|
||||||
user_xid: number,
|
user_xid: number,
|
||||||
|
|||||||
@@ -0,0 +1,38 @@
|
|||||||
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
|
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
||||||
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
|
import { PrePopulateService } from '../services/prepopulate.service';
|
||||||
|
|
||||||
|
const prePopulateService = new PrePopulateService(prismaClient);
|
||||||
|
|
||||||
|
export const handler = safeHandler(async (
|
||||||
|
event: APIGatewayProxyEvent,
|
||||||
|
context?: Context
|
||||||
|
): Promise<APIGatewayProxyResult> => {
|
||||||
|
// Extract token from headers
|
||||||
|
const token = event.headers['x-auth-token'] || event.headers['X-Auth-Token']
|
||||||
|
if (!token) {
|
||||||
|
throw new ApiError(400, 'This is a protected route. Please provide a valid token.');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Authenticate user using the shared authForHost function
|
||||||
|
await verifyMinglarAdminHostToken(token);
|
||||||
|
|
||||||
|
const result = await prePopulateService.getAllPrePopulateDataForAddActivity();
|
||||||
|
|
||||||
|
return {
|
||||||
|
statusCode: 200,
|
||||||
|
headers: {
|
||||||
|
'Content-Type': 'application/json',
|
||||||
|
'Access-Control-Allow-Origin': '*',
|
||||||
|
},
|
||||||
|
body: JSON.stringify({
|
||||||
|
success: true,
|
||||||
|
message: 'Data retrieved successfully',
|
||||||
|
data: result,
|
||||||
|
}),
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
@@ -1,12 +1,11 @@
|
|||||||
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { PrePopulateService } from '../services/prepopulate.service';
|
import { PrePopulateService } from '../services/prepopulate.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const prePopulateService = new PrePopulateService(prismaClient);
|
||||||
const prePopulateService = new PrePopulateService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { PrePopulateService } from '../services/prepopulate.service';
|
import { PrePopulateService } from '../services/prepopulate.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const prePopulateService = new PrePopulateService(prismaClient);
|
||||||
const prePopulateService = new PrePopulateService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { PrePopulateService } from '../services/prepopulate.service';
|
import { PrePopulateService } from '../services/prepopulate.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const prePopulateService = new PrePopulateService(prismaClient);
|
||||||
const prePopulateService = new PrePopulateService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from 'aws-lambda';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { prismaClient } from '../../../common/database/prisma.lambda.service';
|
||||||
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
import { verifyMinglarAdminHostToken } from '../../../common/middlewares/jwt/authForMinglarAdminHost';
|
||||||
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
import { safeHandler } from '../../../common/utils/handlers/safeHandler';
|
||||||
import ApiError from '../../../common/utils/helper/ApiError';
|
import ApiError from '../../../common/utils/helper/ApiError';
|
||||||
import { PrePopulateService } from '../services/prepopulate.service';
|
import { PrePopulateService } from '../services/prepopulate.service';
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const prePopulateService = new PrePopulateService(prismaClient);
|
||||||
const prePopulateService = new PrePopulateService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from "aws-lambda";
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from "aws-lambda";
|
||||||
import { PrismaService } from "../../../common/database/prisma.service";
|
import { prismaClient } from "../../../common/database/prisma.lambda.service";
|
||||||
import { verifyMinglarAdminHostToken } from "../../../common/middlewares/jwt/authForMinglarAdminHost";
|
import { verifyMinglarAdminHostToken } from "../../../common/middlewares/jwt/authForMinglarAdminHost";
|
||||||
import { safeHandler } from "../../../common/utils/handlers/safeHandler";
|
import { safeHandler } from "../../../common/utils/handlers/safeHandler";
|
||||||
import ApiError from "../../../common/utils/helper/ApiError";
|
import ApiError from "../../../common/utils/helper/ApiError";
|
||||||
import { PrePopulateService } from "../services/prepopulate.service";
|
import { PrePopulateService } from "../services/prepopulate.service";
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const prePopulateService = new PrePopulateService(prismaClient);
|
||||||
const prePopulateService = new PrePopulateService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,12 +1,11 @@
|
|||||||
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from "aws-lambda";
|
import { APIGatewayProxyEvent, APIGatewayProxyResult, Context } from "aws-lambda";
|
||||||
import { PrismaService } from "../../../common/database/prisma.service";
|
import { prismaClient } from "../../../common/database/prisma.lambda.service";
|
||||||
import { verifyMinglarAdminHostToken } from "../../../common/middlewares/jwt/authForMinglarAdminHost";
|
import { verifyMinglarAdminHostToken } from "../../../common/middlewares/jwt/authForMinglarAdminHost";
|
||||||
import { safeHandler } from "../../../common/utils/handlers/safeHandler";
|
import { safeHandler } from "../../../common/utils/handlers/safeHandler";
|
||||||
import ApiError from "../../../common/utils/helper/ApiError";
|
import ApiError from "../../../common/utils/helper/ApiError";
|
||||||
import { PrePopulateService } from "../services/prepopulate.service";
|
import { PrePopulateService } from "../services/prepopulate.service";
|
||||||
|
|
||||||
const prismaService = new PrismaService();
|
const prePopulateService = new PrePopulateService(prismaClient);
|
||||||
const prePopulateService = new PrePopulateService(prismaService);
|
|
||||||
|
|
||||||
export const handler = safeHandler(async (
|
export const handler = safeHandler(async (
|
||||||
event: APIGatewayProxyEvent,
|
event: APIGatewayProxyEvent,
|
||||||
|
|||||||
@@ -1,9 +1,8 @@
|
|||||||
import { Injectable } from '@nestjs/common';
|
import { Injectable } from '@nestjs/common';
|
||||||
import { PrismaService } from '../../../common/database/prisma.service';
|
import { PrismaClient } from '@prisma/client';
|
||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class PrePopulateService {
|
export class PrePopulateService {
|
||||||
constructor(private prisma: PrismaService) { }
|
constructor(private prisma: PrismaClient) { }
|
||||||
|
|
||||||
async getAllBankDetails() {
|
async getAllBankDetails() {
|
||||||
return await this.prisma.banks.findMany({
|
return await this.prisma.banks.findMany({
|
||||||
@@ -142,4 +141,62 @@ export class PrePopulateService {
|
|||||||
},
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async getAllPrePopulateDataForAddActivity() {
|
||||||
|
const [
|
||||||
|
foodType,
|
||||||
|
cuisineDetails,
|
||||||
|
vehicleType,
|
||||||
|
navigationMode,
|
||||||
|
taxDetails,
|
||||||
|
energyLevel,
|
||||||
|
aminitiesDetails,
|
||||||
|
allowedEntryType,
|
||||||
|
ageRestrictionDetails
|
||||||
|
] =
|
||||||
|
await this.prisma.$transaction([
|
||||||
|
this.prisma.foodTypes.findMany({
|
||||||
|
where: { isActive: true },
|
||||||
|
orderBy: { foodTypeName: 'asc' },
|
||||||
|
}),
|
||||||
|
this.prisma.foodCuisines.findMany({
|
||||||
|
where: { isActive: true },
|
||||||
|
}),
|
||||||
|
this.prisma.transportModes.findMany({
|
||||||
|
where: { isActive: true },
|
||||||
|
}),
|
||||||
|
this.prisma.navigationModes.findMany({
|
||||||
|
where: { isActive: true },
|
||||||
|
}),
|
||||||
|
this.prisma.taxes.findMany({
|
||||||
|
where: { isActive: true },
|
||||||
|
}),
|
||||||
|
this.prisma.energyLevels.findMany({
|
||||||
|
where: { isActive: true },
|
||||||
|
}),
|
||||||
|
this.prisma.amenities.findMany({
|
||||||
|
where: { isActive: true },
|
||||||
|
}),
|
||||||
|
this.prisma.allowedEntryTypes.findMany({
|
||||||
|
where: { isActive: true },
|
||||||
|
orderBy: { allowedEntryTypeName: 'asc' }
|
||||||
|
}),
|
||||||
|
this.prisma.ageRestrictions.findMany({
|
||||||
|
where: { isActive: true },
|
||||||
|
orderBy: { ageRestrictionName: 'asc' }
|
||||||
|
}),
|
||||||
|
]);
|
||||||
|
|
||||||
|
return {
|
||||||
|
foodType,
|
||||||
|
cuisineDetails,
|
||||||
|
vehicleType,
|
||||||
|
navigationMode,
|
||||||
|
taxDetails,
|
||||||
|
energyLevel,
|
||||||
|
aminitiesDetails,
|
||||||
|
allowedEntryType,
|
||||||
|
ageRestrictionDetails
|
||||||
|
};
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user