app.글_생성/수정/삭제

BABY CAT·2022년 9월 21일
0

HTML, CSS, JavaScript

목록 보기
7/23

폴더 (파일)

view              -  (index.js)
(26.app삭제.js)	    (template.js)

파일

26.app삭제.js (main)

const http = require('http');
const url = require('url');
const fs = require('fs');
const qs = require('querystring');
const view = require('./view/index');
const template = require('./view/template');

http.createServer((req, res) => {
    let pathname = url.parse(req.url).pathname;
    let query = url.parse(req.url, true).query;
    switch(pathname) {
    case '/':
        if (query.id === undefined) {     // 초기 화면
            fs.readdir('data', (err, files) => {
                const title = '웹 기술';
                const list = template.listGen(files);
                const content = template.HOME_CONTENTS.replace(/\n/g,'<br>');
                const control = template.buttonGen();
                const html = view.index(title, list, content, control);
                res.end(html);
            });
        } else {                        // 개별 아이템에 대한 화면
            fs.readdir('data', (err, files) => {
                const title = query.id;
                const list = template.listGen(files);
                const filename = `data/${query.id}.txt`;
                fs.readFile(filename, 'utf8', (err, data) => {
                    let content = data.replace(/\n/g,'<br>');
                    const control = template.buttonGen(title);
                    const html = view.index(title, list, content, control);
                    res.end(html);
                });
            });
        }
        break;
    case '/create':
        if (req.method === 'GET') {
            fs.readdir('data', (err, files) => {
                const title = '글 생성';
                const list = template.listGen(files);
                const content = template.createForm();
                const html = view.index(title, list, content, ' ');
                res.end(html);
            });
        } else {
            let body = '';
            req.on('data', data => {
                body += data;
            });
            req.on('end', () => {
                const param = qs.parse(body);
                if (param.title.trim().length == 0) {       // 제목이 white space인 경우, 생성하지 않음
                    res.writeHead(302, {'Location': '/'});
                    res.end();
                } else {
                    const fname = `data/${param.title}.txt`;
                    fs.writeFile(fname, param.content, err => {
                        res.writeHead(302, {'Location': `/?id=${param.title}`});
                        res.end();
                    });
                }
            });
        }
        break;
    case '/update':
        if (req.method === 'GET') {
            fs.readdir('data', (err, files) => {
                const title = `${query.id} 수정`;
                const list = template.listGen(files);
                const filename = `data/${query.id}.txt`;
                fs.readFile(filename, 'utf8', (err, data) => {
                    const content = template.updateForm(query.id, data)
                    const html = view.index(title, list, content, ' ');
                    res.end(html);
                });
            });
        } else {
            let body = '';
            req.on('data', data => {
                body += data;
            });
            req.on('end', () => {
                const param = qs.parse(body);
                if (param.title.trim().length == 0) {           // 제목이 white space인 경우, 수정하지 않음
                    res.writeHead(302, {'Location': '/'});
                    res.end();
                } else {
                    const fname = `data/${param.title}.txt`;
                    fs.writeFile(fname, param.content, err => {
                        if (param.original != param.title) {    // 제목이 변경된 경우
                            fs.unlink(`data/${param.original}.txt`, err => {
                                res.writeHead(302, {'Location': `/?id=${param.title}`});
                                res.end();
                            });
                        } else {
                            res.writeHead(302, {'Location': `/?id=${param.title}`});
                            res.end();
                        }
                    })
                }
            });
        }
        break;
    case '/delete':
        fs.readdir('data', (err, files) => {
            const title = `${query.id} 삭제`;
            const list = template.listGen(files);
            const content = template.deleteForm(query.id);
            const html = view.index(title, list, content, ' ');
            res.end(html);
        });
        break;
    case '/deleteConfirm':
        const fname = `data/${query.id}.txt`;
        fs.unlink(fname, err => {
            res.writeHead(302, {'Location': `/`});
            res.end();
        });
        break;
    default:
        res.writeHead(404, {'Content-Type': 'text/html'});
        res.end();
    }
}).listen(3000, () => {
    console.log('Server running at http://localhost:3000');
});

index.js

exports.index = function(title, list, content, control) {
   return `
<!DOCTYPE html>
<html lang="ko">
<head>
   <meta charset="UTF-8">
   <meta http-equiv="X-UA-Compatible" content="IE=edge">
   <meta name="viewport" content="width=device-width, initial-scale=1.0">
   <title>${title}</title>     <!-- 23.app조회.js 에서 변경됨 -->
</head>
<body style="margin: 50px;">
   <h1><a href="/">웹 기술</a></h1>
   <ul>
       ${list}                 <!-- 22.app리스트.js 에서 변경됨 -->
   </ul>
   <hr>
   <p>
       ${content}              <!-- 23.app조회.js 에서 변경됨 -->
   </p>
   <hr>
   ${control}                  <!-- 24.app생성.js 에서 추가됨 -->
</body>
</html>
   `;
}

template.js

module.exports = {
	HOME_CONTENTS:
		 `웹 개발(web development)은 인터넷(월드 와이드 웹)이나 인트라넷(사설망)을 위한 웹사이트를 개발하는 일을 가리킨다. 
		 웹 개발은 가장 단순한 단일 정적 문서의 플레인 텍스트에서부터 가장 복잡한 웹 기반 인터넷 애플리케이션, 전자 비즈니스,  소셜 네트워크 서비스에 이르기까지 개발 범위가 다양하다. 
		 일반적으로 웹 개발이라 부를 때는 웹 프로그래밍뿐만 아니라 더 포괄적인 작업인 웹 디자인, 웹 콘텐츠 개발, 클라이언트 사이드/서버 사이드 스크립트 작업, 웹 서버 및 네트워크 보안 구성, 전자 상업 개발을 아우른다.
		 `,
	listGen:    function(files) {
		 let list = '';
		 for (let file of files) {
			  const title = file.substring(0, file.length-4);     // .txt를 제외한 나머지
			  list += `<li><h3><a href="/?id=${title}">${title}</a></h3></li>`;
		 }
		 return list;
	},
	buttonGen:  function(title) {
		 if (title === undefined) {      // 홈 화면, 생성만 가능
			  return `
					<button onclick="location.href='/create'">생성</button>
					<button disabled="disabled">수정</button>
					<button disabled="disabled">삭제</button>
			  `;
		 } else {                        // 조회 화면, 생성/수정/삭제 가능
			  return `
					<button onclick="location.href='/create'">생성</button>
					<button onclick="location.href='/update?id=${title}'">수정</button>
					<button onclick="location.href='/delete?id=${title}'">삭제</button>
			  `;
		 }
	},
	createForm: function() {
		 return `
			  <form action="/create" method="post">
					<table>
						 <tr>
							  <td>제목</td>
							  <td><input type="text" name="title"></td>
						 </tr>
						 <tr>
							  <td>내용</td>
							  <td><textarea name="content" cols="60" rows="5"></textarea></td>
						 </tr>
						 <tr>
							  <td colspan="2" style="text-align: center;"><input type="submit" value="생성"></td>
						 </tr>
					</table>
			  </form>        
		 `;
	},
	updateForm: function(title, content) {
		 return `
			  <form action="/update" method="post">
					<input type="hidden" name="original" value="${title}">
					<table>
						 <tr>
							  <td>제목</td>
							  <td><input type="text" name="title" value="${title}"></td>
						 </tr>
						 <tr>
							  <td>내용</td>
							  <td><textarea name="content" cols="60" rows="5">${content}</textarea></td>
						 </tr>
						 <tr>
							  <td colspan="2" style="text-align: center;"><input type="submit" value="수정"></td>
						 </tr>
					</table>
			  </form>        
		 `;
	},
	deleteForm: function(title) {
		 return `
			  ${title} 글을 삭제하시겠습니까?<br><br>
			  <button onclick="location.href='/deleteConfirm?id=${title}'">삭제</button>
			  <button onclick="location.href='/?id=${title}'">취소</button>
		 `;
	}
}

0개의 댓글