From c48ec70638b5f220b4f6a35a74090cf8fcc97377 Mon Sep 17 00:00:00 2001 From: mahyargdz Date: Wed, 22 Jan 2025 10:34:52 +0330 Subject: [PATCH] chore: add docker file for build --- .env.example | 35 ++++++++++------- .github/workflows/deploy.yaml | 4 +- Dockerfile | 40 ++++++++++++++++++++ src/common/enums/message.enum.ts | 1 + src/modules/auth/DTO/loginPassword.dto.ts | 4 +- src/modules/auth/auth.controller.ts | 9 ++++- src/modules/auth/providers/auth.service.ts | 11 +++++- src/modules/users/providers/users.service.ts | 3 +- 8 files changed, 86 insertions(+), 21 deletions(-) create mode 100644 Dockerfile diff --git a/.env.example b/.env.example index 295917b..b21aa5e 100644 --- a/.env.example +++ b/.env.example @@ -2,22 +2,22 @@ NODE_ENV=development PORT=3500 -DB_HOST=localhost -DB_PORT=5432 -DB_NAME=danak-dsc -DB_USER=danak -DB_PASS=jkm3q2wux56RHYuTuKN11Too6+4pIpGQj3Q/fkNbahM +DB_HOST= +DB_PORT= +DB_NAME= +DB_USER= +DB_PASS= -URL=https://RestfulSms.com/api/UltraFastSend/direct + +PGADMIN_EMAIL=root@test.ir +PGADMIN_PASSWORD=password + + +SMS_API_URL=https://RestfulSms.com/api/UltraFastSend/direct SMS_API_KEY= SMS_SECRET= SMS_PATTERN_OTP= - - -PGADMIN_EMAIL=root@abrclick.ir -PGADMIN_PASSWORD=password - SMTP_HOST= SMTP_PORT= SMTP_USER= @@ -25,9 +25,18 @@ SMTP_PASS= MAIL_FROM= - REDIS_URI=redis://:@localhost:6379/0 CACHE_TTL=120000 + + THROTTLE_TTL=300000 -THROTTLE_LIMIT=10 \ No newline at end of file +THROTTLE_LIMIT=10 + + +JWT_SECRET_KEY=secret + +ACCESS_TOKEN_EXPIRE=1 #==> in hour +REFRESH_TOKEN_EXPIRE=3 #===> in days + + diff --git a/.github/workflows/deploy.yaml b/.github/workflows/deploy.yaml index 8d5a2e9..2e6da85 100644 --- a/.github/workflows/deploy.yaml +++ b/.github/workflows/deploy.yaml @@ -9,7 +9,7 @@ jobs: runs-on: ubuntu-latest env: - DEP_SERVER: "https://captain.run.danakcorp.com" + DANAK_SERVER: "https://captain.run.danakcorp.com" APP_TOKEN: 443dca14bd870283926a9ab3a0c6b41c463cb9423c654e9fbd9069059df9021a APP_NAME: danak-dsc-api GITHUB_TOKEN: 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 @@ -44,4 +44,4 @@ jobs: - name: deploy to server run: | - caprover deploy -a $CAPROVER_APP_NAME -u $DANAK_SERVER --appToken $APP_TOKEN -i "$IMAGE_URL" + caprover deploy -a $APP_NAME -u $DANAK_SERVER --appToken $APP_TOKEN -i "$IMAGE_URL" diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..0a8d236 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,40 @@ +# Stage 1: Build Stage +FROM node:22-alpine AS base + +RUN corepack enable && corepack prepare pnpm@latest --activate + +# Install tzdata to support timezone settings +RUN apk add --no-cache tzdata + +# Set the timezone to Asia/Tehran +RUN cp /usr/share/zoneinfo/Asia/Tehran /etc/localtime && echo "Asia/Tehran" > /etc/timezone + + +FROM base AS deps +WORKDIR /temp-deps +COPY package*.json pnpm-lock.yaml ./ +RUN pnpm install --frozen-lockfile --loglevel info + + +FROM base AS builder +WORKDIR /build +COPY . ./ +COPY --from=deps /temp-deps/node_modules ./node_modules +RUN if [ -f package.json ] && grep -q '"build":' package.json; then pnpm run build; fi +RUN pnpm install --prod --frozen-lockfile --loglevel info + +FROM base AS runner +RUN addgroup -S appgroup && adduser -S appuser -G appgroup +WORKDIR /app + +COPY . ./ +COPY --from=builder --chown=appuser:appgroup /build/ ./ + +RUN chown -R appuser:appgroup /app + +USER appuser + +ENV NODE_ENV=production +EXPOSE 3500 + +CMD ["npm", "start"] diff --git a/src/common/enums/message.enum.ts b/src/common/enums/message.enum.ts index 8e167d9..0322cc0 100644 --- a/src/common/enums/message.enum.ts +++ b/src/common/enums/message.enum.ts @@ -62,4 +62,5 @@ export const enum CommonMessage { VALIDITY_TYPE_REQUIRED = "نوع اعتبار سنجی مورد نیاز است", THIS_FILED_IS_REQUIRED = "این فیلد الزامی است", VALID_FOR_CHOOSE = "معتبر برای انتخاب", + USER_EXIST = "کاربر وجود دارد", } diff --git a/src/modules/auth/DTO/loginPassword.dto.ts b/src/modules/auth/DTO/loginPassword.dto.ts index e3fd475..ab41de7 100644 --- a/src/modules/auth/DTO/loginPassword.dto.ts +++ b/src/modules/auth/DTO/loginPassword.dto.ts @@ -1,4 +1,4 @@ -import { ApiProperty } from "@nestjs/swagger"; +import { ApiProperty, PickType } from "@nestjs/swagger"; import { IsEmail, IsNotEmpty, IsString } from "class-validator"; import { AuthMessage } from "../../../common/enums/message.enum"; @@ -14,3 +14,5 @@ export class LoginPasswordDTO { @ApiProperty({ type: "string", description: "password user", example: "@1234" }) password: string; } + +export class CheckUserExistDto extends PickType(LoginPasswordDTO, ["email"] as const) {} diff --git a/src/modules/auth/auth.controller.ts b/src/modules/auth/auth.controller.ts index 6ef1e8d..b4ff5f6 100644 --- a/src/modules/auth/auth.controller.ts +++ b/src/modules/auth/auth.controller.ts @@ -3,7 +3,7 @@ import { ApiOperation, ApiTags } from "@nestjs/swagger"; import { Throttle, ThrottlerGuard } from "@nestjs/throttler"; import { CompleteRegistrationDto } from "./DTO/complete-register.dto"; -import { LoginPasswordDTO } from "./DTO/loginPassword.dto"; +import { CheckUserExistDto, LoginPasswordDTO } from "./DTO/loginPassword.dto"; import { RequestOtpDto } from "./DTO/request-otp.dto"; import { VerifyOtpDto } from "./DTO/verify-otp.dto"; import { AuthService } from "./providers/auth.service"; @@ -43,6 +43,13 @@ export class AuthController { return this.authService.verifyLoginOtp(verifyOtpDto); } + @ApiOperation({ summary: "check if user email exist" }) + @HttpCode(HttpStatus.OK) + @Post("check") + checkUserExist(@Body() checkUserExistDto: CheckUserExistDto) { + return this.authService.checkUserExist(checkUserExistDto); + } + @ApiOperation({ summary: "login with password" }) @HttpCode(HttpStatus.OK) @Post("login/password") diff --git a/src/modules/auth/providers/auth.service.ts b/src/modules/auth/providers/auth.service.ts index e8a84d1..1a653db 100644 --- a/src/modules/auth/providers/auth.service.ts +++ b/src/modules/auth/providers/auth.service.ts @@ -1,12 +1,12 @@ import { BadRequestException, Injectable, Logger } from "@nestjs/common"; import { TokensService } from "./tokens.service"; -import { AuthMessage, UserMessage } from "../../../common/enums/message.enum"; +import { AuthMessage, CommonMessage, UserMessage } from "../../../common/enums/message.enum"; import { UsersService } from "../../users/providers/users.service"; import { OTPService } from "../../utils/providers/otp.service"; import { PasswordService } from "../../utils/providers/password.service"; import { CompleteRegistrationDto } from "../DTO/complete-register.dto"; -import { LoginPasswordDTO } from "../DTO/loginPassword.dto"; +import { CheckUserExistDto, LoginPasswordDTO } from "../DTO/loginPassword.dto"; import { RequestOtpDto } from "../DTO/request-otp.dto"; import { VerifyOtpDto } from "../DTO/verify-otp.dto"; @@ -77,6 +77,13 @@ export class AuthService { ...tokens, }; } + //****************** */ + + async checkUserExist(checkUserExistDto: CheckUserExistDto) { + const user = await this.usersService.findOneWithEmail(checkUserExistDto.email); + if (!user) throw new BadRequestException(UserMessage.USER_NOT_FOUND); + return { message: CommonMessage.USER_EXIST }; + } //****************** */ diff --git a/src/modules/users/providers/users.service.ts b/src/modules/users/providers/users.service.ts index 516d882..e9abbe8 100644 --- a/src/modules/users/providers/users.service.ts +++ b/src/modules/users/providers/users.service.ts @@ -40,9 +40,8 @@ export class UsersService { } /************************************************************ */ - async findOneWithEmail(email: string): Promise { + async findOneWithEmail(email: string): Promise { const user = await this.userRepository.findOneWithEmail(email); - if (!user) throw new BadRequestException(UserMessage.USER_NOT_FOUND); return user; } /************************************************************ */