2015년 1월 14일 수요일

[node express] express-session 간단 사용 예제


  • session은 서버가 클라이언트를 식별하기 위하여 사용한다. 대표적인 사용예로는 로그인 관리가 있다.
  • express 3.x 버전에서는 express의 Middleware 즉, express-session, cookie-session, body-parser, cookie-parser 외의 여러 내장했던 모듈들이 포함되어 있었다고 한다.
  • 하지만 express 4.x 버전 부터는 이러한 미들웨어들이 분리가 되면서, express-session등을 따로 사용하기 위해선 별도의 설치가 필요하다.

  • 진행중인 express 폴더내에 express-session을 따로 설치해준다.


1
npm install express-session

  • 그리고 express에 연결시켜줍니다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
var express = require('express');
var session = require('express-session');
...
var app = express();
...
app.use(session({
  secret: 'keyboard cat',
  resave: false,
  saveUninitialized: true
}));

  • 여기서 secret은 쿠키의 값의 변조를 방지하기 위한 값입니다. 그리고 세션의 기본 난수 발생 등을 위하여 사용되는 것입니다.??(확인 안해봤습니다.) 값은 원하시는 대로 넣으시면됩니다.
  • resave는 세션의 값이 변경이 될경우 자동 저장의 여부인데 기본적으로 default값은 true값 이지만 express-session 메뉴얼에서도 추천하지 않습니다.
  • saveUninitalized는 반대로 default값이 false지만 역시 express-session에서 추천하지 않습니다. 때문에 true로 설정합시다.
  • 연결이 되었으니 사용해 봅시다.


1
2
3
//req.session.[세션의 변수명] = [넣을 값];

req.session.logined = 'logined';

  • 이제 express내에서 받아오는 request(req)의 세션 값을 가져오고 수정하기 위하여 위와 같이 접근하면 됩니다.

2015년 1월 13일 화요일

[node 웹페이지 만들기] 4. Mysql 연결하기

  • 값이 서로 넘어가는 방법을 알아보았고, mysql 모듈을 사용하는 방법을 알아내었으니 회원가입을 하여 db에 저장하는 방법을 해보려고 합니다.
  • db에 연결하는 방법은 단순히 connection을 이용하는 방법이 있지만, 실제서버에서는 안정적인 connection pooling기법을 사용하고 있습니다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
var pool  = mysql.createPool({
  connectionLimit : 150,
  host     : 'localhost',
  user     : 'root',
  password : '1234',
  database : 'node'
});

...
...
...
//members
router.post('/members', function(req,res){
 // console.log(req.body);
 var attr = req.body;
 delete(attr.id_ch);
 delete(attr.pass_ch);
 delete(attr.email_ch);
 delete(attr.tel1);
 delete(attr.m_tel2);
 delete(attr.m_tel3);
 delete(attr.m_pass_ch);

 var queryString = 'Insert into member Set ?';
 pool.getConnection(function(err,connection){
  connection.query(queryString,req.body, function(err, result) {
   if (err) throw err;
   console.log("insert member!");
  });
  connection.release();
  res.render('members',req.body);
 });
});

  • pooling 예제에서했던것들을 중간에 넣어 사용하면 끗!
  • join(회원가입)에서 members로 페이지를 넘기면 db에관한 처리후(24~30라인) members.ejs를 불러와 페이지를 로드(31번라인)합니다.
  • 제 예제에서는 member에 들어가는 값들에는 불필요한 값들(16~22번라인)의 값들을 제거하고 26번줄의 req.body를 넣어줌으로서 값에 대한 맵핑을 손쉽게 처리하였습니다.


  • 으로 값을 넣어 가입을 눌러
  • DB에 값이 저장되었습을 확인하였습니다.

[node mysql] node-mysql -> transaction


  • node mysql에서는 트랜젝션을 제공한다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
connection.beginTransaction(function(err) {
  var post  = { m_tel: '010-1234-5678', m_id: 'GilDong2', m_pass: 'password1', m_name: '이순신',
                m_date: '2000-01-01', m_gender: '남', m_email: 'GilDong@Hong.com' };

  if (err) { throw err; }
  connection.query('INSERT INTO member SET ?', post, function(err, result) {
    console.log(result);
    if (err) {
      connection.rollback(function() {
        console.log("1.error");
        throw err;
      });
    }

    //실행된 결과가 0일경우
    connection.query('update member set m_gender = ? where m_name = ?', ['여','강감찬'], function(err, result) {
      console.log(result);
      if (!result.affectedRows) {
        connection.rollback(function() {
          console.log("2.error");
        });
      }
      connection.commit(function(err) {
        if (err) {
          connection.rollback(function() {
            throw err;
          });
        }
        console.log('success!');
      });
    });
  });
});


  • 주요코드는 beginTransaction(), rollback(), commit() 이다.
  • beginTransaction으로 감싼 부분이 트렉젝션이 적용된다.
  • 쓰기에 따라서, 8번라인처럼 err가 발생했을경우, 또는 17번라인처럼 해당쿼리의 결과에 따른 경우에 따라서 rollback을 실행시키면된다. 만약 중간에 rollback이 실행된다면 이전의 처리는 모든게 무효화 될것이다.
  • Transaction의 마지막 부분에 있어서 commit을 해줌으로서 모든 결과를 완료한다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
{ fieldCount: 0,
  affectedRows: 1,
  insertId: 0,
  serverStatus: 3,
  warningCount: 0,
  message: '',
  protocol41: true,
  changedRows: 0 }
{ fieldCount: 0,
  affectedRows: 0,
  insertId: 0,
  serverStatus: 35,
  warningCount: 0,
  message: '(Rows matched: 0  Changed: 0  Warnings: 0',
  protocol41: true,
  changedRows: 0 }
2.error
success!


  • 위 코드의 결과이다. 결과값에서의 위쪽 쿼리에서의 처리된 row가 1, 아래의 쿼리에서의 처리된 row는 0으로서 본문코드의 18번에 해당되어 Rollback이  진행되었다.
    • result의 affrectedRows는 처리된 레코드의 수를 반환한다.
    • 2error 발생 확인.
  • 먼저 처리한쿼리(insert)의 결과는 1이므로 적용이 됬어야하지만, 트렌젝션으로 묶여있는 아래쿼리에서 롤백이 일어나 insert됬던 결과가 무효화 되었음을 확인하였다.
    • 기존에 1레코드 있었음

2015년 1월 11일 일요일

[node mysql] node-mysql -> connection pool

  • connection은 연결 때 마다 connection을 새로 만들고 사용하면 연결을 끊는다. 1회성의 성격을 가진다는 뜻이다. 때문에 연결시마다 connection을 새로 생성하는데에 있어 낭비되는 자원이 생긴다.
  • pool은 connection들을 미리 만들어서 관리를 해주기 때문에 이러한 문제를 해결할 수 있다. 
  • connection pooling 기법은 미리 설정해 놓은 크기의 connection들을 준비하여 요청을 받으면 자원을 빌려주고 돌려받는다. pool은 그 connection의 연결을 끊지 않고 요청을 다시 기다리기 시작한다.
    • 즉 connection들을 관리하며 재사용을 한다.
  • 정해진 pool의 크기내의 연결은 원활한 연결을 지원하며, 넘어서는 연결 요청이 들어오면 이후의 요청들은 connection자원들이 생길때까지 대기를 한다.
    • pool이 아닌 보통의 connection에서는 많은 크기의 요청도 다 받아들이지만 느려지는 등의 부하를 준다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
var mysql = require('mysql');
var pool  = mysql.createPool({
  connectionLimit : 10,
  host     : 'localhost',
  user     : 'root',
  password : '1234',
  database : 'node'
});

pool.on('connection', function (connection) {
  console.log('SET SESSION auto_increment_increment=1')
});

pool.on('enqueue', function () {
  console.log('Waiting for available connection slot');
});

for(var i = 1;i<=15;i++){
 console.log(i);
 var pool_con =
  pool.getConnection(function(err, connection) {
    // Use the connection
    connection.query( 'SELECT 1+1 AS solution', function(err, rows) {
      // And done with the connection.
      connection.release();

      // Don't use the connection here, it has been returned to the pool.
    });
  });
}


  • pooling의 예제 입니다. 
  • 3번 Line에서 connectionLimit는 pool의 크기입니다.
  • 10번라인은 pool내의 connection의 자원이 생길때 이벤트처리입니다.
  • 14번라인은 pool의 크기를 넘어서는 요청을 받아 대기열에 들어갈경우 발생하는 이벤트 처리입니다.



 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
0
1
2
3
4
5
6
7
8
9
10
Waiting for available connection slot
11
Waiting for available connection slot
12
Waiting for available connection slot
13
Waiting for available connection slot
14
Waiting for available connection slot
15
Waiting for available connection slot
SET SESSION auto_increment_increment=1
SET SESSION auto_increment_increment=1
SET SESSION auto_increment_increment=1
SET SESSION auto_increment_increment=1
SET SESSION auto_increment_increment=1
SET SESSION auto_increment_increment=1
SET SESSION auto_increment_increment=1
SET SESSION auto_increment_increment=1
SET SESSION auto_increment_increment=1
SET SESSION auto_increment_increment=1

  • 이 나옴을 볼수 있습니다.
  • pool의 크기가 10개인 만큼 10개까지는 처리가 잘되다가 이후부터는 enqueue이벤트가 발생, 즉 대기열에 들어감을 알수 있습니다.
  • 이후 release가 발생된다면 자원이 생겨 다음 요청을 처리하고 다시 다음 요청은 대기열에 들어가는 것이 계속 반복됩니다.
  • 이후 모든 요청이 처리되면 잉여 connection들이 생기면서 connection이벤트가 발생합니다. 모든 처리가 다 되는 시점에는 pool의 크기인 10번이 발생합니다.

2015년 1월 5일 월요일

[node mysql] node-mysql 예제


  • Express-ejs를 이용한 웹 서버에서 DB에 저장하는 것을 하기전에 mysql모듈에서 제공하는 기능들을 하나하나 알아가 보려고 합니다.
  • 또한 DB에 대한 아주 기초적인 쿼리문이나 지식이 필요합니다.

Mysql 모듈을 설치하기전에..

  • 당연 필요한것은 mysql입니다. mysql은 무료로 제공되고 있는 DataBase로서 가장 사랑받고 있습니다.
  • http://dev.mysql.com/downloads/mysql/에서 다운, 설치를 할수 있습니다.

Mysql 테이블 생성하기

  • node라는 스키마(데이터베이스)를 새로 만들어 줍니다.

1
2
3
create database node;

use node;

  • 저의 이전 회원가입 페이지에 맞는 테이블을 기준으로 테스트를 하겠습니다.

1
2
3
4
5
6
7
8
9
create table member(
 m_id varchar(20) primary key,
    m_pass varchar(200) not null,
    m_name varchar(20) not null,
    m_tel varchar(13) not null,
    m_date date not null,
    m_gender char(1) not null,
    m_email varchar(100) not null
);

  • 회원가입에 맞는 간단한 DB가 완성되었습니다. 이제 Node를 이용하여 테스트 해봅시다.

Mysql 모듈 설치하기

  • 우선 mysql 프로젝트 파일을 만들어 줍니다.
  • mysql이라는 모듈을 이용하여 mysql과 연결을 해보려고 합니다.
  • 설치 명령어는 npm install mysql 입니다.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
C:\>mkdir mysql_tutorial

C:\>cd mysql_tutorial

C:\mysql_tutorial>npm install mysql
mysql@2.5.4 node_modules\mysql
├── require-all@0.0.8
├── bignumber.js@1.4.1
└── readable-stream@1.1.13 (string_decoder@0.10.31, isarray@0.0.1, inherits@2
.0.1, core-util-is@1.0.1)

C:\mysql_tutorial>


  • mysql 모듈을 설치하였으니 바로 js파일(저의 경우 mysqls.js)을 만들어서 테스트 해봅시다.

예제 Test

  • 연결하기 -> 값 입력 -> 조회 -> 변경 -> 삭제 순서대로 해보겠습니다.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
var mysql      = require('mysql');
var connection = mysql.createConnection({
  host     : '[address]',
  user     : '[user]',
  password : '[password]',
});

connection.connect();

connection.query('SELECT 1 + 1 AS solution', function(err, rows, fields) {
  if (err) throw err;

  console.log(rows);
  console.log('The solution is: ', rows[0].solution);
});

connection.end();

  • 가장 처음 나오는 예제입니다.
  • 3~5번 라인에서는 각자에 맞는 값을 넣어 설정을 해줍니다.
    • 로컬에서 테스트한다면 [adress] 부분에 localhost
    • 여러가지 옵션이 여기의 connection option에 쭈욱 설명되어 있습니다.
  • 13번 라인은 예제에 없지만 결과값의 리턴 형식을 보기 위해 넣었습니다.
  • node [test].js 로 실행합니다.


1
2
3
4
5
C:\mysql_tutorial>node mysqls.js
[ { solution: 2 } ]
The solution is:  2

C:\mysql_tutorial>

  • [{solution:2}] 를 보아 결과값은 레코드별로 배열로, 컬럼은 JSON방식으로 넘어오는 것을 어림짐작 할수 있겠네요.
  • 예상된 결과가 잘 나왔음을 알수 있습니다.

Insert

mysqls.js

1
2
3
4
5
6
7
8
9
...
connection.connect();
var post  = { m_tel: '010-1234-5678', m_id: 'GilDong', m_pass: 'password1', m_name: '홍길동', m_date: '2000-01-01', m_gender: '남', m_email: 'GilDong@Hong.com' };
var query = connection.query('INSERT INTO member SET ?', post, function(err, result) {
  // Neat!
  console.log(result);
});

connection.end();

  • connection.query(쿼리,입력값,결과처리)로 이루어 집니다.
  • 입력값은 위의 post에 넣어준것처럼 json방식으로 입력하면되고 이는 ejs에서 값이 넘어오는 방식이랑 같으니 값을 db에 넘겨주기에도 편합니다.
  • 이제 실행을 해봅시다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
C:\mysql_tutorial>node mysqls.js
undefined

C:\mysql_tutorial>node mysqls.js
{ fieldCount: 0,
  affectedRows: 1,
  insertId: 0,
  serverStatus: 2,
  warningCount: 0,
  message: '',
  protocol41: true,
  changedRows: 0 }

  • 1~2라인은 실패 했을 경우 result, 4~12라인은 성공했을 경우 result 입니다.
  • mysql workbench에서 확인한 결과 값이 잘 들어갔음을 알수 있습니다.
  • Delete, Update 문도 이와같이 사용하면됩니다.

??와 ?(속성,값이 여러개인경우)


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
connection.connect();

var table = 'member';
var columns = ['m_id', 'm_pass'];
var where = 'm_id';
var userId = 'GilDong';
var query = connection.query('SELECT ?? FROM ?? WHERE ?? = ?', [columns, table, where,userId], function(err,rows, results) {
 console.log(rows);
});

connection.end();


  • 쿼리문에서 ?? 인경우에는 컬럼명, 테이블 명와 같은 속성값일 경우 씁니다.
  • ??와는 다르게 ?인 경우에는 값(변수) 일 경우 사용되며
  • 쿼리문의 ??,?의 순서대로 배열에 넣어 query의 두번째 속성값으로 입력하면됩니다.

결과값(리턴값) 보기

  • select로 한번 더 다른 예제를 해보겠습니다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
...
connection.connect();

connection.query('SELECT * from member', function(err, rows, fields) {
  if (err) throw err;

  console.log(rows);
  console.log(fields);
});

connection.end();

  • select와 동시에 옆에 err,rows,fields에 대한 것을 알아보겠습니다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
C:\mysql_tutorial>node mysqls.js
[ { m_id: 'GilDong',
    m_pass: 'password1',
    m_name: '홍길동',
    m_tel: '010-1234-5678',
    m_date: Sat Jan 01 2000 00:00:00 GMT+0900 (대한민국 표준시),
    m_gender: '남',
    m_email: 'GilDong@Hong.com' } ]
[ { catalog: 'def',
    db: 'node',
    table: 'member',
    orgTable: 'member',
    name: 'm_id',
    orgName: 'm_id',
    charsetNr: 33,
    length: 60,
    type: 253,
    flags: 20483,
    decimals: 0,
    default: undefined,
    zeroFill: false,
    protocol41: true },

  • rows는 앞에서 봤듯이 해당 결과에 대한 것을 레코드는 행렬로, 컬럼명와 값은 json으로 들어오는 것을 볼수 있고,
  • fields에 대한 값은 각각 컬럼에 대한 자세한 정보를 보여주고 있습니다.


1
2
3
4
5
6
7
8
9
connection.connect();

var post = {m_id:'GilDong'};
connection.query('SELECT * from member where ?',post, function(err, rows, fields) {
  if (err) throw err;

  console.log(rows);
  console.log(fields);
});

  • 위의 insert문과 같이 이렇게 사용할수 있습니다.

2015년 1월 4일 일요일

[node 웹페이지 만들기] 3.ejs 등록,실행, 페이지 간 값 넘기기

app.js에서...

  • 저는 이전에 만들어 놨던 페이지(회원가입)등을 member에서 관리를 할것입니다. 때문에 app.js에 등록을 하고 route파일을 만들고 ejs파일을 등록하는 식으로 진행 하겠습니다.

1
2
3
4
5
6
7
...
var routes = require('./routes/index');
var users = require('./routes/users');
...
app.use('/', routes);
app.use('/users', users);
...


  • app.js에서 이곳에 member route를 추가로 등록 하겠습니다.

1
2
3
4
5
6
7
8
9
...
var routes = require('./routes/index');
var users = require('./routes/users');
var member = require('./routes/member');
...
app.use('/', routes);
app.use('/users', users);
app.use('/member', member);
...


  • /member route에 등록된 모든 url은 주소:3000/member에 등록됬습니다.

member.js


1
2
3
4
5
6
7
8
9
var express = require('express');
var router = express.Router();

/* GET home page. */
router.get('/join', function(req, res) {
  res.render('member/join');
});

module.exports = router;



  • view/member/join.ejs는 주소:3000/member/join 의 url을 가지게 됩니다.
  • 다음은 ejs파일 넣어주는 일만이 남았습니다.

EJS 파일로 변경하기

  • [node 웹페이지 만들기] 1번이였던 join.html을 join.ejs로 바꿔줍니다. 끝
    • 제가 만들어 줬던 join페이지는 동적으로 구성할 필요가 없기 때문에 바꿔줄 것이 없습니다.
  • 또한 관련된 js와css를 public 내의 알맞는 위치에 넣어줍니다.

실행해보기

  • 정겨운 콘솔로 프로젝트 디렉터리에 들어가 node bin/www로 실행시켜 봅시다.
  • 그리고 127.0.0.1:3000/member/join 으로 들어가면

  • 알맞는 위치에 잘 작동하는 것을 알수 있습니다.

값넘기기


  • 회원가입에서 가입 버튼을 누르면 form에 등록된 주소로 값을 넘겨보도록 하겠습니다.
  • 값이 넘어갈 페이지를 members.ejs를 간단히 만들어 봤습니다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
<!DOCTYPE html>
<html lang='ko'>
<head>
 <meta charset='utf-8'/>
 <title>Members</title>
 <link rel="stylesheet" type="text/css" href="../style/mycss2.css">
 <script type="text/javascript" src="../js/jquery-1.9.1.min.js"></script>
 <script type="text/javascript" src="../js/myscript2.js"></script>
</head>
<body>
 <header></header>
 <div class = "body">
  <div class ="wrapper_table">
   <table>
    <thead>
     <tr>
      <td>아이디</td>
      <td>비밀번호</td>
      <td>이름</td>
      <td>생년월일</td>
      <td>휴대전화</td>
      <td>성별</td>
      <td>이메일</td>
     </tr>
    </thead>
    <tbody>
     <tr>
      <td><%= m_id %></td>
      <td><%= m_pass %></td>
      <td><%= m_name %></td>
      <td><%= m_tel %></td>
      <td><%= m_date %>
      <td><%= m_gender %></td>
      <td><%= m_email %></td>
     </tr>
    </tbody>
   </table>
  </div>
 </div>
</body>
</html>

  • 따라서 route파일(member.js)에도 추가하겠습니다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
var express = require('express');
var router = express.Router();

/* GET home page. */
router.get('/join', function(req, res) {
  res.render('join');
});

router.post('/members', function(req,res){
 console.log(req);
 res.render('members');
});
module.exports = router;

  • 프로젝트 1장에서 설명했듯이 회원가입과 같이 DB의 값을 입력,수정,삭제 하는 경우는 post로 처리해야 하기 때문에 route.post로 처리합니다.
  • 그리고 넘어오는 값이 어떤식으로 구성되어 있는지 아직 모르기 때문에 request(req)을 통채로 읽어보도록 하겠습니다.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
...
body:
      { id_ch: 'true',
 pass_ch: 'true',
 email_ch: 'true',
 m_tel: '010-1234-5678',
 m_id: 'GilDong',
 m_pass: 'password1',
 m_pass_ch: 'password1',
 m_name: '홍길동',
 m_date: '2000-01-01',
 tel1: '010',
 m_tel2: '1234',
 m_tel3: '5678',
 m_gender: '남',
 m_email: 'GilDong@Hong.com' },
...
  • 이런식으로 콘솔창에 출력된 것을 알수 있었습니다. 브라우저에는 변수값이 입력되지 않아 출력이 되지 않습니다.
  • 우리가 원하는 정보는 req.body에 있다는 것을 알았습니다.
  • 보낸 값을 member.ejs에 출력을 하기 위해 member.js의 11번 라인을 수정해 줍시다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
var express = require('express');
var router = express.Router();

router.get('/join', function(req, res) {
  res.render('join');
});

router.post('/members', function(req,res){
 // console.log(req);
 res.render('members',req.body);
});
module.exports = router;

  • 이제 서버를 리부트 해서 다시 해봅시다.
  • 이렇게 전송하여


  • 이런식으로 결과를 얻어 제대로 전송됬음을 확인했습니다.
  • 만약 파라미터 값들의 이름을 페이지마다, 그리고 나중의 DB와 다르게 할 경우 다시 맵핑하여 입력해야 하는 번거로움이 생기므로 일치시키는게 좋습니다.

[node 웹페이지 만들기] 2.node+express+ejs - 2

EJS 뜯어보기

  • 전에 기본 예제를 실행해 보겠습니다.

EJS 예제

  • ejs의 start는 node bin/www 로 시작합니다.


1
2
C:\web\EJS>node bin/www
 
  • ????
  • 서버가 시작된겁니다.
localhost:3000
  • 로컬서버 인 만큼 주소는 localhost:3000(127.0.01:3000)으로 접속하면 예제 페이지를 볼수 있습니다.

드디어 뜯어보기

  • 시작이 bin 폴더의 www이니까 www파일 부터 살펴보겠습니다.


1
2
3
4
5
6
7
8
9
#!/usr/bin/env node
var debug = require('debug')('EJS');
var app = require('../app');

app.set('port', process.env.PORT || 3000);

var server = app.listen(app.get('port'), function() {
  debug('Express server listening on port ' + server.address().port);
});


  • 2번 라인 : 디버깅을 위한것
  • 3번라인 : ../app을 불러오는 것입니다.
  • 5번 라인 : port번호를 3000으로 설정합니다.
  • 7번~ : 서버를 시작하는 (클라이언트를 기다리는) 명령어가 되겠습니다. 
    • 8번 라인에 console.log('server star'); 를 넣어 서버가 시작됨을 알수 있습니다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
#!/usr/bin/env node
var debug = require('debug')('EJS');
var app = require('../app');

app.set('port', process.env.PORT || 3000);

var server = app.listen(app.get('port'), function() {
 console.log("server start");
  debug('Express server listening on port ' + server.address().port);
});
  • 이렇게 한다면 서버를 구동할경우

1
2
C:\web\EJS>node bin/www
server start

  • server start를 확인 할수 있습니다.
  • 다음은 ../app 파일을 알아보겠습니다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
var express = require('express');
var path = require('path');
var favicon = require('serve-favicon');
var logger = require('morgan');
var cookieParser = require('cookie-parser');
var bodyParser = require('body-parser');

var routes = require('./routes/index');
var users = require('./routes/users');

var app = express();

// view engine setup
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'ejs');

// uncomment after placing your favicon in /public
//app.use(favicon(__dirname + '/public/favicon.ico'));
app.use(logger('dev'));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));

app.use('/', routes);
app.use('/users', users);

// catch 404 and forward to error handler
app.use(function(req, res, next) {
    var err = new Error('Not Found');
    err.status = 404;
    next(err);
});

// error handlers

// development error handler
// will print stacktrace
if (app.get('env') === 'development') {
    app.use(function(err, req, res, next) {
        res.status(err.status || 500);
        res.render('error', {
            message: err.message,
            error: err
        });
    });
}

// production error handler
// no stacktraces leaked to user
app.use(function(err, req, res, next) {
    res.status(err.status || 500);
    res.render('error', {
        message: err.message,
        error: {}
    });
});


module.exports = app;

  • 8,9라인과 25,26라인을 통하여 ejs파일 경로를 등록하고 연결하는 것을 볼 수 있습니다.
  • 29라인과 39번이후 라인을 통해 404(페이지를 찾을수 없는 경우)와 500(서버 에러)를 처리할 수있습니다.
  • 그럼 계속 따라 들어가보기 위해 /routes/폴더의 index.js파일을 따라 들어가보겠습니다.


1
2
3
4
5
6
7
8
9
var express = require('express');
var router = express.Router();

/* GET home page. */
router.get('/', function(req, res) {
  res.render('index', { title: 'Express' });
});

module.exports = router;

  • express.Router.get을 통하여 
    • '/'의 경로에 r
    • esponse(res)에 index.ejs과 title:Express로 넣어 렌더링 함을 알수 있습니다.
  • 5번줄에 get 대신에 post를 쓴다면 post 방식으로 작동합니다.
  • 그럼 마지막으로 index.ejs파일로 따라 들어가 보겠습니다. index.ejs파일의 경로는 위의 app.js에 설정하였던 views 디렉터리 아래 있습니다.


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
<!DOCTYPE html>
<html>
  <head>
    <title><%= title %></title>
    <link rel='stylesheet' href='/stylesheets/style.css' />
  </head>
  <body>
    <h1><%= title %></h1>
    <p>Welcome to <%= title %></p>
  </body>
</html>
  • ?! html과 같은 양식입니다. html을 작성하듯이 작성하고 <%=%>을 통하여 동적으로 페이지를 보여줄 수 있습니다.
  • <%=title%>을 통하여 index.js에서 넣어줬던 title을 값을 받아 동적으로 보여주게 됩니다.
  • stylesheets와 javascript 파일 등은 publice 폴더 아래에 위치하면 됩니다,