ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • nodejs api 인증 예제 ( JWT, sequelize, express )
    개발/백엔드 2021. 3. 29. 08:05

    백엔드 개발에서 가장 중요한 API 인증 예제입니다.

    nodejs 언어를 사용하고, API 는 express 를 ORM (object relational mapping) 는 sequelize 를 사용했습니다.

    api 인증을 위해서는 JWT (json web token) 를 사용했습니다.

     

    회원가입, 로그인, 내정보보기의 3가지 API 를 구현했습니다.

     

    1. 예제 소스코드 다운로드

    github.com/vipick/nodejs-auth-example

     

    2. 소스코드 주요 폴더 및 파일

    app/config/config.js  개발 환경 및 운영서버에서 DB 엑세스 구별 
    app/controllers/auth.controllers.js 인증 컨트롤러
    app/models/index.js DB 엑세스 및 사용하는 모델 초기화 코드 
    app/models/user.model.js user 모델 및 관계를 정의 : users 테이블 생성 코드
    app/routes/index.js 라우터
    app/routes/verifyJwtToken.js API 인증을 위한 미들웨어 코드
    .env 외부에 노출되면 안되는 key 값을 저장합니다. (예: JWT secret, DB 아이디, 패스워드, ip주소 등)
    보통 git으로 관리하지 않습니다. (.gitignore)
    운영 서버에서는 .env-example 에서 이름 명을 .env로 변경하고 key 값을 작성합니다.  
    .gitignore git 으로 관리하지 않는 파일/폴더를 지정
    app.js 메인 
    server.js app.js 를 실행
    package.json 외부 프로그램 버전 관리

    실제 코드 작성이 많이 필요한 곳은 라우터, 컨트롤러, 모델 이렇게 3군데 입니다.

    나머지 코드는 세팅 부분으로 많은 수정이 없습니다.

     

    2-1) 라우터 

    - routes 폴더의 index.js 파일에서 각각의 api 를 정의합니다. 

    - 내 정보 api 미들웨어에서 인증 토큰 값을 검증합니다.

    - 인증 토큰 값은 로그인 시 얻게 되고, 백엔드 인증 api를 요청할 때 토큰 값을 포함시켜서 보내면 인증이 필요한 백엔드 기능을 사용할 수 있습니다.  

    2-2) 컨트롤러(Controller)

    - 회원가입 시 bcrypt 함수로 암호화를 합니다.

    - 로그인 시 회원정보 가(아이디, 패스워드) 일치 하면 jwt secret key 값을 활용해서 token 값을 생성 합니다. 86400 숫자는 24시간 만 유효하다는 것 입니다. 이 시간이 지나면 재로그인 필요합니다.

    - User 모델을 사용해서 users DB 테이블에서 회원가입(create), 조회(findOne)를 진행했습니다. 

    - 모델에 대한 추가적인 공부 구글에서 sequelize 키워드를 검색하면 됩니다.

    const { User } = require("../models");
    const jwt = require("jsonwebtoken");
    const bcrypt = require("bcryptjs");
    
    /**
     * 회원가입
     */
    exports.signup = async (req, res) => {
      try {
        const user = await User.create({
          email: req.body.email,
          password: bcrypt.hashSync(req.body.password, 8),
          type: req.body.type,
        });
    
        if (user) {
          return res.status(201).send("회원가입 성공!");
        }
      } catch (err) {
        return res.status(500).send("회원가입 실패!" + err);
      }
    };
    
    /**
     * 로그인
     */
    exports.signin = async (req, res) => {
      let user = null;
      try {
        user = await User.findOne({
          where: {
            email: req.body.email,
          },
        });
        if (!user) {
          return res.status(404).send("User Not Found.");
        }
      } catch (err) {
        return res.status(500).send("Error -> " + err);
      }
    
      const passwordIsValid = bcrypt.compareSync(req.body.password, user.password);
      if (!passwordIsValid) {
        return res.status(401).send({
          auth: false,
          accessToken: null,
          reason: "Invalid Password!",
        });
      }
    
      const token = jwt.sign(
        {
          id: user.id,
        },
        process.env.JWT_SECRET,
        {
          expiresIn: 86400, // expires in 24 hours
        }
      );
    
      return res.status(200).send({
        auth: true,
        accessToken: token,
      });
    };
    
    /**
     * 내 정보 보기
     */
    exports.me = async (req, res) => {
      try {
        const user = await User.findOne({
          attributes: ["type"],
          where: {
            id: req.userId,
          },
        });
        if (user) {
          return res.status(200).json({
            description: "회원정보 보기",
            content: user,
          });
        }
      } catch (err) {
        return res.status(500).send("Error -> " + err);
      }
    };
    

    '개발 > 백엔드' 카테고리의 다른 글

    nodejs api 예제 : express  (0) 2021.03.27
    Rest API 설계  (0) 2020.06.05

    댓글

Designed by Tistory.