ORM이란 Object-Relation-Mapping의 약자이다.
즉, 객체와 데이터베이스 매핑입니다. 우리가 프로그래밍에서 사용하는 객체(OOP-Object Oriented Programming)의 개념과 RDB(Relational Database)에서 사용하는 테이블을 매핑해서 쉽게 사용한다는 개념이다.
node.js에서의 ORM은 Sequelize, TypeORM, Prisma 등이 있다.
ORM을 이용하면 일반적인 SQL Query가 아닌 좀 더 직관적인 코드로 데이터를 조작할 수 있다.
SELECT * FROM post WHERE authorId = 2;
SQL Query에서 post라는 테이블에 authorId=2인 데이터를 조회하기 위해서 사용하는 쿼리이다.
Post.findAll({
where: {
authorId: 2
}
});
위는 Sequelize에서 사용되는 같은 문법이다.
데이터베이스에 대한 연결을 처리한다. 직접 SQL Query를 작성하여 데이터베이스를 처리한다.
// $ npm install pg
const { Client } = require('pg')
const connection = require('./connection.json')
const client = new Client(connection)
client.connect()
const query = `SELECT
ingredient.*, item.name AS item_name, item.type AS item_type
FROM
ingredient
LEFT JOIN
item ON item.id = ingredient.item_id
WHERE
ingredient.dish_id = $1`
client.query(query, [1]).then((res) => {
console.log('Ingredients:')
for (let row of res.rows) {
console.log(`${row.item_name}: ${row.quantity} ${row.unit}`)
}
client.end()
})
드라이버 모듈을 사용하는 것과 ORM을 사용하는 것의 중간 단계. SQL Query를 작성하는것 보단 좀 더 편리한 동적 쿼리를 프로그래밍 방식으로 생성.
// $ npm install pg knex
const knex = require('knex')
const connection = require('./connection.json')
const client = knex({
client: 'pg',
connection,
})
client
.select([
'*',
client.ref('item.name').as('item_name'),
client.ref('item.type').as('item_type'),
])
.from('ingredient')
.leftJoin('item', 'item.id', 'ingredient.item_id')
.where('dish_id', '=', 1)
.debug()
.then((rows) => {
console.log('Ingredients:')
for (let row of rows) {
console.log(`${row.item_name}: ${row.quantity} ${row.unit}`)
}
client.destroy()
})
관계형 데이터베이스의 데이터를 프로그래밍 객체에 매핑하는 것. 생각보다 복잡한 라이브러리 이므로 많은 학습이 필요하다.
const user = await User.create({
username: 'alice123',
isAdmin: true
}, { fields: ['username'] });
// let's assume the default of isAdmin is false
console.log(user.username); // 'alice123'
console.log(user.isAdmin); // false
.
.
.
const { Op } = require("sequelize");
Post.findAll({
where: {
[Op.and]: [
{ authorId: 12 },
{ status: 'active' }
]
}
});
// SELECT * FROM post WHERE authorId = 12 AND status = 'active';
그렇다면 어떤것을 공부하며 사용하는게 좋을까?
개인적으로는 Raw Query와 ORM 둘 다 꾸준한 학습이 필요하고 상황에 맞게 사용하는것이 필요하다.
Raw쿼리는 세부적이고 복잡한 쿼리 작성이 가능하고 ORM에 비해 빠른 속도를 가지지만 기본적으로 Query 작성법을 숙지하고 db 의존성이 심하다. 또한 코드가 복잡해지면 가독성이 떨어진다.
ORM은 프로그래밍의 객체지향 특성을 살리기 좋고 코드의 가독성이 증가한다. 또한 좀 더 직관적이고 쿼리 의존성이 감소한다. 또한 db가 바뀌어도 쉽게 수정 가능하다.
그러나 복잡하고 세부적인 쿼리를 작성하지 못할 수 있고 속도가 좀 더 느리며 상황에 따라 비효율 적일수 있다.
Sequelize와 TypeORM은 모두 Node.js 생태계에서 널리 사용되는 객체 관계형 매핑(ORM) 라이브러리이다. 이를 통해 개발자는 JavaScript/TypeScript를 사용하여 관계형 데이터베이스와 상호 작용할 수 있으며, 기본 SQL을 추상화할 수 있다.
다음은 결정을 내리는 데 도움이 될 수 있는 두 라이브러리의 몇 가지 차이점이다:
언어 지원: Sequelize는 JavaScript로 작성되어 JavaScript와 TypeScript를 지원하는 반면, TypeORM은 TypeScript로 작성되어 TypeScript를 지원한다.
쿼리 작성: Sequelize와 TypeORM은 데이터베이스와 상호 작용하기 위해 서로 다른 접근 방식을 사용한다. Sequelize는 쿼리 빌더 접근 방식을 따르며, 여기에는 쿼리를 형성하기 위해 메서드를 연결하는 방식이 포함된다. 반면 TypeORM은 엔티티로 작업하고 찾기 또는 저장과 같은 메서드를 사용하여 데이터베이스와 상호 작용하는 데이터 매퍼 접근 방식을 사용한다.
관계: TypeORM은 다대다 관계와 같은 복잡한 관계를 더 잘 지원하는 반면, Sequelize는 이러한 관계를 설정하는 데 더 많은 수동 구성이 필요하다.
데이터베이스 지원: Sequelize는 MySQL, PostgreSQL, SQLite 및 MSSQL과 같은 다양한 데이터베이스와 호환된다. 반면, TypeORM은 MySQL, PostgreSQL, SQLite, Oracle, SQL Server, CockroachDB, MongoDB와 함께 작동할 수 있는 기능을 제공한다.
전반적으로, 데이터 매퍼 접근 방식을 선호하고 복잡한 관계에 대한 더 나은 지원을 원한다면 TypeORM이 프로젝트에 더 적합할 수 있다. 쿼리 빌더 접근 방식을 선호하고 더 광범위한 데이터베이스를 지원해야 하는 경우, Sequelize가 더 적합할 수 있다.
또한 TypeORM은 제공하는 entities의 변화를 자동 감지해서 마이그레이션하는 기능을 제공한다고 한다.(Sequelize는 없는듯하다.)
전반적으로 같은 쿼리를 실행했을 때 TypeORM이 Sequelize는보다 평균적으로 속도가 조금 더 빨랐으며 문법이 개인적으로 조금 더 직관적이었다.
프로젝트마다 차이가 있겠지만 개인적으로 TypeORM을 좀 더 많이 사용할 것 같다.