2022-03-01 노드 공부흔적남기기4일차

박경현·2022년 3월 2일
0
post-thumbnail

저번에 코드 리뷰를 한다고 했는데 챕터 5 강의를 다 듣고 ㅋㅋ 너무 바뀌어서 그거에 대한 정리를 해보려고 한다

전체적인 파일 구조

일단 원래 posts를 main에 담았었는데 이걸 파일로 통째로 빼서 관리를 하는걸로 바뀌었다 내가봐도 이게 나은듯

  1. database.json에 posts들이 저장되어있다
  2. main에는 흐름이 쉽게 읽힐 수 있게 들어가있고
  3. api.js에 서버와 클라이언트 간에 통신에 관한 코드를 정리했다

그럼 지금부터 main.js와 api.js에 대한 리뷰를 해보겠다


api.js 코드

언제나 그랬듯이 다시 한번 적어보면서 스스로 생각해보고 적어볼거다.
강의를 들으면 생각할 시간이 적어지기 때문에 천천히 블로그 정리하면서 끄적거려보자

// @ts-check

/**
* @typedef Post
* @property {string} id
* @property {string} title
* @property {string} content
*/

/**
* @typedef APIResponse
* @property {number} statusCode
* @property {string | Object } body
*/

/**
* @typedef Route
* @property {RegExp } url
* @property {'GET' | 'POST' } method
* @property {(matches: string[], body: Object.<string, *> | undefined ) => Promise<APIResponse>} callback
*/
const fs =require("fs")
const DB_JSON_FILENAME = 'database.json'

/** @returns {Promise<Post[]>} */
async function getPosts(){
	const json = await fs.promises.readFile(DB_JSON_FILENAME, 'utf-8')
    return JSON.parse(json).posts
}

/** @param {Post[]} posts */
async function savePosts(posts) {
	const content = {
     	posts,
    }
    return fs.promises.writeFile(DB_JSON_FILENAME, JSON.stringify(content), 'utf-8')
}

/** @type {Route[]} */
const routes = [
	{
    	url: /^\/posts$/,
        method: 'GET',
        callback: async () => {
        	statusCode: 200,
            body: await getPosts()
        }
    },
    {
    	url: /^\/posts\/([a-zA-Z0-9-_]+)$/,
        method: 'GET',
        callback: async (matches) => {
        	const postId =matches[1]
            if(!postId){
            	return {
                	statusCode: 404,
                    body: 'NotFound!'
                }
            }
            const posts = await getPosts()
            const post = posts.find(_post => _post.id === postId)
            
            if(!post){
            	return {
                	statusCode: 404,
                    body: 'NotFound!'
                }
            }
            
            return {
            	statusCode: 200,
                body: post
           		}
        },
    },
    {
    	url: /^\/posts$/,
        method: 'POST',
        callback: async (_, body) => {
        	if(!body){
            	return {
                	statusCode: 400,
                    body: 'NotFound'
                }
            }
            
            /** @type {string} */
            /* eslint-disable-nex-line prefer-destructuring */
            const title = body.title
            
            const newPost = {
            	id: title.replace(/\s/g, '_'),
                title,
                content: body.content
            }
            const posts = await getPosts()
            
            posts.push(newPost)
            savePosts(post)
            
            return {
            	statusCode: 200,
                body: newPost
            }
        }
        
    }
  
]
module.exports = {
	routes,
}

api.js코드 리뷰

언제나 그랬듯이 @ts-check로 타입을 엄격하게 정해준다

이번에 적으면서 확실하게 알게 된건데 @typedef가 틀이고 @property가 그 안에
필수로 적은 타입에 맞게 정확하게 적혀있어야하는 애들이다

@propery중에 RegExp는 정규식을 뜻한다!

cosnt fs = requires("fs")로 밖에 있는 database.json을 읽고 쓸 수가 있게 되었다.

함수들에 대한 설명 (getPosts, savePosts)

getPosts

  • json에 동기식으로 database.json의 내용을 전부 담는다

    await fs.promises.readFile(DB_JSON_FILENAME, 'utf-8')

  • return 해주는데 @returns 타입에 맞게 posts를 리턴한다

savePosts

  • 인자로 받아온 posts를 content라는 변수 안에 객체형태로 넣는다
  • 동기식으로 database.json에 적게 된다 즉 저걸 하고 그 다음 행동이 있으면 실행된다

    return fs.promises.writeFile(DB_JSON_FILENAME, JSON.stringify(content), 'utf-8')


블로그 글을 보고 적을 수 있는 기능 부분 코드 리뷰!

  1. 전체적인 post들을 볼 수 있는 posts의 경우
    callback부분에 body를 await getPosts()로 가져와서 보여준다!

  2. 하나의 post를 볼 수 있는 post의 경우
    callback에서 matches라고 해서 내가 적은 post를 가져온다
    그리고 postId의 경우 matches[1]인데 이게 이유가 있다
    post를 가져오게 되면 id가 배열의 1번째 위치에 있어서...
    find로 postId와 _posts.id가 같은지 보고 같으면 post를 통째로 출력한다ㅎ

  3. 마지막은 post를 적어보는건데 이거 은근 간단하다.
    callback에서 body를 받는데 body는 내가 틀에 맞게 적은거
    그래서 newPost에 다가 정제해서 넣는다 -> 그리고 posts에 push
    추가로 정보를 새로고침해도 나올 수 있게 savePosts를 써서 database.json에 저장한다!!


느낀점

흐름을 이해한다고 하긴했지만 정규식 부분, 그리고 실제 동기화를 언제 해야하는지 등 아직은 미흡하다 더 차근차근 해보면서 서버-클라이언트 관계를 이해해보려고 한다

profile
SW로 문제를 해결하려는 열정만 있는 대학생

0개의 댓글