게시글

5만명이 선택한 평균 별점 4.9의 제로초 프로그래밍 강좌! 로드맵만 따라오면 됩니다! 클릭
강좌3 - NodeJS - 8년 전 등록 / 7년 전 수정

HTML 전송하기

안녕하세요! 이번 시간에는 Node.js로 text 대신에 HTML을 전송하는 방법을 알아보겠습니다! 지난 시간에는 간단한 text를 전송했는데, text로 HTML 구조를 만들어서 전송하기는 힘들겠죠? 그래서 아예 통째로 HTML 파일을 전송하는 방법이 있습니다.

일단 지난 시간 만들었던 server.js와 같은 폴더 위치에 main.html을 만듭니다. (이름은 상관 없습니다) HTML 파일의 내용물은 자바스크립트 강좌28 턴제 게임 만들기의 HTML을 쓰겠습니다.

그리고 실제 서비스에서는 여러 페이지를 사용하기 때문에 저희도 여러 페이지 구현을 위한 about.html도 만들겠습니다. 게임에 관한 정보가 나와있는 페이지입니다.

about.html

<html>
<head>
  <meta charset="utf-8" />
  <title>About</title>
</head>
<body>
  <div>제작자: ZeroCho</div>
</body>
</html>

이렇게 만든 main.html, about.html을 다음과 같이 전송해줍니다. 아 그리고 turn.js 파일도 강좌30에서 복사하여 같은 폴더에 넣어주세요.

server.js

const http = require('http');
const url = require('url');
const fs = require('fs');
http.createServer((request, response) => {
  const path = url.parse(request.url, true).pathname; // url에서 path 추출
  if (request.method === 'GET') { // GET 요청이면
    if (path === '/about') { // 주소가 /about이면
      response.writeHead(200,{'Content-Type':'text/html'}); // header 설정
      fs.readFile(__dirname + '/about.html', (err, data) => { // 파일 읽는 메소드
        if (err) {
          return console.error(err); // 에러 발생시 에러 기록하고 종료
        }
        response.end(data, 'utf-8'); // 브라우저로 전송
      });
    } else if (path === '/') { // 주소가 /이면
      response.writeHead(200,{'Content-Type':'text/html'});
      fs.readFile(__dirname + '/main.html', (err, data) => {
        if (err) {
          return console.error(err);
        }
        response.end(data, 'utf-8');
      });
    } else { // 매칭되는 주소가 없으면
      response.statusCode = 404; // 404 상태 코드
      response.end('주소가 없습니다');
    }
  }
}).listen(8080);

fsurl 모듈을 추가했습니다. fs 모듈은 파일을 읽고 쓰는 모듈입니다. 여기서는 readFile 메소드로 HTML 파일을 읽어서 읽은 데이터를 브라우저로 보내고 있네요. url 모듈은 주소를 분석하는 모듈입니다. 이 모듈을 사용해서 url에 따라 다른 HTML을 전송하는 라우팅을 구현하고 있습니다.

url.parse 메소드로 요청한 주소request.url을 분석할 수 있습니다. path 변수에 분석한 url을 담고, GET 요청(기본적으로 GET 요청입니다. 폼의 POST, GET 요청과 같은 겁니다)일 때 url에 따라 각각 다른 HTML 파일을 읽습니다.

그 전에 response.writeHead 메소드로 response.setHeader 메소드와 같이 header을 설정합니다. 파일을 다 읽은 후 response.end 메소드로 읽은 data를 전송하고 있습니다. __dirname은 현재 프로젝트의 경로를 의미합니다. __dirname + '/main.html'은 현재 프로젝트 경로의 main.html의 주소겠죠? 만약 요청 주소가 '/'도 아니고 '/about'도 아닌 경우에는 404 NOT FOUND 에러를 전송합니다. 해당하는 주소에 맞는 파일이 없을 때 발생하는 에러입니다. 몇 번 보신 적이 있을 겁니다.

cmd로 서버가 있는 곳으로 가서 node server하면 다음과 같이 브라우저 주소를 쳤을 때 경로에 맞는 HTML 페이지가 보여집니다.

undefined

undefined

이렇게 HTML을 전송해보았는데요. 코드가 너무 반복되고, 페이지 별로 HTML을 따로 만들어야하며, 이를 각각 주소와 일일히 연결해야하는 단점이 있습니다. 페이지가 수십 페이지 이상 늘어난다고 생각해보세요. 매번 GET 요청인지 확인하고, 주소를 파악하고, fs로 매칭되는 파일을 읽어서 브라우저로 전송해야 합니다. 이렇게 해서는 실제 서비스는 무리겠죠? 다음 시간에는 이 귀찮은 과정을 간단히 해결해 줄 Express 프레임워크에 대해서 알아봅시다!

조회수:
0
목록
투표로 게시글에 관해 피드백을 해주시면 게시글 수정 시 반영됩니다. 오류가 있다면 어떤 부분에 오류가 있는지도 알려주세요! 잘못된 정보가 퍼져나가지 않도록 도와주세요.
Copyright 2016- . 무단 전재 및 재배포 금지. 출처 표기 시 인용 가능.
5만명이 선택한 평균 별점 4.9의 제로초 프로그래밍 강좌! 로드맵만 따라오면 됩니다! 클릭

댓글

8개의 댓글이 있습니다.
2년 전
혹시 지금도 질문 받으시나요?
2년 전
네 받습니다
5년 전
안녕하세요, 책을보며 공부하고있습니다.
궁금한게 있어서 질문드립니다.
http.createServer((req, res) => {
if(req.method === 'GET'){
if(req.url === '/'){
fs.readFile('./practice4.3/restFront.html', (err, data) => {



http.createServer((req, res) => {
if(req.method === 'GET'){
if(req.url === '/'){
return fs.readFile('./practice4.3/restFront.html', (err, data) => {



sample 소스코드를보니깐 저렇게 return이 있는것도 있고 없는것도 있던데, return 유무에 따라 어떤 차이가 있는지 궁금합니다.
5년 전
return을 하면 그 자리에서 함수가 종료됩니다.
5년 전
url / 부분에서 main.html에서 임포트시키는 turn.js 가 404에러가 나오네요. 정상인가요?
5년 전
express 사용했을때는 app.use 파일을 이용해 정적파일을 사용할수 있는 형태로 만들어둬서 사용하였지만 지금은 그렇지 않아서 발생하는 현상인가요?
5년 전
네네 그런 부분들 직접 다 연결해주셔야 합니다. 노드교과서 보신다면 4장 서버만들기에서 정적파일(js나 css) 서빙하는 예제가 있습니다.
7년 전
안녕하세요~ 처음 node를 공부하는 학생입니다.
다름이아니라 서버를 돌리고 브라우저에서 확인하면
cmd창이나 브라우저 한글이 출력될 때면 깨져 나옵니다.
혹시 해결방안을 아시는지요?
7년 전
meta utf-8 태그를 넣었는데도 브라우저에서 깨지나요? cmd 한글 깨지는 문제는 구글에 검색하시면 됩니다.
7년 전
안녕하세요~ 꾸준히 보다가 서버 강의까지 보게 되었네요
인코딩이 제대로 안되서 검색해보니
response.writeHead 부분에도 'Content-Type' : 'text/html; charset=utf-8' 이라고 써줘야 하는 것 같습니다.
7년 전
아아 맞습니다. 아니면 head 부분에 \u003cmeta charset='utf-8'/>을 추가하셔도 됩니다.
8년 전
res 세팅은 req에 영향 못 주는 걸로 알고 있습니다. 프록시 세팅해주었어요~
8년 전
감사합니다. 미들웨어에서 컨텐트 타입 지정해서 보내고 받는 곳에서 파싱하는 방법으로 해결하였습니다.
8년 전
app.use랑 res.set({ content-Type: ... })으로 하신 건가요?
8년 전
IE8에서 쓰는 XDomainRequest는 Content-Type이 하나도 없는데, 이런 경우 어떻게 전송해야 하나요? 받는 곳에서 어떻게 파싱을 해야 할까요
8년 전
XDomainRequest는 content-type을 전송할 수 없지만 데이터는 보낼 수 있습니다. 예를 들어, 객체를 전송할 때는 JSON.stringify로 보내고, 받는 곳에서 JSON.parse로 받으면 됩니다.