Skip to content

Commit

Permalink
Add: Posts CRUD & User SignUp
Browse files Browse the repository at this point in the history
Add: Posts CRUD & User SignUp
  • Loading branch information
JJieunn authored Oct 25, 2022
2 parents 81be2f6 + 4ecd40b commit 4a97bf8
Show file tree
Hide file tree
Showing 24 changed files with 470 additions and 13 deletions.
12 changes: 12 additions & 0 deletions db/migrations/20221023163702_create_users_table.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
-- migrate:up
CREATE TABLE users (
id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
email VARCHAR(30) NOT NULL UNIQUE,
password VARCHAR(1500) NOT NULL,
nickname VARCHAR(15) NOT NULL,
created_at TIMESTAMP NOT NULL DEFAULT NOW(),
updated_at TIMESTAMP NOT NULL DEFAULT NOW() ON UPDATE CURRENT_TIMESTAMP
);

-- migrate:down
DROP TABLE users;
13 changes: 13 additions & 0 deletions db/migrations/20221023163709_create_posts_table.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
-- migrate:up
CREATE TABLE posts (
id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
user_id INT NOT NULL,
title VARCHAR(30) NOT NULL,
content VARCHAR(3000) NOT NULL,
created_at TIMESTAMP NOT NULL DEFAULT NOW(),
updated_at TIMESTAMP NOT NULL DEFAULT NOW() ON UPDATE CURRENT_TIMESTAMP,
FOREIGN KEY (user_id) REFERENCES users (id) ON DELETE CASCADE
);

-- migrate:down
DROP TABLE posts;
44 changes: 44 additions & 0 deletions db/schema.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
/*!50503 SET NAMES utf8mb4 */;
/*!40103 SET @OLD_TIME_ZONE=@@TIME_ZONE */;
/*!40103 SET TIME_ZONE='+00:00' */;
/*!40014 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0 */;
/*!40014 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0 */;
/*!40101 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='NO_AUTO_VALUE_ON_ZERO' */;
/*!40111 SET @OLD_SQL_NOTES=@@SQL_NOTES, SQL_NOTES=0 */;

--
-- Table structure for table `schema_migrations`
--

/*!40101 SET @saved_cs_client = @@character_set_client */;
/*!50503 SET character_set_client = utf8mb4 */;
CREATE TABLE `schema_migrations` (
`version` varchar(255) COLLATE latin1_bin NOT NULL,
PRIMARY KEY (`version`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_bin;
/*!40101 SET character_set_client = @saved_cs_client */;

--
-- Dumping routines for database 'Study'
--
/*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */;

/*!40101 SET SQL_MODE=@OLD_SQL_MODE */;
/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */;
/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */;
/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
/*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */;

-- Dump completed

--
-- Dbmate schema migrations
--

LOCK TABLES `schema_migrations` WRITE;
UNLOCK TABLES;
35 changes: 29 additions & 6 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@
"@types/cors": "^2.8.12",
"@types/express": "^4.17.14",
"@types/morgan": "^1.9.3",
"@types/node": "^18.11.4",
"cors": "^2.8.5",
"dbmate": "^1.0.3",
"dotenv": "^16.0.3",
"express": "^4.18.2",
Expand Down
2 changes: 1 addition & 1 deletion src/app.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ const createApp = () => {

const app = express()
app.use(
cors(), express.json(), logger("tiny"), routes
cors(), express.json(), logger("dev"), routes
)

return app;
Expand Down
8 changes: 6 additions & 2 deletions src/configs/common.ts → src/configs/db.connection.ts
Original file line number Diff line number Diff line change
@@ -1,20 +1,24 @@
import { DataSource } from "typeorm"
import { Posts } from "../entities/post.entity";
import { Users } from "../entities/user.entity";

const myDataSource = new DataSource ({
type: "mysql",
host: process.env.TYPEORM_HOST,
port: 3306,
username: process.env.TYPEORM_USERNAME,
password: process.env.TYPEORM_PASSWORD,
database: process.env.TYPEORM_DATABASE
database: process.env.TYPEORM_DATABASE,
entities: [Posts, Users],
synchronize: true
});

myDataSource
.initialize()
.then(() => {
console.log("Data Source has been initailized!");
})
.catch(() => {
.catch((err: any) => {
console.log("Database initialize failed.");
});

Expand Down
52 changes: 51 additions & 1 deletion src/controllers/postsController.ts
Original file line number Diff line number Diff line change
@@ -1 +1,51 @@
import postService from "../services/postsService"
import postService from "../services/postsService"
import { Request, Response } from "express";
import { CreatePostDTO } from "../dto/createPostDto";
import { UpdaatePostDTO } from "../dto/updatePostDto";
import { asyncWrap } from "../middlewares/errorHandler";

const createPost = asyncWrap (async (req: Request, res: Response) => {
const userId = req.headers.id;
const postData: CreatePostDTO = req.body;

await postService.createPost(userId, postData);
res.status(201).json({ message: "POST_CREATED" })
});

const getPostList = asyncWrap (async (req: Request, res: Response) => {
const postList = await postService.getPostList();
res.status(200).json(postList)
});

const getPost = asyncWrap (async (req: Request, res: Response) => {
const postId = req.params.postId;

const post = await postService.getPost(postId);
res.status(200).json(post)
});


const updatePost = asyncWrap (async (req: Request, res: Response) => {
const userId = req.headers.id;
const postId = req.params.postId;
const updateData: UpdaatePostDTO = req.body;

const updatePostRes = await postService.updatePost(userId, postId, updateData);
res.status(200).json({ message: "UPDATE_SUCCESS", updatePostRes })
});

const deletePost = asyncWrap (async (req: Request, res: Response) => {
const userId = req.headers.id;
const postId = req.params.postId;

await postService.deletePost(userId, postId);
res.status(204).send({ message: "DELETE_SUCCESS" })
});

export default {
createPost,
getPostList,
getPost,
updatePost,
deletePost
}
14 changes: 14 additions & 0 deletions src/controllers/usersController.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import userService from "../services/usersService"
import { Request, Response } from "express";
import { UserDTO } from "../dto/userDto";
import { asyncWrap } from "../middlewares/errorHandler";

const createUser = asyncWrap (async (req: Request, res: Response) => {
const userData: UserDTO = req.body;

await userService.createUser(userData)
res.status(201).json({ message: "USER_CREATED" })
});


export default { createUser }
4 changes: 4 additions & 0 deletions src/dto/createPostDto.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
export interface CreatePostDTO {
title: string;
content: string;
}
6 changes: 6 additions & 0 deletions src/dto/updatePostDto.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
export interface UpdaatePostDTO {
title?: string;
content?: string;
}


5 changes: 5 additions & 0 deletions src/dto/userDto.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
export interface UserDTO {
nickname: string;
email: string;
password: string;
}
34 changes: 34 additions & 0 deletions src/entities/post.entity.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import { BaseEntity, Column, CreateDateColumn, Entity, JoinColumn, ManyToOne, PrimaryGeneratedColumn, UpdateDateColumn } from "typeorm"
import { Users } from "./user.entity";

@Entity('posts')
export class Posts {
@PrimaryGeneratedColumn()
id?: number

@Column("varchar", { length: 30 })
title?: string

@Column("varchar", { length: 3000 })
content?: string

@CreateDateColumn({
type: 'timestamp',
default: () => 'CURRENT_TIMESTAMP(6)',
})
created_at?: Date;

@UpdateDateColumn({
type: 'timestamp',
default: () => 'CURRENT_TIMESTAMP(6)',
onUpdate: 'CURRENT_TIMESTAMP(6)',
})
updated_at?: Date;

@Column("int")
user_id?: number;

@ManyToOne(() => Users, (user) => user.posts )
@JoinColumn({ name: "user_id", referencedColumnName: 'id' })
user?: Users;
}
33 changes: 33 additions & 0 deletions src/entities/user.entity.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import { BaseEntity, Column, Entity, OneToMany, PrimaryGeneratedColumn, CreateDateColumn, UpdateDateColumn } from "typeorm"
import { Posts } from "./post.entity";

@Entity('users')
export class Users {
@PrimaryGeneratedColumn()
id?: number;

@Column("varchar", { length: 15 })
nickname?: string;

@Column("varchar", { length: 30 })
email?: string;

@Column("varchar", { length: 1500 })
password?: string;

@CreateDateColumn({
type: 'timestamp',
default: () => 'CURRENT_TIMESTAMP(6)',
})
created_at?: Date;

@UpdateDateColumn({
type: 'timestamp',
default: () => 'CURRENT_TIMESTAMP(6)',
onUpdate: 'CURRENT_TIMESTAMP(6)',
})
updated_at?: Date;

@OneToMany(() => Posts, (post) => post.user)
posts?: Posts[];
}
19 changes: 19 additions & 0 deletions src/middlewares/createError.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
export class NotFoundError extends Error {
private statusCode: number;

constructor(message: string) {
super(message);
this.name = "NotFoundError"
this.statusCode = 404
}
}

export class ForbiddenError extends Error {
private statusCode: number;

constructor(message: string) {
super(message);
this.name = "ForbiddenError"
this.statusCode = 403
}
}
13 changes: 13 additions & 0 deletions src/middlewares/errorHandler.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import { Request, Response } from "express"

export const asyncWrap = (asyncController: Function) => {
return async (req: Request, res: Response) => {
try {
await asyncController(req, res);
} catch(err: any) {
// next(err);
console.log(err)
res.status(err.statusCode || 500).json({ err: err.message || "Internal Server Error" })
}
}
}
Loading

0 comments on commit 4a97bf8

Please sign in to comment.