Express.js와 MySql기반 서버 구축(SignUp 구축)

·

3 min read

개요

Next.js와 Express.js를 연계하여 도서 대여 서비스를 구축하고자 한다. 로그인 서비스를 구축하고 있으며 오늘은 서버 구축 과정에 대해 이야기해보고자 한다.

Server.js

const express = require('express');
const bodyParser = require('body-parser');

const cors = require('cors');

const loginRouter = require('./routes/auth/login');
const signUpRouter = require('./routes/auth/signup');
const authRouter = require('./routes/auth/auth');
const secretGenerator = require('./secret');

const app = express();
const port = 3001;

secretGenerator.updateSecretKey();

// 주기적으로 실행 (예: 24시간마다)
const interval = 2 * 60 * 60 * 1000; // 24시간
setInterval(secretGenerator.updateSecretKey, interval);

app.use(cors());

app.use(express.urlencoded({ extended: true }));
app.use(bodyParser.json());

// app.post('/auth/login', login.getUserHandler);
app.use('/auth/login', loginRouter);
app.use('/auth/signup', signUpRouter);
app.use('/auth/auth', authRouter);

app.listen(port, () => {
    console.log('Server port: ', port);
});

loginRouter와 signUpRouter를 분리했다.

기본적으로 app.use()로 원하는 라우터에 분리한 라우터 모듈을 분리하여 등록했다. 이중 signUpRouter에 대해 자세히 보자.

signUpRouter

const express = require('express');

const signUpController = require('../../controllers/userSignupController');

const router = express.Router();

router.use((req, res, next) => {
    console.log('sign up process');
    next();
});

router.post('/', signUpController.addUserHandler);

module.exports = router;

라우터를 살펴보면, express.Router()로 라우터를 생성하고, router.post('/', function );를 통해 '/auth/signup'에 signUpController 모듈의 addUserHandler함수를 등록하여, 이 라우터로 post 요청이 들어올 때마다, 이 함수를 실행한다.

signUpController

signUp 과정에서 데이터를 request로 보냈을 때, 데이터를 처리하는 프로세스를 담당한다.

const db = require('../db');
const User = require('../models/user');

exports.addUserHandler = async (req, res) => {
    const userName = req.body.user;
    const studentId = req.body.student_id;
    const password = req.body.password;

    const userData = new User(userName, studentId, password);

    function callback_onAdd(object) {
        res.set('Content-Type', 'application/json');
        if (!object.result) {
            res.send({ message: 'Database failed', result: 0 });
        } else {
            res.send({ message: 'Sign up success', result: 1 });
        }
    }

    function callback_onCheck(object) {
        res.set('Content-Type', 'application/json');
        if (object.isSuccess === 'no data') {
            userData.addUser(callback_onAdd);
        } else if (object.isSuccess === 'log in') {
            res.send({ message: 'You already have account', result: 0 });
        }
    }

    userData.checkUser(callback_onCheck);
};

addUserHandler 함수는 클라이언트에서 request를 보냈을 때, body에서 student_id와 password, username을 얻어낸다. 이는 클라이언트에서 회원가입할 때, 입력하는 정보이다.

checkUser 함수는 user 모델 클래스의 메소드로

    checkUser(cb) {
        let sql = `SELECT * FROM login_data WHERE student_id='${this.student_id}' AND password='${this.password}'`;

        db.query(sql, (err, rows) => {
            if (err) {
                console.log('Error occured during checking user data', err);
                cb({ isSuccess: 'error', id: -1, username: '' });
            } else if (rows.length >= 1) {
                console.log('You log in!');
                cb({
                    isSuccess: 'log in',
                    id: rows[0].id,
                    username: rows[0].user_name,
                });
            } else if (rows.length === 0) {
                console.log('no data please make an account');
                cb({ isSuccess: 'no data', id: -1, username: '' });
            }
        });
    }

mysql 데이터베이스에 SELECT구문으로 모든 데이터를 가져온다. db.query문을 통해 쿼리 결과가 rows에 들어가 콜백함수를 실행한다.콜백 함수의 인자로 쿼리 성공 여부와 쿼리 결과로 얻은 username을 입력한다.

username: rows[0].user_name 에서 rows[0]는 쿼리 결과로 얻는 데이터 중 첫 번째 데이터이므로, 여기서 user_name을 얻을 수 있다.

콜백함수로 실행하는 callback_onCheck(object)

    function callback_onCheck(object) {
        res.set('Content-Type', 'application/json');
        if (object.isSuccess === 'no data') {
            userData.addUser(callback_onAdd);
        } else if (object.isSuccess === 'log in') {
            res.send({ message: 'You already have account', result: 0 });
        }
    }

쿼리결과로 얻는 isSuccess 값에 따라 no data일 때, addUser()를하고, log in일 때, 이미 계정이 있음을 res.send()로 전달한다. addUser()는

    addUser(cb) {
        let sql = `INSERT INTO login_data (user_name, student_id, password) VALUES (?, ?, ?)`;

        db.query(
            sql,
            [this.username, this.student_id, this.password],
            (err, results) => {
                if (err) {
                    cb({
                        message: 'Error occured during adding user data',
                        result: 0,
                    });
                } else {
                    cb({ message: 'Adding account success', result: 1 });
                }
            }
        );
    }
    function callback_onAdd(object) {
        res.set('Content-Type', 'application/json');
        if (!object.result) {
            res.send({ message: 'Database failed', result: 0 });
        } else {
            res.send({ message: 'Sign up success', result: 1 });
        }
    }

addUser는 Insert 구문을 통해 입력한 username, student_id, password로 sql구문을 통해 데이터베이스에 유저데이터를 넣는다. 그리고, 해당 쿼리문 결과에 따라 callback 함수로 callback_onAdd()함수를 실행하여 insert쿼리에 성공했으면, res.send()로 클라이언트에 회원가입을 성공했음을 result에 담아서 보낸다.