
npm install -g yarn 을 해준다 << 여기서 글로벌로 선언 안했을 가능성 高
yarn init -y 를 친다
yarn add express 를 친다
위 순서대로 했는데도 package-lock.json이 생긴다면 그냥 조용히 삭제해주자.
아마 npm install yarn 때 생기는 경우가 많을 것 (-g 해줘야 안 생긴다)
지금은 기억하겠지만 기억하지 못할 나중을 위해 적자면, lock 파일이 두개 있어선 안된다. yarn.lock을 쓰든 package-lock.json을 쓰든 한개만 남겨야 한다. 이 둘은 git에 커밋되어야 한다.
현대 웹의 근간. TCP랑은 다르게 7층인 애플리케이션 계층에서 사용된다. 웹 소켓 또한 HTML5에서 등장한 TCP 기반 통신이라 7층에서 돌아간다.
하지만, 그냥 TCP 통신은? 4층인 전송 계층의 프로토콜. 그러니 헤더가 무겁든 어쩌든 TCP를 이용한 방법이 당연히 더 빠르다.
유데미 강의가 require 문을 쓰는 형태라 당황했다. 그러고보니 구매해놓은 다른 Node 강의도 ES5 이하의 CJS 문법을 쓴다.

Error: listen EACCES: permission denied 0.0.0.0:3000
아니 이게 뭐야. 무슨 permission이 왜 denied야?
하지만 참고 블로그 덕분에 무사히 해결했다. 네트워크 드라이브를 멈췄다가 다시 실행해주면 ok
net stop winnat 을 입력한다net start winnat 을 입력한다이 과정으로 해결.
역시나 고마운 스택 오버플로우 웨건이 해결해 주었다.
// Source - https://stackoverflow.com/a/41540536
// Posted by BlackMamba
// Retrieved 2026-01-12, License - CC BY-SA 3.0
var http = require('http');
var server = http.createServer(function (req, res) {
res.writeHead(200, {'Content-Type': 'text/plain'});
res.end('Hello World\n');
}).listen(8080);
console.log('Server listening:', `http://${server.address().address}:${server.address().port}`);
이런식으로 쓰라고 하기에 똑같이 써보니 잘 되었다.

이 명령어는 git bash에서 사용해야 하니 터미널 추가 시 git bash를 선택해주자. -v는 요청과 응답 송수신의 상세를 볼 수 있는 명령어이다.
curl http://localhost:3000 -v

이렇게 무사히 송수신 되었음을 볼 수 있다. 저기서 Accept:*/* 아랫줄이 비어있는 이유는 요청 시에 아무 내용도 넣지 않았기 때문이라고.
아울러 잊고있던 localhost 주소가 127.0.0.1임을 상기했다 (...)
server.listen(PORT, () => {
console.log(`Server is listening on port ${PORT}`);
});
이렇게 써있는 것을 보고 서버는 3000번 포트에서 HTTP 트래픽 수신을 대기한다 고 한다. 서버 자체는 HTTP 트래픽이 언제 어디서 발생하는지 신경쓰지 않으며, 요청이 오면 정의한 콜백함수를 실행할 뿐이다.
그래서 요청의 경로에 따라 다른 응답을 보내주려면 개발자가 직접 구현해야 한다. 이것이 라우팅이고, 이렇게 정의된 개별 로직의 단위가 라우터.
웹 개발에서 이는 상당히 중요하다. 여러 종류의 타입이 있는데 일부를 보자면 다음과 같다.
text/html
text/plain
text/css
application/javascript
image/jpeg
image/png
application/pdf
application/json
웹서버에서는 이런 컨텐츠 타입을 분석하여 MIME 타입을 설정하고, HTTP 응답헤더의 컨텐츠 타입 필드에 포함하여 클라이언트에게 전송한다.
const serveStatic = (rootDir, req, res) => {
const filePath = path.join(rootDir, req.url);
fs.readFile(filePath, (err, data) => {
if (err) {
if (err.code === "ENOENT") {
res.writeHead(404, { "content-type": "text/html" });
res.end("<h1> 404 Not Found! </h1>");
} else {
res.writeHead(500, { "content-type": "text/html" });
res.end("<h1> 500 Internal Server Error! </h1>");
}
} else {
const extname = path.extname(filePath);
const content = contentType.getContentType(extname);
res.writeHead(200, { "content-type": content });
res.end(data);
}
});
};
우선 이런 식으로 최소한의 뼈대만 구현.


자꾸 이렇게 터지면서 홈페이지가 나오지 않는 것이었다. 메시지는 대강 클라이언트에 이미 응답을 보내고 나서 다시 헤더를 쓸 수 없다는 것 같았다.

문제의 부분은 여기였다. 이 가장 바깥 res.end()를 지워주니 정상적으로 출력되었다.
부트캠프 때 touch로 새 파일을 만드시던 강사님의 모습이 떠올라 우클릭 하지 않고 CLI로 새 파일을 만들어보고 싶었는데, 파워쉘은 물론이고 깃배쉬에서도 touch가 먹히지 않는 것이다.
알고보니 touch는 Linux 명령어라고. Powershell에서는 ni .gitignore 하니 만들어졌다.