Node Express 기반에서 가장 많이 사용하는 ORM Framework은 Sequelize ORM Framework입니다.
Sequelize ORM Framework 을 사용하면 SQL을 직접 작성하지 않고도 데이터베이스 작업을 수행할 수 있습니다. 이는 개발 시간을 단축하고 코드의 가독성을 향상시키는 데 도움이 됩니다.

관련 실습 깃허브 링크 정보 : https://github.com/eddykang1074/node-express-app.git

Sequelize ORM Framework의 주요 특징에 대해 알아봅니다.
-다양한 데이터베이스 지원: Sequelize는 MySQL, PostgreSQL, SQLite, MariaDB, MSSQL 등 다양한 SQL 데이터베이스를 지원합니다.
-모델 정의: Sequelize를 사용하면 데이터베이스의 테이블을 JavaScript 객체로 표현할 수 있습니다. 이 객체를 모델이라고 부릅니다.
-동기화: Sequelize는 모델과 데이터베이스 스키마 간의 동기화를 지원합니다. 이는 모델의 변경 사항을 데이터베이스에 자동으로 반영할 수 있게 해줍니다.
-CRUD 연산: Sequelize는 데이터베이스의 레코드를 생성(Create), 읽기(Read), 업데이트(Update), 삭제(Delete)하는 기능을 제공합니다.
-트랜잭션: Sequelize는 데이터베이스 트랜잭션을 지원합니다. 이는 여러 개의 쿼리를 하나의 단위로 묶을 수 있게 해줍니다.
-관계: Sequelize는 일대일, 일대다, 다대다 관계를 포함한 다양한 유형의 관계를 지원합니다.


Node Express 프로젝트에서 Sequelize ORM Framework을 사용하는 절차는
크게 Node Express 프로젝트에  ORM 환경 구성단계와 모델 생성 및 사용하기 단계로 나누어집니다.


1) Node Express 프로젝트 Sequelize ORM Framework 환경 구성하기 
아래의 Step1~ Step6 단계까지 절차를 따라 진행해주세요. 


Step1)Express 프로젝트 Sequelize ORM 패키지 설치
- Sequelize는 Node 기반의 MySQL 지원 오픈소스 노드 패키지 모듈
- NPM 을 통해 별도 패키지 설치 필요
- Express 프로젝트 생성 이후 추가 설치 가능하며 설치 후 Model 기반 ORM 프로젝트 환경 구성 자동화 제공

-sequelize(ORM기능제공),mysql2(MySQL서버연결기능제공) 노드 패키지 2개 동시 설치합니다.
npm install sequelize mysql2 


-sequelize-cli 패키지  전역설치 :  sequelize 명령어 사용을 위한 전역 패키지로 설치함
npm install -g sequelize-cli


Step2)Express 프로젝트에 ORM/Model 개발환경/프로젝트 구조 만들기 
-sequelize-cli 전역 패키지를 설치하면
sequelize CLI 명령어를 통해 노드 Express 프로젝트에 ORM(모델기반) 기반 프로젝트 템플릿(샘플소스/구조)을 자동으로 생성하여 빠르게 ORM/Model기반 프로그래밍할수 있는 프로젝트 구조를 생성해줍니다.  

-Node Express 프로젝트 ORM/Model 기반 개발환경/프로젝트 구조 만들기
sequelize init

-sequelize init 명령어를 실행하면 현재 Node Express프로젝트 MVC 패턴 Model 영역에 관련된 프로젝트 폴더/파일들을 신규 생성/구성 해줍니다.

ㅁORM/Model 관련 주요 폴더 
- config 폴더 : DB연결정보 환경설정 파일 제공
- models 폴더 : 테이블과 맵핑 되는 모델 정의 파일 보관 및 모델 기반 프로그래밍 처리 모듈 제공

- migrations 폴더 : 구조변경 마이그레이션 계획 정보 기록
- seeders 폴더 : 테이블 생성시 초기 데이터 생성 설정


Step3) MySQL Database 생성하기  
-여러분 컴퓨터에 MySQL이나 MariaDB서버를 설치합니다.
-설치 가이드는 아래 링크를 참고합니다.
-DB 서버 설치가 완료되었으면 Workbench를 통해 로컬에 설치된 MySQL DB서버에 접속하고 아래와 같이 blog 스키마명으로 신규 Database를 생성합니다.
schema name : blog

CREATE SCHEMA `blog` DEFAULT CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;


Step4) Express 프로젝트 MYSQL DB 연결 환경설정 적용하기 
-프로젝트내 config폴더내 config.json파일 오픈 후 여러분 환경에 맞는  DB연결정보(development) 수정 후 저장합니다.
-development는 로컬 개발환경에서의 DB서버 연결정보이고 test는 회사내 개발 DB 서버 연결정보, production은 실제 운영DB서버 연결정보를 저장합니다.
-development/test/production는 어플리케이션의 서비스모드를 나타내며 .env환경설정 파일에서 관련 서비스 모드를 관리할수 있습니다.
**주의: 실제 서비스 시점에는 반드시 config.json내 DB연결정보는 .env 환경설정 파일에 설정해서 사용해야하며 소스저장소들에 config.json 내용이 공유안되게 관리에 주의를 해야합니다.

-config/config.json

{
  "development": {
    "username": "root",
    "password": "eddy123456!",
    "database": "blog",
    "host": "127.0.0.1",
    "dialect": "mysql",
    "timezone":"+09:00"
  },
  "test": {
    "username": "root",
    "password": "eddy123456!",
    "database": "blog",
    "host": "127.0.0.1",
    "dialect": "mysql",
    "timezone":"+09:00"
  },
  "production": {
    "username": "root",
    "password": "eddy123456!",
    "database": "blog",
    "host": "127.0.0.1",
    "dialect": "mysql",
    "timezone":"+09:00"
  }
}


Step5) Model Index 모듈 구성하기 
-ORM에서 상기 연결하고자 하는 MySQL서버의 blog Database(Schema)와 앱핑되는 DB객체를 제공하는 DB모듈파일을 구성해야합니다.
-models\index.js 모듈을 열고 예시로 코딩된 내용을 모두 삭제하고 아래 예시 코드로 변경 저장합니다.
-models\index.js 모듈 파일은 MySQL서버의 blog Database(Schema)와 매핑되는 db객체를 제공하고 DB서버와의 연결 및 향후 해당 db객체에 연결되는
각종 테이블과 맵핑되는 모델속성을 통해 ORM 데이터 관리 기능이 제공되는 핵심 모듈파일입니다. 

- models\index.js

const path = require('path');
const Sequelize = require('sequelize');

//개발모드 환경설정
const env = process.env.NODE_ENV || 'development';

//DB연결 환경설정정보 변경처리//관련정보 수정
const config = require(path.join(__dirname,'..','config','config.json'))[env];

//데이터 베이스 객체
const db= {};

//DB연결정보로 시퀄라이즈 ORM 객체 생성
const sequelize = new Sequelize(config.database,config.username,config.password,config);

//DB 처리 객체에 시퀄라이즈 정보 맵핑처리
//이후 DB객체를 통해 데이터 관리가능해짐
db.sequelize = sequelize; //DB연결정보를 포함한 DB제어 객체속성(CRUD)
db.Sequelize = Sequelize; //Sequelize팩키지에서 제공하는 각종 데이터 타입 및 관련 객체정보를 제공함


//게시글 모델 모듈 파일 참조하고 db속성정의하기
//db.Article = require('./article.js')(sequelize,Sequelize);

//db객체 외부로 노출하기
module.exports = db;


Step6) Node Applicaiton에 MY SQL 서버 연결 및 동기화 하기 
- app.js 파일에  시퀄라이즈  models/index.js Database 모듈을  참조하여 DB서버와 연결하고
- 각종 모델 파일과 물리적 테이블간의 맵핑을 동기화 처리합니다. 

--app.js 

...
//기본 샘플 라우터 모듈 파일 참조 영역
var indexRouter = require('./routes/index');
var usersRouter = require('./routes/users');
//게시글 웹페이지 요청/응답 라우터모듈 파일 참조
var articleRouter = require('./routes/article');


//mysql 서버와 연결합니다.  
var sequelize = require('./models/index.js').sequelize;

var app = express();
//DB 객체를  기반으로 DB객체,모델파일과  물리적 Database,Table들을 동기화 처리합니다.
sequelize.sync();
...


지금까지 총 Step6 단계를 완료하면 Node Express 프로젝트 ORM 기반 MVC 패턴의 Model 영역 개발환경 구성을 완료한것입니다.
Sequelize ORM DB 프로그래밍 환경 구성이 완료되었다면 노드 어플리케이션을 실행해보십시오.

정상적으로 Node Application 이 실행되면 아래와 같이 DB서버 연결 메시징 로그가 터미널영역에 출력될것이며 그렇지 않다면 붉은색 글자로 App Crash 에러 메시지가 표시될것입니다. 
Executing (default): SELECT 1+1 AS result

App Crash 에러가 발생하면 에러 로그의 자세한 내용을 확인해보거나 DB연결 정보가 정확한지  다시 한번 확인해보시기 바랍니다.
Sequelize ORM 환경의 실행순서를 간략히 정리해드립니다.
아직 models/article.js 모델 모듈을 생성하지는 않았지만 실행순서는 아래와 같은 실행됩니다.
app.js -> models/index.js - db server connection - models/article.js(모델파일) 동기화 -> article 물리 테이블 생성(blog DB에 article 테이블이 없는경우)


2) Node Express 프로젝트 Sequelize ORM 모델 생성 및 사용하기 
Node Express 프로젝트에 Sequelize ORM Framework 환경 구성이 완료되면 
Data Model(Object) 모듈을 생성하고 해당 모듈 과  물리적 테이블을 1:1  맵핑시켜 ORM DB 프로그래밍이 가능합니다. 

A) ORM 기반 모델을 생성하는 방식 2가지 소개  

ㅁ Code(Model) First 방식
-현대적 ORM Framework이 기본적으로 제공하는 방식으로 모델(오브젝트) 모듈(클래스)를 먼저 만들고 해당 모델 모듈을 통해 물리적 테이블을 생성하는 방식
-신규 백엔드 프로젝트를 진행하고 신규 DB/Table을 생성하는 프로젝트에 용이
-모델 모듈을 먼저 만들고 관련 물리적 테이블이 없으면 새로 물리적 테이블을 생성하고 이미 존재하면 물리 테이블은 생성하지 않습니다. 

ㅁ DB First 방식
-물리적 Table을 먼저 만들고 만들어진 Table을 기반으로 모델(오브젝트) 모듈을 만드는 방식
-기존에 이미 사용중인 Database와 Table,Data가 존재하는 경우 주로 사용
-DB는 그래도 사용하고 백엔드 어플리케이션만 재구축하는 경우 주로 사용  

B) 게시글 모델 모듈 생성하기
- ORM DB 프로그래밍을 위해서는 먼저 물리적 테이블과 맵핑될 모델 모듈을 먼저 생성(Code First방식)합니다.
- 모델 모듈은 models 폴더내에 테이블 이름의 모델 모듈을 생성합니다.
-아래 article.js는 게시글 테이블과 맵핑되는 article 모델 모듈 정의를 위한 모듈파일입니다.
-models폴더 아래 article.js 파일을 생성합니다. 

-models/article.js


module.exports = function(sequelize,DataTypes){
    return sequelize.define('article',{
        aid: {
            type: DataTypes.INTEGER,
            autoIncrement: true, //자동채번 설정
            primaryKey: true, //Primary키 설정
            allowNull: false,
            comment: '게시글고유번호',
        },
        title: {
          type: DataTypes.STRING(200),
          allowNull: false,
          comment: '글제목',
        },
        content: {
            type: DataTypes.TEXT,
            allowNull: true,
            comment: '글내용',
        },
        view_cnt: {
            type: DataTypes.INTEGER,
            allowNull: false,
            comment: '조회수',
        },
        ip_address: {
            type: DataTypes.STRING(50),
            allowNull: false,
            comment: '작성자IP주소',
        },
        display_yn: {
            type: DataTypes.TINYINT,
            allowNull: false,
            comment: '게시여부 0:게시안함 1:게시함',
        },
        regist_date: {
            type: DataTypes.DATE,
            allowNull: false,
            comment: '등록일시',
        },
        regist_user_name: {
            type: DataTypes.STRING(100),
            allowNull: false,
            comment: '등록자명',
        },
        moidify_date: {
            type: DataTypes.DATE,
            allowNull: true,
            comment: '수정일시',
        },
        modify_user_name: {
            type: DataTypes.STRING(100),
            allowNull: true,
            comment: '수정자명',
        }
    },
    {
        sequelize,
        tableName: 'article', //기본 테이블명 옵션이 복수형이 아닌 여기 지정한 테이블명으로 생성됨
        timestamps: false,
        comment: '게시글정보테이블',
        indexes: [
          {
            name: 'PRIMARY',
            unique: true,
            using: 'BTREE',
            fields: [{ name: 'aid' }],//여러개의 컬럼이 프라이머리키인경우(복합키){}추가하여 설정가능
          },
        ],
    }
 );
}


C) DB 객체에 게시글 모델 속성으로 제공하기 
- 특정 모델을 만들고 나면 반드시 models/index.js 모듈내에 db객체에 속성으로 관련 모델 모듈을 참조하고 속성으로 노출시켜줘야
- 다음 라우팅모듈에서 db객체의 속성명으로 해당 모델에 접근가능하게 됩니다.
-models/index.js DB모듈에 아래와 같이 특정 모델 모듈을 참조하고 저장하면 DB서버와 연결 후 물리적 article 테이블이 MYSQL 서버 blog Tables목록에 자동 생성된것을 확인해보십시오.
-models/index.js

.... //DB 처리 객체에 시퀄라이즈 정보 맵핑처리
//이후 DB객체를 통해 데이터 관리가능해짐
db.sequelize = sequelize; //DB연결정보를 포함한 DB제어 객체속성(CRUD)
db.Sequelize = Sequelize; //Sequelize팩키지에서 제공하는 각종 데이터 타입 및 관련 객체정보를 제공함


//게시글 모델 모듈 파일 참조하고 db속성정의하기
db.Article = require('./article.js')(sequelize,Sequelize);

//db객체 외부로 노출하기
module.exports = db;


D) 라우팅 모듈에서 ORM DB모듈 참조하기 
- 새로 만들어진 모델 모듈은 models/index.js 모듈내 db 객체의 속성을 통해 데이터 등록/수정/삭제/조회 등 기본 ORM 기본 메소드가 제공됩니다.
- 모델을 이용한 DB 프로그래밍 위치는 주로 MVC 패턴을 사용하는경우 Controller(Router) 영역이나 별도 DB 프로그래밍 계층에서 사용됩니다.
- routes/article.js 라우터 파일을 열고 ORM DB 모듈을 참조하여 ORM DB 프로그래밍을 위한 db객체를 생성합니다.
- routes/article.js

//express 패키지를 참조합니다.
var express = require('express');

//express객체의 Router()메소드를 호출하여 사용자 요청과 응답을 처리하는 서버측 router 객체를 생성합니다.
//일반적으로 서버측 각각의 라우팅 모듈은 추후 app.js내에서 기본 URL주소체계를 정의하게 되며
//article.js 라우팅 모듈의  기본주소 체계로  http://localhost:3000/article 를 사용할 예정입니다.  
var router = express.Router();


//ORM db객체 참조하기
var db = require('../models/index'); ...