Blinking My Melody

190402) REST 서버 만들기

2019. 4. 2. 16:50

 

restServer.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
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
const http = require('http');
// RESTful 서버...
const fs = require('fs');
 
const users = {}; // 등록되는 사용자 정보를 저장하는 객체
 
const srv = http.createServer((req, res) => { // function (req, res) {
    if (req.method === 'GET') {
        if (req.url === '/') {
            return fs.readFile('./restFront.html'
                    (err, data) => {
                        if (err) throw err;
 
                        res.end(data);
                    }
            );
        } else if (req.url === '/about') {
            return fs.readFile('./about.html'
                    (err, data) => {
                        if (err) throw err;
 
                        res.end(data);
                    }
            );
        } else if (req.url === '/users') {
            return res.end(JSON.stringify(users));
        } 
 
        return fs.readFile(`.${req.url}`, (err, data) => { // http://localhost:8085/ 뒷 부분에 about, users, restFront.html 셋 중 하나 반환
            if (err) {
                res.writeHead(404'파일 없음...');
                return res.end('파일 없음...');
            } 
            
            return res.end(data);
        }); //이 부분을 함수처리해서 `.${req.url}을 변수 처리 한다
    } else if (req.method === 'POST') {
        if (req.url === '/users') {
            let body = '';
            req.on('data', (fromClientData) => {
                body += fromClientData;
            });
 
            return req.on('end', () => {
                console.log('POST 본문 정보 : ', body); //'POST 본문 정보 : ' + body => '+'도 가능
                const { name } = JSON.parse(body);
                const id = +new Date();
                user[id] = name;
                res.writeHead(201);
                res.end('등록 성공');
            });
        }
    } else if (req.method === 'PUT') {
        if (req.url.startsWith('/users/')) {
            const key = req.url.split('/')[2];
            // http://localhost:8085/users/15049523에서 /users/15049523이 req.url에 저장
            // 그 상태에서 split을 하면 '/'을 기준으로 나눠서 배열이 됨 ['', users, 15049523]
            // 그리고 뒤에 [2]는 배열에서 2번째(15049523)을 key에 저장하겠다 라는 의미
            let body = '';
            req.on('data', (fromClientData) => {
                body += fromClientData;
            });
 
            return req.on('end', () => {
                console.log('PUT 본문 정보 : ', body);
                users[key] = JSON.parse(body).name;
                // body ==> { name:'사용자 수정 값' }
                return res.end(JSON.stringify(users));
            });
        }
    } else if (req.method === 'DELETE') {
        if (req.url.startsWith('/users/')) {
            const key = req.url.split('/')[2];
            delete users[key];
            return res.end(JSON.stringify(users));
         }
    }
 
    res.writeHead(404'파일 없음');
    return res.end('파일 없음');
});
 
srv.listen(8085, () => {
    console.log("서버 대기중 (8085 포트), http://localhost.8085/");
}); // 여기서 callback 함수는 대기가 성공됐을 때 실행
http://colorscripter.com/info#e" target="_blank" style="color:#e5e5e5; text-decoration:none">Colored by Color Scripter

 

 

restFront.css

1
2
3
4
{
    color: violet;
    text-decoration: none;
}

 

 

restFront.html

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>RESTFul 서버 만들기</title>
    <link rel="stylesheet" href="./restFront.css" />
</head>
<body>
    <nav>
        <a href="/">Home</a>
        <a href="/about">About</a>
    </nav>
    <div>
        <form id="form">
            <input type="text" id="username">
            <button type="submit">등록</button>
        </form>
    </div>
    <div id="list"></div>
    <script src="./restFront.js"></script>
</body>
</html>
http://colorscripter.com/info#e" target="_blank" style="color:#e5e5e5; text-decoration:none">Colored by Color Scripter

 

 

about.html

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>RESTful 서버에 대하여</title>
    <link rel="stylesheet" href="./restFront.css" />
</head>
<body>
    <nav>
        <a href="/">Home</a>
        <a href="/about">About</a>
    </nav>
    <div>
        <h2>소개 페이지</h2>
        <p>사용자 이름을 등록하세요</p>
    </div>
    
</body>
</html>
http://colorscripter.com/info#e" target="_blank" style="color:#e5e5e5; text-decoration:none">Colored by Color Scripter

 

 

restFront.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
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
function getUser() {
    var xhr = new XMLHttpRequest();
    xhr.onload = function() {
        if (xhr.status === 200) {
            var users = JSON.parse(xhr.responseText);
            var list = document.getElementById('list');
            list.innerHTML = '';
            Object.keys(users).map(function (key) {
                var userDiv = document.createElement('div');
                var span = document.createElement('span');
                span.textContent = users[key];
                var edit = document.createElement('button');
                edit.textContent = '수정';
                edit.addEventListener('click'function() { // 수정 버튼 클릭
                    var name = prompt('바꿀 이름을 입력하세요');
                    if (!name) {
                        return alert('이름을 반드시 입력하셔야 합니다');
                    }
                    var xhr = new XMLHttpRequest();
                    xhr.onload = function() {
                        if (xhr.status === 200) {
                            console.log(xhr.responseText);
                            getUser();
                        } else {
                            console.error(xhr.responseText);
                        }
                    };
                    xhr.open('PUT''/users/' + key);
                    xhr.setRequestHeader('Content-Type''application/json');
                    xhr.send(JSON.stringify(namename }));
                });
                var remove = document.createElement('button');
                remove.textContent = '삭제';
                remove.addEventListener('click'function () { // 삭제 버튼 클릭
                    var xhr = new XMLHttpRequest();
                    xhr.onload = function() {
                        if (xhr.status === 200) {
                            console.log(xhr.responseText);
                            getUser();
                        } else {
                            console.error(xhr.responseText);
                        }
                    };
                    xhr.open('DELETE''/users/' + key);
                    xhr.send();
                });
                userDiv.appendChild(span);
                userDiv.appendChild(edit);
                userDiv.appendChild(remove);
                list.appendChild(userDiv);
            });
        } else {
            console.error(xhr.responseText);
        }
    };
    xhr.open('GET''/users');
    xhr.send();
}
window.onload = getUser; // 로딩 시 getUser 호출
// 폼 제출
document.getElementById('form').addEventListener('submit'function(e) {
    e.preventDefault();
    var name = e.target.username.value;
    if (!name) {
        return alert('이름을 입력하세요');
    }
    var xhr = new XMLHttpRequest();
    xhr.onload = function() {
        if (xhr.status === 201) {
            console.log(xhr.responseText);
        }
    };
    xhr.open('POST''/users');
    xhr.setRequestHeader('Content-Type''application/json');
    xhr.send(JSON.stringify(namename }));
});
http://colorscripter.com/info#e" target="_blank" style="color:#e5e5e5; text-decoration:none">Colored by Color Scripter

 

 


+ restFront.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
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
/* Promise 처리 */
function getUsers() { // 로딩 시 사용자 가져오는 함수
    fetch('/users', { method : 'GET' })
    .then((response) => {
        if (resizeBy.status == '200') {
            return response.json(); // JSON 형식으로 리턴하는 Promise 객체
        }
    })
    .then((resJson) => {
        showUsers(resJson, document.querySelector('#list'));
    })
    .catch((error) => {
        console.error('fetch 호출에서 에러 발생 : ' + error.message);
    })
};
 
function showUsers(users, location) {
    location.innerHTML = '';
    Object.keys(users).map((key) => {
        var userDiv = document.createElement('div');
        var span = document.createElement('span');
        span.textContent = users[key];
 
        var edit = createModifyBtn(key);
        var remove = createDelBtn(key);
 
        userDiv.appendChild(span);
        userDiv.appendChild(edit);
        userDiv.appendChild(remove);
        userDiv.appendChild(userDiv);
    });
}
 
function createModifyBtn(key) {
    var edit = document.createElement('button');
    edit.textContent = '수정';
    edit.addEventListener('click', () => { //수정 버튼 클릭
        var name = prompt('바꿀 이름을 입력하세요');
        if (!name) {
            return alert('이름을 반드시 입력하셔야 합니다');
        }
        fetch('/users/' + key, {
            headers: {
                'Accept' : 'application/json',
                'Content-Type' : 'application/json'
            },
            method : "PUT",
            body : JSON.stringify({ name : name })
        }).then((res) => {
            if(res.status == '200') {
                return res.json();
            }
        }).then((resJson) => {
            console.log(resJson);
            showUsers(resJson, document.querySelector('#list'));
        }).catch((error) => {
            console.error('fetch 호출에서 에러 발생 : ' + error.message);
        });
    });
    return edit;
}
 
function createDelBtn(key) {
    var remove = document.createElement('button');
    remove.textContent = '삭제';
    remove.addEventListener('click', () => { // 삭제 버튼 클릭
        fetch('/users/' + key, {
            headers : {
                'Accept' : 'application/json',
                'Content-Type' : 'application/json'
            },
            method : "DELETE"
        }).then((res) => {
            if(res.status == '200') {
                return res.json();
            }
        }).then((resJson) => {
            showUsers(resJson, document.querySelector('#list'));
        }).catch((error) => {
            console.error('fetch 호출에서 에러 발생 : ' + error.message);
        });
    });
    return remove;
}
 
window.onload = getUsers; //로딩시 getUser 호출
// 폼 제출
 
document.querySelector('#form').addEventListener('submit', (e) => {
    e.preventDefault();
    var name = e.target.username.value;
    if (!name) {
        return alert('이름을 입력하세요');
    }
    fetch('/users', {
        headers : {
            'Accept' : 'application/json',
            'Content-Type' : 'application/json'
        },
        method : "POST",
        body : JSON.stringify({ name : name })
    }).then((res) => {
        if(res.status == '201') {
            return res.json();
        }
    }).then((result) => {
        showUsers(result, document.querySelector('#list'));
    }).catch((error) => {
        console.error('fetch 호출에서 에러 발생 : ' + error.message);
    });
});
http://colorscripter.com/info#e" target="_blank" style="color:#e5e5e5; text-decoration:none">Colored by Color Scripter