[WEB] 세션(Session) in Express

June hyoung Park·2020년 12월 14일
0

NodeJs

목록 보기
8/8
post-thumbnail
post-custom-banner

현대의 웹은 HTTP 프로토콜로 이루어져있고, HTTP가 가지는 비연결성(Connectionless)과 비상태성(Stateless) 특성 때문에 사용자와의 연결이 유지되지않고, 연결 해제 후에도 상태 정보를 저장하지않는다. 물론 서버의 자원 절약이라는 장점도 있지만, 사용자 식별이 불가하기 때문에 매번 새로운 사용자로 인식하는 단점이 있지만, 쿠키(Cookie) 및 세션(Session) 인증 방식을 통해 클라이언트의 상태정보를 지속적으로 가져오고, 이에 알맞는 정보 및 화면을 제공할 수 있으며, HTTP의 비상태, 비연결 적인 특성들을 보완할 수 있다.

세션 (Session)

특정 정보를 브라우저 메모리에 저장하는 쿠키와는 달리 세션은 웹 서버가 돌아가고 있는 서버에 저장을 한다. 또한 세션 이용 시 각 유저마다 고유한 세션을 갖기 위해 sessionId값을 클라이언트의 쿠키에 저장하여, 이로 유저를 구분한다. 이런식으로 서버에서 유저의 데이터를 저장하다 보니 쿠키를 이용하는 방식보단 보안성이 탁월하나, 확장성이나 서버에 데이터를 저장하므로 양이 많아질수록 서버에 부담이 갈 수 있다.

작동 방식

  1. 클라이언트가 서버에 처음으로 Request를 보낸 후 클라이언트엔 session id 쿠키 값이 없기에 새로 발급 후 저장.
  2. 요청마다 클라이언트는 전달받은 session id 값을 헤더 쿠키에 넣어서 서버에 전달하고 서버는 이를 이용해 사용자를 식별한다.
  3. 클라이언트가 로그인을 요청하면 서버는 session을 로그인한 사용자 정보로 갱신하고 새로운 session id를 발급한다.

In Express

install express-session

$ npm install express-session
공식 문서

express-session 은 Express 프레임워크에서 세션을 관리하기 위한 미들웨어이다.

const session = require("express-session"); //모듈 가져오기

{ ... }

app.use( // 미들웨어 적용
  session({
    secret: "@haAdvanced",
    resave: false,
    saveUninitialized: true,
  })
);
 
 { ... }
  • secret – 쿠키를 임의로 변조하는것을 방지하기 위한 값이며, 이 값을 토대로 세션을 암호화 하여 저장한다.
  • resave – 세션에 변경사항이 없어도 항상 저장할 지 설정하는 값이다.
  • saveUninitialized – 세션이 저장되기 전에 uninitialized 상태로 미리 만들어서 저장한다.

login / express

 signInController: async (req, res) => {
    const { email, password } = req.body; // POST요청으로 받은 email, password 추출
    const userData = await Users.findOne({
      where: { email: email, password: password },
    });
    if (!userData) res.status(404).send("invalid user");
    req.session.userid = email; // DB 조회에 성공한다면, 세션에 userid라는 키를 만들어서 유저의 email값을 저장한다.
    return res.status(200).json({ id: req.body.email });
  },

POST요청으로 로그인 시 데이터베이스에 해당 이메일과 패스워드가 유효한지 검사한다. 유효하다면 세션객체에 userid라는 키값을 만들어서 추후에 해당 값을 토대로 유저 데이터에 접근하기위해 유저 이메일을 저장한다.

또한 로그인 시 브라우저 쿠키에 유저 식별을 위한 session id값이 생기게된다.

userData / express

 userController: async (req, res) => {
    if (!req.session.userid) {
      return res.status(401).send("authenticateFailedUser");
    }
    const userInfo = await Users.findOne({
      where: { email: req.session.userid },
    });
    const { dataValues } = userInfo;
    const user = { ...dataValues };
    delete user.password;
    res.status(200).json(user);
  },

세션에 저장한 값을 바탕으로 특정 페이지에서 유저 데이터에 접근하기위해선 로그인 시 저장했던 req.session에 있는 userid을 이용해서 db에서 조회한 뒤 결과값을 클라이언트로 응답해준다.

signOutController: (req, res) => {
    req.session.destroy(function (err) {
      if (err) throw new Error(err);
      return res.status(205).send("Logged out successfully");
    });
  },

삭제시엔 req.session.destroy를 이용해서 세션을 지워준뒤, 콜백으로 205 상태코드와 로그아웃 완료 메세지를 반환해준다.

profile
Take me home~~~~
post-custom-banner

0개의 댓글