본문 바로가기
프로그래밍 개발/Express

Express - 비밀번호 암호화

by Jinseok Kim 2021. 1. 19.
반응형

 

 

 비밀번호 암호화

 

 

아래와 같이 회원정보가 들어있는 파일에 비밀번호가 암호화 되어있지 않는다면 보안에 심각한 문제를 초래할 수 있다.

 

 

 

 

 

아래 링크 페이지에 자세한 사용설명이 존재한다.

www.npmjs.com/package/bcrypt

 

bcrypt

A bcrypt library for NodeJS.

www.npmjs.com

npm install -s bcrypt

비밀번호를 암호화하는 프로그램 모듈이 따로 존재하기에 위의 명령어를 입력하여 프로그램을 다운받는다.

 

 

 

 

 

 syntax/bcrypt.js

//따로 bcrypt 프로그램을 구동시킬 코드를 모아둔 파일 만듬.

var bcrypt = require('bcrypt'); //bcrypt 모듈 연동
const saltRounds = 10;
const myPlaintextPassword = '111111'; //자신의 패스워드
const someOtherPlaintextPassword = '111112'; //남의 패스워드
           //myPlaintextPassword는 나의 패스워드이며 saltRounds는 패스워드를 뚫는 시도를 막는
           //일종의 노이즈 값이라고 보면된다. 높을수록 뚫기 어렵다.
           //이렇게 만들어진 패스워드가 콜백함수의 두번째 인자 hash라고 보면 된다.
bcrypt.hash(myPlaintextPassword, saltRounds, function (err, hash) {
   
    console.log(hash);
    //자신의 패스워드
    bcrypt.compare(myPlaintextPassword, hash, function(err, result){
        console.log('my password', result);
    })
    //남의 패스워드, 즉 자신의 패스워드와 다르므로 다른 패스워드로 결과가 도출되는 코드다. 
    bcrypt.compare(someOtherPlaintextPassword, hash, function(err, result){
        console.log('other password', result);
    })

});

 

 

 

 

 

 lib/passport.js

var db = require('../lib/db');
var bcrypt = require('bcrypt'); //bcrypt 모듈 연동

module.exports = function (app) {


    var passport = require('passport'),
        LocalStrategy = require('passport-local').Strategy;

    app.use(passport.initialize());
    app.use(passport.session());

    passport.serializeUser(function (user, done) {
        done(null, user.id);
    });

    passport.deserializeUser(function (id, done) {
        var user = db.get('users').find({id:id}).value();
        done(null, user);
    });

    passport.use(new LocalStrategy({
            usernameField: 'email',
            passwordField: 'pwd'
        },
        function (email, password, done) {
        var user = db.get('users').find({
            email:email
            
        }).value();
           if(user){
           //bcrypt을 사용하자면 compare메소드의 첫번째인자는 입력한 패스워드 값
           // 두번째 인자는 암호화된 패스워드이자 hash 값이다.
           //이때 입력한 패스워드 값과 암호화된 패스워드이자 hash 값이 같으면
           //result가 true이므로  로그인이 성공되며 환영의 플래시 메세지가 등장하도록 하였고
           //false면 로그인이 실패되면서 패스워드의 오류를 알리는 플래시 메세지 등장하게 하였다.
           //여기서 따로 bcrypt을 쓰는 이유는 암호화된 패스워드와 사용자가 입력한 패스워드를 비교하기
           //위해서는 bcrypt을 거쳐야 하기 때문이다.
                    bcrypt.compare(password, user.password, function(err,result){
                    if(result){
                        return done(null, user, {
                            message: 'Welcome.'
                        });
                    } else {
                        return done(null, false, {
                            message: 'Password is not correct.'
                        });
                    }
                    });
               }
               //처음부터 email 값이 틀렸으므로 email값이 틀렸다는 오류 플래시 메세지 등장.
                 else {
                    return done(null, false, {
                        message: 'There is no email.'
                    });
                }
            
            }
    ));
    return passport;
}

 

 

 

routes/auth.js

var express = require('express');
var router = express.Router();
var path = require('path');
var fs = require('fs');
var sanitizeHtml = require('sanitize-html');
var template = require('../lib/template.js');
var shortid = require('shortid');
var db = require('../lib/db');
var bcrypt = require('bcrypt');


module.exports = function (passport) {
  router.get('/login', function (request, response) {
    var fmsg = request.flash();
    var feedback = '';
    if (fmsg.error) {
      feedback = fmsg.error[0];
    }
    var title = 'WEB - login';
    var list = template.list(request.list);
    var html = template.HTML(title, list, `
      <div style="color:red;">${feedback}</div>
      <form action="/auth/login_process" method="post">
        <p><input type="text" name="email" placeholder="email"></p>
        <p><input type="password" name="pwd" placeholder="password"></p>
        <p>
          <input type="submit" value="login">
        </p>
      </form>
    `, '');
    response.send(html);
  });

  router.post('/login_process',
    passport.authenticate('local', {
      successRedirect: '/',
      failureRedirect: '/auth/login',
      failureFlash: true,
      successFlash: true
    }));
    
    router.get('/register', function (request, response) {
    var fmsg = request.flash();
    var feedback = '';
    if (fmsg.error) {
      feedback = fmsg.error[0];
    }
    var title = 'WEB - login';
    var list = template.list(request.list);
    var html = template.HTML(title, list, `
        <div style="color:red;">${feedback}</div>
        <form action="/auth/register_process" method="post">
          <p><input type="text" name="email" placeholder="email"></p>
          <p><input type="password" name="pwd" placeholder="password"></p>
          <p><input type="password" name="pwd2" placeholder="password"></p>
          <p><input type="text" name="displayName" placeholder="display name"></p>
          <p>
            <input type="submit" value="register">
          </p>
        </form>
      `, '');
    response.send(html);
  });
    
router.post('/register_process', function (request, response) {
    var post = request.body;
    var email = post.email;
    var pwd = post.pwd;
    var pwd2 = post.pwd2;
    var displayName = post.displayName;
   if(pwd !== pwd2){
      request.flash('error', 'Password must same!');
      response.redirect('/auth/register');
    } else {
    //회원가입으로 작성한 생성할 패스워드를 bcrypt의 hash로 설정하여 암호화 하였다.
       bcrypt.hash(pwd, 10, function (err, hash) {
        var user = {
          id: shortid.generate(),
          email: email,
          password: hash,
          displayName: displayName
        };
        db.get('users').push(user).write();
        request.login(user, function (err) {
          console.log('redirect');
          return response.redirect('/');
        })
      });
      
    }
  });    

  router.get('/logout', function (request, response) {
    request.logout();
    request.session.save(function () {
      response.redirect('/');
    });
});

  return router;
} 

 

 

 

 

 

패스워드가 111으로 새로 회원가입을 하여 새로운 정보를 만들어 보았더니 패스워드가 암호화 되어있는 것을 확인 할 수 있었다.

반응형

댓글