본문 바로가기
node.js

라우팅(routing)

by 루에 2015. 12. 4.
반응형

http 요청이 다른 코드를 가리키는 것을 라우팅이라 한다.


그것을 위해서는 먼저 http요청의 url과 get/post 부분을 뽑아내야 한다.


이것을 위해 node에서는 url 모듈을 지원한다. 또한 querystring은 query string을 request 파라미터로 파싱하는데 사용한다.


이런 요청이 있다고 하자.



http://localhost:8888/start?foo=bar&hello=world

그리고 요청이 들어왔을 때 콘솔에 출력할 코드를 작성한다.

server.js

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
var http = require("http");
var url = require("url");
var querystring = require("querystring");
 
function start(){
    http.createServer(function(request, response){
        console.log("Request received.");
 
        var u = request.url;
 
        var query = url.parse(u).query;
        var pathname = url.parse(u).pathname;
        var foo = querystring.parse(u)["foo"];
        var hello = querystring.parse(u)["hello"];
 
        console.log("query : " + query + "\n" +
                    "pathname : " + pathname + "\n" +
                    "foo : " + foo + "\n" +
                    "hello : " + hello);
 
 
        response.writeHead(200, {"Content-Type""text/plain"});
        response.write("Hello World");
        response.end();
    }).listen(8888);
 
    console.log("Server has started");
 
    end();    
}
 
function end(){
    console.log("call end");
}
 
exports.start = start;
cs


그리고 위의 주소로 요청하면,

C:\Users\Administrator\data_node>node index.js

Server has started

call end

Request received.

query : foo=bar&hello=world

pathname : /start

foo : undefined

hello : world


왜인지 foo의 값이 undefined가 된다... 왜일까?


start? 뒤에 &를 추가한뒤 해보았다.

C:\Users\Administrator\data_node>node index.js

Server has started

call end

Request received.

query : &foo=bar&hello=world

pathname : /start

foo : bar

hello : world


잘 출력된다. 즉, querystring의 문법에 조금 문제가 있다는 것을 알 수 있다. 이유는 아직 모르겠다. 구글링을 해도 나오지 않는다...



이제 진짜 라우터를 작성해본다.

route.js

1
2
3
4
5
function route(pathname){
    console.log("About to route a request for " + pathname);
}
 
exports.route = route;
cs

새로운 파일을 만들고 모듈화 한다.


server.js를 확장한다.

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
var http = require("http");
var url = require("url");
var querystring = require("querystring");
 
function start(route){
    http.createServer(function(request, response){
        console.log("Request received.");
 
        var pathname = request.url.pathname;
 
        route(pathname);
 
        response.writeHead(200, {"Content-Type""text/plain"});
        response.write("Hello World");
        response.end();
    }).listen(8888);
 
    console.log("Server has started");
 
    end();    
}
 
function end(){
    console.log("call end");
}
 
exports.start = start;
cs


index.js를 확장하고 주입-inject- 한다.

1
2
3
4
var start = require("./server");
var router = require("./route");
 
start.start(router.route);
cs



그리고 요청을 보내면,

1
2
3
4
5
C:\Users\Administrator\data_node>node index.js
Server has started
call end
Request received.
About to route a request for /start
cs


현재 router.js가 하는 일은 콘솔에 출력하는 것 밖에 없지만, 이 것을 기초로 라우팅을 한다.



실제 라우팅을 하기 위해, requestHandler를 작성한다. 이를 위해 requestHandlers.js를 생성하고 파일을 작성한다.


requestHandlers.js

1
2
3
4
5
6
7
8
9
10
function start() {
    console.log("Request handler 'start' was called");
}
 
function upload(){
    console.log("Request handler 'upload' was called");
}
 
exports.start = start;
exports.upload = upload;
cs


index.js

1
2
3
4
5
6
7
8
9
10
11
var server = require("./server");
var router = require("./route");
var requestHandlers = require("./requestHandlers");
 
var handle = {}
handle["/"= requestHandlers.start;
handle["/start"= requestHandlers.start;
handle["/upload"= requestHandlers.upload;
 
console.log(handle);
server.start(router.route, handle);
cs


server.js

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
var http = require("http");
var url = require("url");
var querystring = require("querystring");
 
function start(route, handle){
    http.createServer(function(request, response){
        console.log("Request received.");
 
        var pathname = url.parse(request.url).pathname;
 
        route(handle, pathname);
 
        response.writeHead(200, {"Content-Type""text/plain"});
        response.write("Hello World");
        response.end();
    }).listen(8888);
 
    console.log("Server has started");
}
 
exports.start = start;
cs


route.js

1
2
3
4
5
6
7
8
9
10
11
function route(handle, pathname){
    console.log("About to route a request for " + pathname);
    if(typeof handle[pathname] === 'function'){
        handle[pathname]();
    }
    else {
    console.log("No request handler found for" + pathname);        
    }
}
 
exports.route = route;
cs


index.js에 명시한 handle을 통해 요청 주소값에 따라 다른 분기를 타도록 설정한다. 그리고 route에서 handle[pathname](); 구문으로 해당 함수를 실행한다.


실행결과

1
2
3
4
5
6
C:\Users\Administrator\data_node>node index.js
[Function: start]
Server has started
Request received.
About to route a request for /
Request handler 'start' was called
cs


반응형

댓글