[MYSQL] node-mysql CRUD

jihan kong·2022년 3월 16일
0

MySQL 

목록 보기
4/9
post-thumbnail

Review

지난 시간에 node를 통해 mysql을 사용하는 방법에 대해서 학습했다. mysql의 createConnection 메소드를 사용해서 DB와 연결하고, 이 메소드는 query 라는 함수를 사용하여 error 를 출력시키거나 rows, fields 와 같은 값을 호출시킬 수 있었다.

그렇다면 node-mysql도 기본적인 CRUD를 구현하지 않고 넘어갈 수는 없다. 먼저 조회(READ) 기능부터 들어간다.

database_mysql.js

var mysql = require('mysql');
var conn = mysql.createConnection({
  host     : 'localhost',
  user     : 'root',
  password : 'kjh950330',
  database : 'o2'
});

conn.connect();

var sql = 'SELECT * FROM topic';
conn.query(sql, function(err, rows, fields){
  if(err) {
    console.log(err);
  } else {
    for(var i=0; i<rows.length; i++){
      console.log(rows[i].title);
    }
  }
});
conn.end();

당연히 SELECT * FROM 문으로 데이터를 선택하고 만약 err가 발생하면 err를 출력, 그렇지 않다면 for문을 통해 들의 title 을 차례대로 출력한다. for문으로 출력이 가능한 이유는 지난 포스트에서 살펴본 바와 같이 rows가 배열에 담기기 때문이다.

table의 rows의 내용이 출력되었다.

생성(Create) 또한, SQL 문과 동일하다.

database_mysql.js

var mysql = require('mysql');
var conn = mysql.createConnection({
  host     : 'localhost',
  user     : 'root',
  password : 'kjh950330',
  database : 'o2'
});

conn.connect();

var sql = 'INSERT INTO topic (title, description, author) VALUES("Nodejs", "Server side javascript", "kkongji")';

conn.query(sql, function(err, rows, fields) {
  if(err) {
    console.log(err);
  } else {
    console.log(rows);
  }
});
conn.end();

SQL 문에서의 삽입 INSERT INTO "table_name" "(column1, column2, ...)" VALUES("value1", "value2", ...) 을 사용하고 query 함수로 연결 및 출력한다.

이제, 우리가 입력한 값이 잘 들어갔는지 확인해볼 시간이다.
idtitle 만 조회해보자.

데이터가 잘 삽입된 것을 볼 수 있다.

코드의 수정

그런데... 뭔가 좀 아쉽다. 우리가 코딩한 database_mysql.js 은 정상적인 앱의 기능을 하지 못하고 있다.

SQL문에서 VALUES 의 값을 매번 ("Nodejs", "Server side javascript", "kkongji") 와 같이 하드코딩해야한다면 nodejs가 하는 일을 우리가 하는 격이다.

다음과 같이 코드를 수정해보면 어떨까?

database_mysql.js

var mysql = require('mysql');
var conn = mysql.createConnection({
  host     : 'localhost',
  user     : 'root',
  password : 'kjh950330',
  database : 'o2'
});

conn.connect();

var sql = 'INSERT INTO topic (title, description, author) VALUES(?, ?, ?)';
var params = ['Supervisor', 'Watcher', 'graphitte'];

conn.query(sql, params, function(err, rows, fields) {
  if(err) {
    console.log(err);
  } else {
    console.log(rows);
  }
});
conn.end();

VALUES 의 파라미터에 ? 치환자를 입력하고, 변수 params 에 각 ? 에 해당하는 원소를 집어넣는 방식으로 바꾼다. 그리고 query 함수의 인자값으로 params을 넣어준다. 이제 node에 의해 params 배열에 해당하는 값들을 인식해 DB에 알아서 INSERT 될 것이다.

(* CRUD 중 Update와 Delete의 내용이 남아있지만 Create(Insert), Read(SELECT) 의 내용과 대동소이하기 때문에 생략함)

장점

위처럼 치환자를 이용하는 방식은 보안에 있어서도 장점이 있다. 우리가 DB에 사용자의 입력 값을 그대로 DB에 저장하면 다음과 같은 일이 발생할 소지가 있다.

SQL문은 특성상 데이터를 삽입하는 과정에서 보안상 취약점이 있다. 대표적으로 SQL injection 이라고 불리는 DB 공격 방식을 들 수 있다. 이는 DB에서 클라이언트의 입력값을 그대로 저장하는 로직을 사용한다면 이를 이용해 악의적으로 코드를 조작하여 DB에 심각한 장애를 초래하는 방식이다. 쉬운 난이도에 비해 엄청난 파괴력을 가지고 있기 때문에 보안쪽에서는 위협 1순위로 분류하고 있다.

너무나도 잘 알려진 취약점 공격이기 때문에 요즘 대부분의 서버는 SQL 인젝션에 대한 방어가 되어있다고 한다. (출처: 나무위키) 그렇지만 이런 이슈를 항상 염두에 두고 DB 로직을 설계하는 것이 백엔드 개발자의 기본 소양이라고 생각한다.

여담으로..

치환자 ? 와 같은 Preparedstatement에 대해 더욱 알고 싶다면?
저의 포스팅 JSP - 로그인 기능 구현하기 참조해주시길..ㅎㅎ

profile
학습하며 도전하는 것을 즐기는 개발자

0개의 댓글