diff --git a/modulo5/projeto-labook/template-projeto-labook/.gitignore b/modulo5/projeto-labook/template-projeto-labook/.gitignore new file mode 100644 index 0000000..51ef85c --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/.gitignore @@ -0,0 +1,4 @@ +.env +.DS_STORE +node_modules +build \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/package.json b/modulo5/projeto-labook/template-projeto-labook/package.json new file mode 100644 index 0000000..d4e7d06 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/package.json @@ -0,0 +1,36 @@ +{ + "name": "projeto-cookenu-backend", + "version": "1.0.0", + "description": "", + "main": "index.js", + "scripts": { + "start": "node ./build/index.js", + "build": "tsc", + "dev": "ts-node-dev ./src/index.ts", + "migrations": "tsc && node ./build/database/migrations/Migrations.js" + }, + "keywords": [], + "author": "", + "license": "ISC", + "devDependencies": { + "@types/cors": "^2.8.12", + "@types/express": "^4.17.13", + "@types/jsonwebtoken": "^8.5.8", + "@types/knex": "^0.16.1", + "@types/node": "^18.0.6", + "@types/uuid": "^8.3.4", + "@types/bcryptjs": "^2.4.2", + "ts-node-dev": "^2.0.0", + "typescript": "^4.7.4" + }, + "dependencies": { + "bcryptjs": "^2.4.3", + "cors": "^2.8.5", + "dotenv": "^16.0.1", + "express": "^4.18.1", + "jsonwebtoken": "^8.5.1", + "knex": "^2.2.0", + "mysql": "^2.18.1", + "uuid": "^8.3.2" + } +} diff --git a/modulo5/projeto-labook/template-projeto-labook/requests.rest b/modulo5/projeto-labook/template-projeto-labook/requests.rest new file mode 100644 index 0000000..ced738b --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/requests.rest @@ -0,0 +1,2 @@ +### Endpoint de teste +GET http://localhost:3003/ping \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/business/PingBusiness.ts b/modulo5/projeto-labook/template-projeto-labook/src/business/PingBusiness.ts new file mode 100644 index 0000000..d426790 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/business/PingBusiness.ts @@ -0,0 +1,9 @@ +export class PingBusiness { + public ping = async () => { + const response = { + message: "Pong!" + } + + return response + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/business/PostBusiness.ts b/modulo5/projeto-labook/template-projeto-labook/src/business/PostBusiness.ts new file mode 100644 index 0000000..5168dcb --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/business/PostBusiness.ts @@ -0,0 +1,12 @@ +import { PostDatabase } from "../database/PostDatabase" +import { Authenticator } from "../services/Authenticator" +import { IdGenerator } from "../services/IdGenerator" + +export class PostBusiness { + constructor( + private postDatabase: PostDatabase, + private idGenerator: IdGenerator, + private authenticator: Authenticator + ) {} + +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/business/UserBusiness.ts b/modulo5/projeto-labook/template-projeto-labook/src/business/UserBusiness.ts new file mode 100644 index 0000000..b297908 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/business/UserBusiness.ts @@ -0,0 +1,14 @@ +import { UserDatabase } from "../database/UserDatabase" +import { Authenticator } from "../services/Authenticator" +import { HashManager } from "../services/HashManager" +import { IdGenerator } from "../services/IdGenerator" + +export class UserBusiness { + constructor( + private userDatabase: UserDatabase, + private idGenerator: IdGenerator, + private hashManager: HashManager, + private authenticator: Authenticator + ) {} + +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/controller/PingController.ts b/modulo5/projeto-labook/template-projeto-labook/src/controller/PingController.ts new file mode 100644 index 0000000..9d79129 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/controller/PingController.ts @@ -0,0 +1,23 @@ +import { Request, Response } from "express" +import { PingBusiness } from "../business/PingBusiness" +import { BaseError } from "../errors/BaseError" + +export class PingController { + constructor( + private pingBusiness: PingBusiness + ) {} + + public ping = async (req: Request, res: Response) => { + try { + const response = await this.pingBusiness.ping() + + res.status(200).send(response) + } catch (error) { + console.log(error) + if (error instanceof BaseError) { + return res.status(error.statusCode).send({ message: error.message }) + } + res.status(500).send({ message: "Erro inesperado" }) + } + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/controller/PostController.ts b/modulo5/projeto-labook/template-projeto-labook/src/controller/PostController.ts new file mode 100644 index 0000000..6c51ab2 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/controller/PostController.ts @@ -0,0 +1,8 @@ +import { PostBusiness } from "../business/PostBusiness"; + +export class PostController { + constructor( + private postBusiness: PostBusiness + ) {} + +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/controller/UserController.ts b/modulo5/projeto-labook/template-projeto-labook/src/controller/UserController.ts new file mode 100644 index 0000000..96a09ed --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/controller/UserController.ts @@ -0,0 +1,8 @@ +import { UserBusiness } from "../business/UserBusiness"; + +export class UserController { + constructor( + private userBusiness: UserBusiness + ) {} + +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/database/BaseDatabase.ts b/modulo5/projeto-labook/template-projeto-labook/src/database/BaseDatabase.ts new file mode 100644 index 0000000..fd05f8c --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/database/BaseDatabase.ts @@ -0,0 +1,18 @@ +import knex from "knex" +import dotenv from "dotenv" + +dotenv.config() + +export abstract class BaseDatabase { + protected static connection = knex({ + client: "mysql", + connection: { + host: process.env.DB_HOST, + port: 3306, + user: process.env.DB_USER, + password: process.env.DB_PASSWORD, + database: process.env.DB_DATABASE, + multipleStatements: true + }, + }) +} diff --git a/modulo5/projeto-labook/template-projeto-labook/src/database/PostDatabase.ts b/modulo5/projeto-labook/template-projeto-labook/src/database/PostDatabase.ts new file mode 100644 index 0000000..a35c44a --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/database/PostDatabase.ts @@ -0,0 +1,7 @@ +import { BaseDatabase } from "./BaseDatabase" + +export class PostDatabase extends BaseDatabase { + public static TABLE_POSTS = "Labook_Posts" + public static TABLE_LIKES = "Labook_Likes" + +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/database/UserDatabase.ts b/modulo5/projeto-labook/template-projeto-labook/src/database/UserDatabase.ts new file mode 100644 index 0000000..c8df512 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/database/UserDatabase.ts @@ -0,0 +1,6 @@ +import { BaseDatabase } from "./BaseDatabase" + +export class UserDatabase extends BaseDatabase { + public static TABLE_USERS = "Labook_Users" + +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/database/migrations/Migrations.ts b/modulo5/projeto-labook/template-projeto-labook/src/database/migrations/Migrations.ts new file mode 100644 index 0000000..291a5ab --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/database/migrations/Migrations.ts @@ -0,0 +1,77 @@ +import { BaseDatabase } from "../BaseDatabase" +import { PostDatabase } from "../PostDatabase" +import { UserDatabase } from "../UserDatabase" +import { likes, posts, users } from "./data" + +class Migrations extends BaseDatabase { + execute = async () => { + try { + console.log("Creating tables...") + await this.createTables() + console.log("Tables created successfully.") + + console.log("Populating tables...") + await this.insertData() + console.log("Tables populated successfully.") + + console.log("Migrations completed.") + } catch (error) { + console.log("FAILED! Error in migrations...") + if (error instanceof Error) { + console.log(error.message) + } + } finally { + console.log("Ending connection...") + BaseDatabase.connection.destroy() + console.log("Connection closed graciously.") + } + } + + createTables = async () => { + await BaseDatabase.connection.raw(` + DROP TABLE IF EXISTS ${PostDatabase.TABLE_LIKES}; + DROP TABLE IF EXISTS ${PostDatabase.TABLE_POSTS}; + DROP TABLE IF EXISTS ${UserDatabase.TABLE_USERS}; + + CREATE TABLE IF NOT EXISTS ${UserDatabase.TABLE_USERS}( + id VARCHAR(255) PRIMARY KEY, + name VARCHAR(255) NOT NULL, + email VARCHAR(255) NOT NULL UNIQUE, + password VARCHAR(255) NOT NULL, + role ENUM("NORMAL", "ADMIN") DEFAULT "NORMAL" NOT NULL + ); + + CREATE TABLE IF NOT EXISTS ${PostDatabase.TABLE_POSTS}( + id VARCHAR(255) PRIMARY KEY, + content VARCHAR(255) NOT NULL, + user_id VARCHAR(255) NOT NULL, + FOREIGN KEY (user_id) REFERENCES ${UserDatabase.TABLE_USERS}(id) + ); + + CREATE TABLE IF NOT EXISTS ${PostDatabase.TABLE_LIKES}( + id VARCHAR(255) PRIMARY KEY, + post_id VARCHAR(255) NOT NULL, + user_id VARCHAR(255) NOT NULL, + FOREIGN KEY (user_id) REFERENCES ${UserDatabase.TABLE_USERS}(id), + FOREIGN KEY (post_id) REFERENCES ${PostDatabase.TABLE_POSTS}(id) + ); + `) + } + + insertData = async () => { + await BaseDatabase + .connection(UserDatabase.TABLE_USERS) + .insert(users) + + await BaseDatabase + .connection(PostDatabase.TABLE_POSTS) + .insert(posts) + + await BaseDatabase + .connection(PostDatabase.TABLE_LIKES) + .insert(likes) + } +} + +const migrations = new Migrations() +migrations.execute() \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/database/migrations/data.ts b/modulo5/projeto-labook/template-projeto-labook/src/database/migrations/data.ts new file mode 100644 index 0000000..bc6c4c1 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/database/migrations/data.ts @@ -0,0 +1,77 @@ +import { ILikeDB, IPostDB } from "../../models/Post" +import { IUserDB, USER_ROLES } from "../../models/User" + +export const users: IUserDB[] = [ + { + id: "101", + name: "Astrodev", + email: "astrodev@gmail.com", + password: "$2a$12$RBAWOHpUvGTE.MEeIohAzec9tlVqtNA/x2PMPt/Hrt0vI437cQdJC", // bananinha + role: USER_ROLES.ADMIN + }, + { + id: "102", + name: "Fulano", + email: "fulano@gmail.com", + password: "$2a$12$PULtVNlAll87D6E8pR/0HO9vbzVDPaUMA89rc5cNmYoAAepbwmkcO", // qwerty00 + role: USER_ROLES.NORMAL + }, + { + id: "103", + name: "Ciclana", + email: "ciclana@gmail.com", + password: "$2a$12$LkWMqS3oPhP2iVMcZOVvWer9ahUPulxjB0EA4TWPxWaRuEEfYGu/i", // asdfg123 + role: USER_ROLES.NORMAL + } +] + +export const posts: IPostDB[] = [ + { + id: "201", + content: "Olá, sou novo por aqui!", + user_id: "101" + }, + { + id: "202", + content: "Bom dia, família!", + user_id: "102" + }, + { + id: "203", + content: "Receba!", + user_id: "103" + } +] + +export const likes: ILikeDB[] = [ + { + id: "301", + post_id: "201", + user_id: "101" + }, + { + id: "302", + post_id: "202", + user_id: "101" + }, + { + id: "303", + post_id: "203", + user_id: "101" + }, + { + id: "304", + post_id: "201", + user_id: "102" + }, + { + id: "305", + post_id: "201", + user_id: "103" + }, + { + id: "306", + post_id: "202", + user_id: "103" + } +] \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/errors/AuthenticationError.ts b/modulo5/projeto-labook/template-projeto-labook/src/errors/AuthenticationError.ts new file mode 100644 index 0000000..0a5bfac --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/errors/AuthenticationError.ts @@ -0,0 +1,9 @@ +import { BaseError } from "./BaseError"; + +export class AuthenticationError extends BaseError { + constructor( + message: string = "Credenciais inválidas" + ) { + super(401, message) + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/errors/AuthorizationError.ts b/modulo5/projeto-labook/template-projeto-labook/src/errors/AuthorizationError.ts new file mode 100644 index 0000000..6b9f2a0 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/errors/AuthorizationError.ts @@ -0,0 +1,9 @@ +import { BaseError } from "./BaseError"; + +export class AuthorizationError extends BaseError { + constructor( + message: string = "Permissão insuficiente" + ) { + super(403, message) + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/errors/BaseError.ts b/modulo5/projeto-labook/template-projeto-labook/src/errors/BaseError.ts new file mode 100644 index 0000000..1dae99f --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/errors/BaseError.ts @@ -0,0 +1,8 @@ +export class BaseError extends Error { + constructor( + public statusCode: number, + message: string + ) { + super(message) + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/errors/ConflictError.ts b/modulo5/projeto-labook/template-projeto-labook/src/errors/ConflictError.ts new file mode 100644 index 0000000..e5934ef --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/errors/ConflictError.ts @@ -0,0 +1,9 @@ +import { BaseError } from "./BaseError"; + +export class ConflictError extends BaseError { + constructor( + message: string = "Recurso já existe" + ) { + super(409, message) + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/errors/NotFoundError.ts b/modulo5/projeto-labook/template-projeto-labook/src/errors/NotFoundError.ts new file mode 100644 index 0000000..697098f --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/errors/NotFoundError.ts @@ -0,0 +1,9 @@ +import { BaseError } from "./BaseError"; + +export class NotFoundError extends BaseError { + constructor( + message: string = "Recurso não encontrado" + ) { + super(404, message) + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/errors/ParamsError.ts b/modulo5/projeto-labook/template-projeto-labook/src/errors/ParamsError.ts new file mode 100644 index 0000000..b43539b --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/errors/ParamsError.ts @@ -0,0 +1,9 @@ +import { BaseError } from "./BaseError"; + +export class ParamsError extends BaseError { + constructor( + message: string = "Parâmetros inválidos ou faltando" + ) { + super(400, message) + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/errors/UnprocessableError.ts b/modulo5/projeto-labook/template-projeto-labook/src/errors/UnprocessableError.ts new file mode 100644 index 0000000..85e971e --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/errors/UnprocessableError.ts @@ -0,0 +1,9 @@ +import { BaseError } from "./BaseError"; + +export class UnprocessableError extends BaseError { + constructor( + message: string = "Parâmetros válidos, porém com erros de semântica" + ) { + super(422, message) + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/index.ts b/modulo5/projeto-labook/template-projeto-labook/src/index.ts new file mode 100644 index 0000000..5ba1bbd --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/index.ts @@ -0,0 +1,20 @@ +import express from 'express' +import cors from 'cors' +import dotenv from "dotenv" +import { pingRouter } from './router/pingRouter' +import { userRouter } from './router/userRouter' +import { postRouter } from './router/postRouter' + +dotenv.config() + +const app = express() +app.use(express.json()) +app.use(cors()) + +app.listen(process.env.PORT || 3003, () => { + console.log(`Servidor rodando na porta ${process.env.PORT || 3003}`) +}) + +app.use("/ping", pingRouter) +app.use("/users", userRouter) +app.use("/posts", postRouter) \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/models/Post.ts b/modulo5/projeto-labook/template-projeto-labook/src/models/Post.ts new file mode 100644 index 0000000..7f55d20 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/models/Post.ts @@ -0,0 +1,52 @@ +export interface IPostDB { + id: string, + content: string, + user_id: string +} + +export interface ILikeDB { + id: string, + post_id: string, + user_id: string +} + +export class Post { + constructor( + private id: string, + private content: string, + private userId: string, + private likes: number = 0 + ) {} + + public getId = () => { + return this.id + } + + public getContent = () => { + return this.content + } + + public getUserId = () => { + return this.userId + } + + public getLikes = () => { + return this.likes + } + + public setId = (newId: string) => { + this.id = newId + } + + public setContent = (newContent: string) => { + this.content = newContent + } + + public setUserId = (newUserId: string) => { + this.userId = newUserId + } + + public setLikes = (newLikes: number) => { + this.likes = newLikes + } +} diff --git a/modulo5/projeto-labook/template-projeto-labook/src/models/User.ts b/modulo5/projeto-labook/template-projeto-labook/src/models/User.ts new file mode 100644 index 0000000..9f28195 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/models/User.ts @@ -0,0 +1,62 @@ +export enum USER_ROLES { + NORMAL = "NORMAL", + ADMIN = "ADMIN" +} + +export interface IUserDB { + id: string, + name: string, + email: string, + password: string, + role: USER_ROLES +} + +export class User { + constructor( + private id: string, + private name: string, + private email: string, + private password: string, + private role: USER_ROLES + ) {} + + public getId = () => { + return this.id + } + + public getName = () => { + return this.name + } + + public getEmail = () => { + return this.email + } + + public getPassword = () => { + return this.password + } + + public getRole = () => { + return this.role + } + + public setId = (newId: string) => { + this.id = newId + } + + public setName = (newName: string) => { + this.name = newName + } + + public setEmail = (newEmail: string) => { + this.email = newEmail + } + + public setPassword = (newPassword: string) => { + this.password = newPassword + } + + public setRole = (newRole: USER_ROLES) => { + this.role = newRole + } +} diff --git a/modulo5/projeto-labook/template-projeto-labook/src/router/pingRouter.ts b/modulo5/projeto-labook/template-projeto-labook/src/router/pingRouter.ts new file mode 100644 index 0000000..3b328b6 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/router/pingRouter.ts @@ -0,0 +1,11 @@ +import { Router } from 'express' +import { PingBusiness } from '../business/PingBusiness' +import { PingController } from '../controller/PingController' + +export const pingRouter = Router() + +const pingController = new PingController( + new PingBusiness() +) + +pingRouter.get("/", pingController.ping) \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/router/postRouter.ts b/modulo5/projeto-labook/template-projeto-labook/src/router/postRouter.ts new file mode 100644 index 0000000..049ee65 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/router/postRouter.ts @@ -0,0 +1,19 @@ +import { Router } from 'express' +import { PostBusiness } from '../business/PostBusiness' +import { PostController } from '../controller/PostController' +import { PostDatabase } from '../database/PostDatabase' +import { Authenticator } from '../services/Authenticator' +import { IdGenerator } from '../services/IdGenerator' + +export const postRouter = Router() + +const postController = new PostController( + new PostBusiness( + new PostDatabase(), + new IdGenerator(), + new Authenticator() + ) +) + +// postRouter.post("/", PostController.createPost) +// etc \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/router/userRouter.ts b/modulo5/projeto-labook/template-projeto-labook/src/router/userRouter.ts new file mode 100644 index 0000000..21ecfc9 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/router/userRouter.ts @@ -0,0 +1,21 @@ +import { Router } from 'express' +import { UserBusiness } from '../business/UserBusiness' +import { UserController } from '../controller/UserController' +import { UserDatabase } from '../database/UserDatabase' +import { Authenticator } from '../services/Authenticator' +import { HashManager } from '../services/HashManager' +import { IdGenerator } from '../services/IdGenerator' + +export const userRouter = Router() + +const userController = new UserController( + new UserBusiness( + new UserDatabase(), + new IdGenerator(), + new HashManager(), + new Authenticator() + ) +) + +// userRouter.post("/signup", userController.signup) +// etc \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/services/Authenticator.ts b/modulo5/projeto-labook/template-projeto-labook/src/services/Authenticator.ts new file mode 100644 index 0000000..de5112e --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/services/Authenticator.ts @@ -0,0 +1,37 @@ +import jwt from 'jsonwebtoken' +import dotenv from "dotenv" +import { USER_ROLES } from '../models/User' + +dotenv.config() + +export interface ITokenPayload { + id: string, + role: USER_ROLES +} + +export class Authenticator { + generateToken = (payload: ITokenPayload): string => { + const token = jwt.sign( + payload, + process.env.JWT_KEY as string, + { + expiresIn: process.env.JWT_EXPIRES_IN + } + ) + + return token + } + + getTokenPayload = (token: string): ITokenPayload | null => { + try { + const payload = jwt.verify( + token, + process.env.JWT_KEY as string + ) + + return payload as ITokenPayload + } catch (error) { + return null + } + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/services/HashManager.ts b/modulo5/projeto-labook/template-projeto-labook/src/services/HashManager.ts new file mode 100644 index 0000000..4eb3ac2 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/services/HashManager.ts @@ -0,0 +1,15 @@ +import bcrypt from 'bcryptjs' + +export class HashManager { + public hash = async (plaintext: string) => { + const rounds = Number(process.env.BCRYPT_SALT_ROUNDS) + const salt = await bcrypt.genSalt(rounds) + const hash = await bcrypt.hash(plaintext, salt) + + return hash + } + + public compare = async (plaintext: string, hash: string) => { + return bcrypt.compare(plaintext, hash) + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/src/services/IdGenerator.ts b/modulo5/projeto-labook/template-projeto-labook/src/services/IdGenerator.ts new file mode 100644 index 0000000..a6ba76e --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/src/services/IdGenerator.ts @@ -0,0 +1,7 @@ +import { v4 } from 'uuid' + +export class IdGenerator { + public generate = (): string => { + return v4() + } +} \ No newline at end of file diff --git a/modulo5/projeto-labook/template-projeto-labook/tsconfig.json b/modulo5/projeto-labook/template-projeto-labook/tsconfig.json new file mode 100644 index 0000000..f97b176 --- /dev/null +++ b/modulo5/projeto-labook/template-projeto-labook/tsconfig.json @@ -0,0 +1,13 @@ +{ + "compilerOptions": { + "target": "es2021", + "module": "commonjs", + "sourceMap": true, + "outDir": "./build", + "rootDir": "./src", + "removeComments": true, + "noImplicitAny": true, + "esModuleInterop": true, + "strict": true + } +} \ No newline at end of file