본문 바로가기
Javascript/Node.js

Node.js Express - Oracle DB 연동하기 (with Connection Pool)

by eurowondollaryen 2021. 8. 27.

서론

검색하면 여러 글이 나오긴 하는데 대부분 Standalone connection에 대한 내용이었습니다. connection pool에 대한 부분은 구조를 어떻게 짜야할 지 이해가 잘 되지 않아, 결국 Oracle 공식 문서를 보고 이해한 뒤, 까먹을 때 마다 보려고 이 포스트를 작성하게 되었습니다.

 

0. 파일 구성 및 사용 방법

작성할 소스 파일은 아래 2가지 입니다.

db.js - connection pool을 통해 sql을 실행하는 함수를 가진 소스

dbConfig.js - 접속 정보를 가진 소스

 

db는 dbConfig.js를 참조하며, DB 조회가 필요한 소스코드에는 db.js만 require해서, 그 안의 query(sql, parameterArray) 함수를 사용하시면 됩니다. 파라미터의 경우, :ABC 와 같이 임의의 변수 형태로 sql문에 넣은 뒤, 배열을 통해 대입하여 쿼리문을 실행하게 됩니다. 아래처럼.

app.get("/searchEmployees", async (req, res) => {
  try {
    const { keyword } = req.query;
    const sql = `SELECT * FROM HR_RATE001
    WHERE STDR_DE = '20210524'
    AND DEPT_NM LIKE '%' || :DEPT_NAME || '%'`;
    pool.query(sql, [keyword]);
    res.json({"msg": "done"});
  } catch (err) {
    console.error(err.message);
    res.json(err.message);
  }
});

 

1. dbConfig.js

DB 접속 정보를 다음 형식에 맞게 적기만 하면 됩니다. 환경변수는 나중에 Heroku 등에 배포할 때 적절한 명칭을 사용하면 됩니다.

/* Database Info */
module.exports =
{
    user : process.env.NODEORACLEDB_USER || "접속id",
    password : process.env.NODEORACLEDB_PASSWORD || "접속pw",
    connectString : process.env.NODE_ORACLEDB_CONNECTIONSTRING || "IP:포트/SID"
}

 

2.db.js

sql문, 파라미터만 받아서 실행할 수 있게 모듈화한 소스코드입니다. 설명은 주석을 참고 바랍니다.

const oracledb = require('oracledb');
const dbConfig = require("./dbConfig.js");

/*****************************************************
* query
* query를 connection pool을 통해 실행하는 함수.
*  < parameters >
* sql : query를 담은 string 타입
* parameterArray : query에서 사용될 파라미터를 담은 Array
*****************************************************/
const query = async(sql, parameterArray) => {
  let pool;

  try {
    pool = await oracledb.createPool({
      user: dbConfig.user,
      password: dbConfig.password,
      connectString: dbConfig.connectString,
      enableStatistics: true,
    });
    console.log("Connection pool started.");

    //pool이 running중이므로, 여기에 query 로직
    await dostuff(sql, parameterArray);
  } catch (err) {
    console.error("init() error: " + err.message);
  } finally {
    //await closePoolAndExit();
    await pool.close();
  }
};

/*****************************************************
 * dostuff
 * query()가 받은 sql을 실제로 실행해주는 함수
*****************************************************/
const dostuff = async (sql, parameterArray) => {
  let connection;
  try {
    //get a connection from the default pool
    connection = await oracledb.getConnection();
    const options = { outFormat: oracledb.OUT_FORMAT_OBJECT };
    const result = await connection.execute(sql, parameterArray, options);
    console.log(result);
    //oracledb.getPool().logStatistics(); //query 실행 통계값을 출력해준다. pool 생성 시, enableStatistics 옵션이 true여야 사용 가능.
  } catch (err) {
    console.error(err);
  } finally {
    if (connection) {
      try {
        await connection.close();
      } catch(err) {
        console.error(err);
      }
    }
  }
};
exports.query = query;

 

 

Reference

아래 링크의 15. Connection Handling에서 Standalone Connection, Pooled Connection 방식을 모두 다루고 있습니다.

http://oracle.github.io/node-oracledb/doc/api.html#usermanual

'Javascript > Node.js' 카테고리의 다른 글

macOS에서 Nodemon 실행이 되지 않을 때  (0) 2021.05.02