Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/workflow.yml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ on:
- "**.js"
- "**.json"
- "**.yml"
branches: ["master", "dev_prod", "dev_featsUser"]
branches: ["master", "dev_prod", "dev_featsUser", "dev_featsProducts"]
pull_request:
branches: ["master", "dev_prod"]

Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
"test:actions": "node --test --experimental-test-coverage",
"dc:up": "docker compose up -d && docker compose logs -f prisma_tests",
"dc:down": "docker compose down --volumes --remove-orphans",
"setup:prisma": "npx prisma migrate deploy && npx prisma db push"
"setup:prisma": "npx prisma generate && npx prisma migrate deploy && npx prisma db push"
},
"repository": {
"type": "git",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,18 @@ CREATE TABLE "public"."Users" (
CONSTRAINT "Users_pkey" PRIMARY KEY ("user_id")
);

-- CreateTable
CREATE TABLE "public"."Products" (
"user_id" TEXT NOT NULL,
"product_id" TEXT NOT NULL,
"product_name" TEXT NOT NULL,
"price" DOUBLE PRECISION NOT NULL,
"category" TEXT NOT NULL,
"createdAt" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,

CONSTRAINT "Products_pkey" PRIMARY KEY ("product_id")
);

-- CreateTable
CREATE TABLE "public"."UserTokens" (
"id" TEXT NOT NULL,
Expand All @@ -21,5 +33,8 @@ CREATE TABLE "public"."UserTokens" (
-- CreateIndex
CREATE UNIQUE INDEX "Users_email_key" ON "public"."Users"("email");

-- AddForeignKey
ALTER TABLE "public"."Products" ADD CONSTRAINT "Products_user_id_fkey" FOREIGN KEY ("user_id") REFERENCES "public"."Users"("user_id") ON DELETE CASCADE ON UPDATE CASCADE;

-- AddForeignKey
ALTER TABLE "public"."UserTokens" ADD CONSTRAINT "UserTokens_user_id_fkey" FOREIGN KEY ("user_id") REFERENCES "public"."Users"("user_id") ON DELETE CASCADE ON UPDATE CASCADE;
11 changes: 11 additions & 0 deletions prisma/schema.prisma
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,20 @@ model Users {
email String @unique
password String
createdAt DateTime @default(now())
Products Products[]
UserToken UserTokens[]
}

model Products {
user_id String
product_id String @id @default(uuid())
product_name String
price Float @db.DoublePrecision
category String
createdAt DateTime @default(now())
user Users @relation(fields: [user_id], references: [user_id], onDelete: Cascade)
}

model UserTokens {
id String @id @default(uuid())
user_id String
Expand Down
64 changes: 64 additions & 0 deletions src/controllers/productsController.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
import { ProductsService } from "../services/productsService.js";
import { Middleware } from "../utils/auth/middleware.js";
import { decode } from "jsonwebtoken"
import { once } from "node:events";

export class ProductsController {
_productsService;
_userMiddleware;

constructor(productsService = new ProductsService, userMiddleware = new Middleware()) {
this._productsService = productsService;
this._userMiddleware = userMiddleware;
}

async createProduct(request, response) {

const checkToken = await this._userMiddleware.ensureUserAuthenthicated(request, response);

if(checkToken === true) {

const { product_name, price, category } = JSON.parse(await once(request, "data"));

if(product_name === "" || price === "" || category === "") {
response.writeHead(401);
return response.end(JSON.stringify({ message: "All data must have a value !" }));

}else if(typeof(product_name) !== "string" || typeof(category) !== "string") {
response.writeHead(401);
return response.end(JSON.stringify({ message: "ProductName and Cataegory must be a string !" }));

}else if(typeof(price) !== "number") {
response.writeHead(401);
return response.end(JSON.stringify({ message: "Price must be a float/decimal number !" }));
}

const authToken = request.headers.authorization;
const [, token] = authToken.split(' ');
const getUserId = decode(token);

const createProduct = await this._productsService.create({
product_name,
price,
category,
user_id: getUserId.user.user_id
});

return response.end(JSON.stringify({
product: {
user_id: createProduct.user_id,
product_id: createProduct.product_id,
product_name: createProduct.product_name,
price: createProduct.price,
category: createProduct.category,
createdAt: createProduct.createdAt
}
}));

}

response.writeHead(401);
return response.end(JSON.stringify({ message: checkToken }));
}

}
3 changes: 2 additions & 1 deletion src/controllers/userController.js
Original file line number Diff line number Diff line change
Expand Up @@ -142,7 +142,8 @@ export class UserController {
user_id: findUserById.user_id,
username: findUserById.username,
email: findUserById.email,
createdAt: findUserById.createdAt
createdAt: findUserById.createdAt,
products: findUserById.Products
}
}));

Expand Down
18 changes: 18 additions & 0 deletions src/models/productsModel.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import { PrismaService } from "../database/prisma/prismaService.js";

export class ProductsModelRepository {
_database;

constructor(prismaService = new PrismaService) {
this._database = prismaService;
}

async create(data) {
const create = await this._database._prismaService.products.create({
data: data
});

return create;
}

}
13 changes: 13 additions & 0 deletions src/models/userModel.js
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,19 @@ export class UserModelRepository {

}

async listUser(user_id) {
const listUser = await this._database._prismaService.users.findUnique({
where: {
user_id: user_id
},
include: {
Products: true
}
});

return listUser;
}

async updateUser(user_id, username) {
const update = await this._database._prismaService.users.update({
where: {
Expand Down
6 changes: 6 additions & 0 deletions src/routes/user.routes.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
import { UserController } from "../controllers/userController.js";
import { ProductsController } from "../controllers/productsController.js";

const userController = new UserController();
const productController = new ProductsController();

export class UserRoutes {

Expand Down Expand Up @@ -32,6 +34,10 @@ export class UserRoutes {
case "/deleteUser/":
await userController.deleteUser(request, response);
break;

case "/createProduct":
await productController.createProduct(request, response);
break;

default:
response.writeHead(404);
Expand Down
15 changes: 15 additions & 0 deletions src/services/productsService.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import { ProductsModelRepository } from "../models/productsModel.js";

export class ProductsService {
_productsModelRepository;

constructor(productsModelRepository = new ProductsModelRepository) {
this._productsModelRepository = productsModelRepository;
}

async create(data) {
const create = await this._productsModelRepository.create(data);
return create;
}

}
2 changes: 1 addition & 1 deletion src/services/userService.js
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ export class UserService {
}

async listUser(user_id) {
const find = await this._userRepository.findUserById(user_id);
const find = await this._userRepository.listUser(user_id);
return find;
}

Expand Down