Skip to content

Commit

Permalink
Merge pull request #58 from iam-abin/dev
Browse files Browse the repository at this point in the history
Dev
  • Loading branch information
iam-abin authored Oct 8, 2024
2 parents f32974a + 69af732 commit 7e119f8
Show file tree
Hide file tree
Showing 25 changed files with 803 additions and 750 deletions.
1 change: 1 addition & 0 deletions admin/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import { JobUpdatedEventConsumer } from "./frameworks/utils/kafka-events/consume
import { UserCreatedEventConsumer } from "./frameworks/utils/kafka-events/consumers/user-created-consumer";
import { UserUpdatedEventConsumer } from "./frameworks/utils/kafka-events/consumers/user-updated-consumer";


import { kafkaClient } from "./config/kafka-connection";
import { JobDeletedEventConsumer } from "./frameworks/utils/kafka-events/consumers/job-deleted-consumer";
import { CandidateProfileUpdatedEventConsumer } from "./frameworks/utils/kafka-events/consumers/candidate-profile-updated-consumer";
Expand Down
18 changes: 9 additions & 9 deletions auth/src/config/db.ts
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
import { DatabaseConnectionError } from "@abijobportal/common";
import mongoose from "mongoose";

const connectDB = async (): Promise<void> => {
try {
await mongoose.connect(process.env.MONGO_URL_AUTH as string);
console.log("auth service connected to mongodb...");
} catch (error) {
console.error("auth service mongodb connection failed!!!!",error);
throw new DatabaseConnectionError()
}
const connectDB = async (): Promise<void> => {
try {
await mongoose.connect(process.env.MONGO_URL_AUTH as string);
console.log("auth service connected to mongodb...");
} catch (error) {
console.error("auth service mongodb connection failed!!!!", error);
throw new DatabaseConnectionError();
}
};

export { connectDB }
export { connectDB };
28 changes: 5 additions & 23 deletions auth/src/controllers/recruiter/signin.controller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,42 +16,24 @@ export = (dependencies: IDependenciesData) => {
const { email, password } = req.body;

// check user exist
const isExistingUser = await getUserByEmailUseCase(
dependencies
).execute(email);
const isExistingUser = await getUserByEmailUseCase( dependencies ).execute(email);

if (!isExistingUser) {
// return res.status(400).json({message:"Invalid email or password"})

throw new BadRequestError("Invalid email or password");
}



// check password is correct
const isSamePassword = await comparePassword(
password,
isExistingUser.password
);

if (!isSamePassword) {
// return res.status(400).json({message:"Invalid email or passwordd"})

throw new BadRequestError("Invalid email or passwordd");
}

if (isExistingUser.userType !== "recruiter") {
// return res.status(400).json({message:"Invalid email or password"})
if (!isSamePassword) throw new BadRequestError("Invalid email or passwordd");

throw new BadRequestError("Invalid Recruiter");
}


if (!isExistingUser.isActive) {
// return res.status(400).json({message:"Invalid email or passwordd"})

throw new BadRequestError("This is a blocked user");
}
if (isExistingUser.userType !== "recruiter") throw new BadRequestError("Invalid Recruiter");

if (!isExistingUser.isActive) throw new BadRequestError("This is a blocked user");

// Generate Jwt
const recruiterPayloadData = {
Expand Down
12 changes: 4 additions & 8 deletions auth/src/controllers/recruiter/signup.controller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,34 +3,30 @@ import { BadRequestError } from "@abijobportal/common";

import { IDependenciesData } from "../../frameworks/types/dependencyInterface";
import { generateEmailVerificationOtp, sendVerificationEmail } from "../../frameworks/utils/sendEmail";
import { IUserAttributes } from "../../frameworks/database/mongo/models/users";

export = (dependencies: IDependenciesData) => {
const {
useCases: { userSignupUseCase, getUserByEmailUseCase},
} = dependencies;

return async (req: Request, res: Response) => {
const { name, email, phone, password } = req.body;
const { name, email, phone, password } = req.body as Partial<IUserAttributes>;

const isExistingUser = await getUserByEmailUseCase(
dependencies
).execute(email);

if (isExistingUser && isExistingUser.isVarified) {
// return res.status(400).json({message:"Email already exist"})
throw new BadRequestError("Email already exist");
}
if (isExistingUser && isExistingUser.isVarified) throw new BadRequestError("Email already exist");

const subject = "Verify Your Email";
const topic = "Enter the 6 digit otp to verify your email"
if(isExistingUser && !isExistingUser.isVarified){
const response = await sendVerificationEmail(isExistingUser.email, isExistingUser.otp ,subject ,topic);

return res.status(200).json({"message": "An email is send to your email, please verify."});
}
// userData.password = await // password hashing can be done in schema or model

const {otp, expiryTime} = generateEmailVerificationOtp()
const { otp } = generateEmailVerificationOtp()

const newUser = await userSignupUseCase(dependencies).execute({
name,
Expand Down
6 changes: 3 additions & 3 deletions auth/src/frameworks/database/mongo/models/users.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import mongoose from "mongoose";
import { generateHashedPassword } from "../../../utils/password";

// 1. An interface that describes the properties ,that are requried to create a new User
interface UserAttributes {
export interface IUserAttributes {
name: string;
email: string;
phone: number;
Expand Down Expand Up @@ -99,11 +99,11 @@ userSchema.pre("save", async function (next) {

// 4. An interface that describes the properties ,that a user model has
interface UserModel extends mongoose.Model<UserDocument> {
buildUser(attributes: UserAttributes): UserDocument;
buildUser(attributes: IUserAttributes): UserDocument;
}

// 5.In Mongoose, you can also add custom functions to a model using statics.
userSchema.statics.buildUser = (attributes: UserAttributes) => {
userSchema.statics.buildUser = (attributes: IUserAttributes) => {
return new UserModel({
// to create a new user document
name: attributes.name,
Expand Down
2 changes: 1 addition & 1 deletion auth/src/frameworks/utils/sendEmail.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ export const sendVerificationEmail = async (
secure: false,
auth: {
user: "[email protected]",
pass: "frjn aczl fyet pxaj",
pass: "dogu rtwq gxiv dton",
},
connectionTimeout: 10000,
});
Expand Down
1 change: 0 additions & 1 deletion auth/src/useCases/authusecases/getUserByEmail.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ export = (dependencies: IDependenciesData) => {
if (!usersRepository) throw new Error("usersRepository should exist in dependencies");

const execute = async (email: string) => {

return await usersRepository.getByEmail(email);
};

Expand Down
14 changes: 7 additions & 7 deletions auth/src/useCases/authusecases/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,11 @@ import userSignupUseCase from "./userSignup";
import updatePasswordUseCase from "./updatePassword";
import setNodemailerOtpUseCase from "./setNodemailerOtp";
export {
checkEmailVerificationOtpUseCase,
getEmailVerifyOtpUseCase,
getUserByEmailUseCase,
getUserByPhoneUseCase,
userSignupUseCase,
updatePasswordUseCase,
setNodemailerOtpUseCase
checkEmailVerificationOtpUseCase,
getEmailVerifyOtpUseCase,
getUserByEmailUseCase,
getUserByPhoneUseCase,
userSignupUseCase,
updatePasswordUseCase,
setNodemailerOtpUseCase,
};
4 changes: 1 addition & 3 deletions auth/src/useCases/authusecases/updatePassword.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,7 @@ import { IUpdatePasswordInput } from "../../frameworks/types/userInterface";
export = (dependencies: IDependenciesData)=>{
const { repositories:{usersRepository} } = dependencies;

if (!usersRepository) {
throw new Error("usersRepository should exist in dependencies");
}
if (!usersRepository) throw new Error("usersRepository should exist in dependencies");

const execute = ({id, password}: IUpdatePasswordInput)=>{
return usersRepository.updatePassword({id, password})
Expand Down
4 changes: 0 additions & 4 deletions chat/src/entities/users.ts
Original file line number Diff line number Diff line change
@@ -1,28 +1,24 @@
interface UserInterface {
userId: string;
name: string;
email: string;
profileImgUrl?: string;
userType: string;
}

export class User {
userId: string;
name: string;
email: string;
profileImgUrl?: string;
userType: string;

constructor({
userId,
name,
email,
profileImgUrl,
userType,
}: UserInterface) {
(this.userId = userId),
(this.name = name),
(this.email = email),
(this.profileImgUrl = profileImgUrl),
(this.userType = userType);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ interface NotificationAttributes {
senderId: string;
targetUserId: string;
message: string;
// email: string;
// profileImgUrl: number;
// userType: string;
}
Expand Down Expand Up @@ -64,7 +63,6 @@ notificationSchema.statics.buildNotification = (
senderId: attributes.senderId,
targetUserId: attributes.targetUserId,
message: attributes.message,
// email: attributes.email,
// profileImgUrl: attributes.profileImgUrl,
// userType: attributes.userType,
});
Expand Down
12 changes: 4 additions & 8 deletions chat/src/frameworks/database/mongo/models/users.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,16 +3,14 @@ import mongoose from "mongoose";
interface UserAttributes {
userId: string;
name: string;
email: string;
profileImgUrl: number;
profile_image: number;
userType: string;
}
// 2. An interface that describes the properties ,that a User Document has
interface UserDocument extends mongoose.Document {
// _id: mongoose.Schema.Types.ObjectId;
name: string;
email: string;
profileImgUrl: number;
profile_image: number;
userType: string;
isActive: boolean;
createdAt: string;
Expand All @@ -24,8 +22,7 @@ const userSchema = new mongoose.Schema(
{
// userId: mongoose.Schema.Types.ObjectId,
name: String,
email: String,
profileImgUrl: String,
profile_image: String,
userType: {
type: String,
required: true,
Expand Down Expand Up @@ -60,8 +57,7 @@ userSchema.statics.buildUser = (attributes: UserAttributes) => {
// to create a new user document
_id: attributes.userId,
name: attributes.name,
email: attributes.email,
profileImgUrl: attributes.profileImgUrl,
profile_image: attributes.profile_image,
userType: attributes.userType,
});
};
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import { Kafka, KafkaMessage } from "kafkajs";
import { KafkaConsumer, TOPICS, CANDIDATE_PROFILE_UPDATED_EVENT } from "@abijobportal/common";
import { handleMessage } from "../handleMessage";

export class CandidateProfileUpdatedEventConsumer extends KafkaConsumer<CANDIDATE_PROFILE_UPDATED_EVENT>{
topic: TOPICS.CANDIDATE_PROFILE_UPDATED_TOPIC = TOPICS.CANDIDATE_PROFILE_UPDATED_TOPIC;

groupId: string = "chat-3";

constructor(client: Kafka){
super(client);
}

async onMessage(data: CANDIDATE_PROFILE_UPDATED_EVENT['data'], topic: string, message: KafkaMessage): Promise<void> {

// dont need to check userType as every users are stored in one collection
handleMessage(data, topic, message )

}

}
35 changes: 24 additions & 11 deletions chat/src/frameworks/utils/kafka-events/handleMessage.ts
Original file line number Diff line number Diff line change
@@ -1,17 +1,30 @@
import userRepository from "../../repositories/mongo/user.repository";


export const handleMessage = (data: any, topic: string, message: any) => {
switch (topic) {
case "USER-CREATED-TOPIC":
userRepository.createUser(data);
break;
switch (topic) {
case "USER-CREATED-TOPIC":
userRepository.createUser(data);
break;

case "USER-UPDATED-TOPIC":
userRepository.updateUser(data.userId, data);
console.log(data);

break;

case "CANDIDATE-PROFILE-UPDATED-TOPIC":
console.log(data);
const userData = {
name: data.name,
profile_image: data.profile_image,
isActive: data.isActive,
};
console.log(userData);
userRepository.updateUser(data.userId, userData);

case "USER-UPDATED-TOPIC":
userRepository.updateUser(data.userId, data);
break;
break;

default:
break;
}
default:
break;
}
};
6 changes: 6 additions & 0 deletions chat/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { connectDB } from "./config/db";
import { kafkaClient } from "./config/kafka-connection";
import { app, httpServer } from "./frameworks/express/app";
import { CandidateProfileUpdatedEventConsumer } from "./frameworks/utils/kafka-events/consumers/candidate-profile-updated-consumer";
import { UserCreatedEventConsumer } from "./frameworks/utils/kafka-events/consumers/user-created-consumer";
import { UserUpdatedEventConsumer } from "./frameworks/utils/kafka-events/consumers/user-updated-consumer";
import { setupSocketIO } from "./frameworks/webSocket/socket";
Expand Down Expand Up @@ -32,20 +33,25 @@ const start = async () => {
const userCreatedEvent = new UserCreatedEventConsumer(kafkaClient);

const userUpdatedEvent = new UserUpdatedEventConsumer(kafkaClient);

const candidateProfileUpdatedEvent = new CandidateProfileUpdatedEventConsumer(kafkaClient)

await userUpdatedEvent.subscribe();
await userCreatedEvent.subscribe();
await candidateProfileUpdatedEvent.subscribe();

httpServer.listen(3000, () => {
console.log("chat service Listening on port 3000....");
})
.on("error", async () => {
await userUpdatedEvent.disconnect();
await userCreatedEvent.disconnect();
await candidateProfileUpdatedEvent.disconnect();
})
.on("close", async () => {
await userUpdatedEvent.disconnect();
await userCreatedEvent.disconnect();
await candidateProfileUpdatedEvent.disconnect();
});
};

Expand Down
4 changes: 2 additions & 2 deletions client/src/axios/apiMethods/profile-service/candidate.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,8 @@ export const updateCandidateProfileApi = async (candidateProfileData: any): Prom
};


export const uploadCandidateImageProfileApi = async (userId: string,profileImageData: any): Promise<any> => {
const response: any = await candidateApiCalls("put", profileApiUrlConfig.uploadCandidateImageUrl, profileImageData, true);
export const uploadCandidateImageProfileApi = async (userId: string,profile_imageData: any): Promise<any> => {
const response: any = await candidateApiCalls("put", profileApiUrlConfig.uploadCandidateImageUrl, profile_imageData, true);
// isFileUpload is giving 'true' because we are sending a file to the backend.
return response.data;
};
Expand Down
Loading

0 comments on commit 7e119f8

Please sign in to comment.