[TIL] 24.09.15 SUN

GDORI·2024년 9월 15일
0

TIL

목록 보기
42/79
post-thumbnail

오늘 한 것 + 배운 것

일부 코드 수정

  • 회원가입 DB입력 단일 쿼리 트랜젝션 제거
  • auth 미들웨어 Bearer split 기준 공백으로 수정, 페이로드 부분 수정
  • 패스워드 해시화 이전 페퍼값 추가
  • 부분 오타 및 주석 수정

추가 라우터 ( 기본 틀, 수정 예정)

  • 캐시 충전
  • 캐시 조회
  • 비밀번호 수정
  • 랭킹 조회

회원가입 DB입력 단일 쿼리 트랜젝션 제거

// 변경 전
const user = await prisma.$transaction(
    async (tx) => {
        const user = await tx.Users.create({
            data: { email, password: hashedPw, name }, // 새로운 사용자 생성
        });
        return user;
    },
    {
        isolationLevel: Prisma.TransactionIsolationLevel.ReadCommitted,
    },
);

// 변경 후
const user = await prisma.users.create({
    data: { email, password: hashedPw, name },
});

개인 과제 피드백 중 단일쿼리에 대해서는 트랜잭션을 할 필요가 없다. 트랜잭션은 작업의 한 단위이며 쿼리
그자체로 하나의 트랜잭션으로 처리가 된다는 피드백을 받았기 때문에 그에 맞춰 수정하였다.

DB 입력을 처리하다가 문제가 생기면 롤백되니까 럭키비키자나~ 하는 생각에 다 집어넣었으나 쓸 때 없는
행동이었던 것...😂

auth 미들웨어 Bearer split 기준 공백으로 수정, 페이로드 부분 수정

// 변경 전
const [tokenType, token] = authorization.split('%20');
// 변경 후
const [tokenType, token] = authorization.split(' ');

토큰 타입과 토큰 사이 공백을 %20으로 split 되어있는 부분을 공백으로 처리하면 URL 인코딩이 필요없다고 하여
수정하였다.
원래 공백으로 하긴 했었는데, 팀프로젝트 기본 틀에 구현되어 있는 미들웨어 부분이 %20으로 처리되어 있었는데,
인썸니아에서 Auth - Bearer 로는 처리가 되지 않아 원인을 찾아보니 내가 생성한 토큰은 공백으로 처리했는데
검증 부분에서는 %20으로 처리해서 그런 것 같더라.

패스워드 해시화 이전 페퍼값 추가

const combinedPw = password + PEPPER; // 패스워드 페퍼 적용
const hashedPw = await bcrypt.hash(combinedPw, 10); // 페퍼 컴바인 된 비밀번호 해시화

bcrypt 해시화 이전 페퍼값을 추가하면 보안성에 더 좋다는 게시글을 읽고 추가 구현해보았다.
PEPPER 값은 환경변수에 저장하고 해시된 패스워드는 DB에 저장되기 때문에 보안성이 좋다고 한다.

추가 라우터 구현

추가 라우터 부분은 인가 처리 부분에서 아직 팀원들과 소통이 되지 않아서 소통 후 정리하겠다.
현재 내 생각은 인증 미들웨어에서 받은 userID 기준으로 처리를 하면 되지 않나? 라는 생각이라 인가 과정이
따로 필요 없을 것이라고 생각한다.
어드민 권한을 가진 계정도 구현한게 아니라 다른 아이디를 접근할 껀덕지도 주지 않으면 되지 않나? 라는 생각이지만...
현직자였던 분들 + 튜터님 생각을 좀 들어보고 추가 수정작업 해야겠다.

랭킹조회는 인증, 인가가 필요 없지

어차피 누구나 조회가 가능한 것이니까.. get 메서드로 요청만 하면 처리해서 반환하는 형식으로 구현해보았다.
우선 유저테이블을 가져오고 승,무,패 기록으로 승률을 구해놓은 후 score 기준으로 내림차순 정렬, 중복 시 승률기준으로
처리하여 반환 로직을 구현 해 보았다.

router.get('/user/rank', async (req, res, next) => {
    // 유저 테이블 가져오기
    const results = await prisma.users.findMany({
        select: {
            name: true,
            score: true,
            win: true,
            draw: true,
            loss: true,
        },
    });
    // 받아오기 실패 시 에러
    if (!results) throw new Error('DB를 불러오는데 문제가 생겼습니다.');

    // 승률 구하기
    const addWinRate = results.map((result) => {
        const totalGame = result.win + result.draw + result.loss;
        const winRate = totalGame > 0 ? (result.win / totalGame) * 100 : 0;
        return {
            ...result,
            winRate: winRate.toFixed(0) + '%',
        };
    });

    // 점수 기준 내림차순 정렬, 중복 시 승률 기준으로 내림차순
    const rank = addWinRate.sort((a, b) => {
        if (b.score === a.score)
            return parseInt(b.winRate, 10) - parseInt(a.winRate, 10);
        return b.score - a.score;
    });

    // 객체 배열로 반환
    return res.status(200).json({ data: rank });
});
profile
하루 최소 1시간이라도 공부하자..

0개의 댓글