
Node.js + MongoDB를 공부해보자! 위대하신 코딩애플(codingapple.com)님과 함께:)
const MongoClient = require('mongodb').MongoClient;
<script>
var db;
MongoClient.connect('MongoDB에서 가져온 URL',
function(err, client) {
if (err) {return console.log(err)}
// db라는 변수에 TodoApp이라는 데이터베이스를 연결.
db = client.db('TodoApp')
// 연결 후에 8080으로 lisetn.
app.listen(8080, function() {
console.log('listening on 8080')
});
})
</script>
<script>
db.collection('post').insertOne({이름 : "ryu.jh"}, function(err,result) {
if (err) {return console.log(err)}
...
저장되면 실행될 코드
})
</script>
아까 지정했던 데이터베이스가 연결된 db의 collection 중에서 post라는 것을 고르고, 거기에 {이름 : "ryu.jh"}를 insertOne한다는 뜻이다.
되도록 에러가 일어났을 때 로그를 확인할 수 있도록 처리해두는 것이 좋다
또, db.collection('콜렉션 선택').사용할함수() 이런 패턴이 자주 나온다!
이제 HTML에서 사용할 수 있는 대표적인 문법 2가지는
1. <%= 서버에서 가져온 데이터 %>
2. <% 자바스크립트 문법 사용 (if, for 등등) %>
끝이다!
데이터는 어떻게 가져오냐구요?
<script>
app.get('/list', function(req,res) {
db.collection('post').find().toArray(function(err, result){
console.log('post의 모든 데이터를 가져온 결과 입니다 : ', result);
res.render('list.ejs' , { posts : result})
});
})
</script>
나중에 다루기(삭제, 수정 등) 쉬우니까!
다른 SQL 친구들처럼 Auto-Increment 기능이 있으면 좋으겠지만... mongodb에는 그런게 없다하니 직접 만들어야한다.
그러면 게시물을 만들때 (/add라는 api로 post요청을 할때), 자동증가하는 id가 달리게 만들어보자!
<script>
app.post('/add', function(req, res) {
//db의 collection중에서 counter선택. 게시물갯수의 값을 불러와서 "총게시물갯수"라는 변수에 저장
db.collection('counter').findOne({name : "게시물갯수"}, function(err, result){
if (err) {return console.log(err)}
console.log('터미널에 표시 - 현재 총 게시물 갯수 :', result.totalPost);
var 총게시물갯수 = result.totalPost;
//db의 collection중에서 post 선택. id가 총게시물갯수+1인 데이터를 insertOne.
db.collection('post').insertOne({_id : 총게시물갯수 +1, 제목 : req.body.title, 날짜 : req.body.date}, function(err, result){
console.log('터미널에 표시 - DB 저장완료');
res.send('페이지에 표시 - DB 저장완료');
//counter선택. name이 "게시물갯수"인 데이터의 totalPost를 1만큼 increment해서 updateOne.
db.collection('counter').updateOne({name : "게시물갯수"},{ $inc :{totalPost : 1}},function(err, result){
if(err) {return console.log(err)}
})
});
})
})
</script>
정신건강을 위해 jQuery와 함께 이용하는 Ajax이다!
EJS 파일에는 AJAX로 이렇게 기능을 구현하고
<script>
// btn-delete라는 class를 가진 요소를 클릭하면
$('.btn-delete').click(function(e) {
$.ajax({
//method는 DELETE, api는 /delete, 전달할 데이터는 글번호
method : 'DELETE',
url : '/delete',
// 현재 클릭된 (e.target)의 data-id
data : { _id : e.target.dataset.id}
}).done( (result)=>{
// $(this)는 지금 누른거
// 지금누른거의 부모요소 중에서 li를 찾아 fadeOut()
$(this).parent('li').fadeOut();
}).fail(function(XMLHttpRequest(몰라도됨), 에러코드, 에러메세지){
// 실패했을때 실행될 코드
});
})
</script>
JS 서버 파일에는 이렇게 진행하면된다!
<script>
// /delete라는 api 요청이 들어오면
app.delete('/delete', function(req, res) {
// post라는 콜렉션에서 _id가 request의 body의 _id와 동일한 것을 하나 찾아서 삭제한다.
db.collection('post').deleteOne({_id : parseInt(req.body._id)}, function(err, result) {
if (err) {
// 응답코드 400, 실패
res.status(400);
return console.log(err)
}
console.log('삭제완료');
// 응답코드 200, 일반적으로 성공
res.status(200).send({ message : '성공했습니다' });
})
})
</script>
특이한 점은, deleteOne안에 있는 쿼리문의 parseInt()인데, 데이터가 넘어오면서 자동적으로 String 형태가 되어있기 때문에, typeCasting을 통해서 데이터베이스에 있는 Int타입과 동일하게 해주어야된다.
또한 고객 요청에 응답하는 방법은 이런 것들이 있다! (json빼고 다 썼던 거)
<script>
app.get('/api', function(req, res){
res.send('<p>some html</p>') // 간단한 문자 or html
res.status(404).send('Sorry, we cannot find that!') // 응답코드
res.sendFile('/uploads/logo.png') // staticFile 전송
res.render('list.ejs', { ejs에 보낼 데이터 }) // EJS 등의 템플릿 페이지
res.json(제이슨데이터) // json 데이터 전송
});
</script>
<script>
//url의 파라미터. /detail/아무거나 라면 실행된다.
app.get('/detail/:id', function (req, res) {
// _id가 request의 parameter들 중 id와 같은 데이터를 찾아와서 그 결과를 detail페이지에 render
// 다만 아까처럼 type이 string이 되었기에, parseInt를 통해서 바꿔 찾아줘야한다.
db.collection('post').findOne({ _id: parseInt(req.params.id) }, function(err, result) {
if (err) { return console.log('findOne Error', err) }
res.render('detail.ejs', {foundData : result})
})
});
</script>