nextculture.github.io

 

 

서버를 어디서 어떻게 구동할 것인가... 이게 관건이었습니다.

토이프로젝트나 간단한 서비스를 위한 서버 구동을 위해 AWS나 Google Could를 사용하자니 돈벌이도 없는데 좀 그렇더군요. ㅠ.,ㅜ;

 

아래 블로그를 보다가 Freehosting 서비스로 무료 플랜도 괜찮아 보여 진행하려 하다가,...

 

토이프로젝트에 시용하기 좋은 무료 웹호스팅 및 서비스

들어가며 간단하게 도메인 1개, API 서버, Database, Github action CI/CD 구성, SSL, DNS, 통계만 하면 되는 작은 토이 프로젝트를 만들일이 생겼다. 일단 웹페이지는 추후에 SEO도 붙일까 해서 nextjs로 만들었

uznam8x.tistory.com

 

결국 여기저기를 보던와중  Synology NAS 로 설정하는 걸 보았고.. 나도 있는데!?

 DS918+  Docker가 지원되는 모델!!!! 와우.. 그래서 밤샘하여 설정 테스트를 완료!! ㅎㅎ 기쁘네요.

 

시놀로지 Docker로 Nodejs 웹서버 설치하고 띄우기는 아래 블로그를 보고 차근히 따라 하면 됩니다.

 

 

시놀로지 Docker로 Nodejs 웹서버 설치하고 띄우기

도커에서 Nodejs웹서버를 설치하고 띄우는 일은 간단하면서도 매우 유용한 작업입니다. 시놀로지 도커(Docker)은 주로 GUI로 설치를 진행하게되어 있어서 편리하기는 하나 아직 참고할 만한 자료들

ux.stories.pe.kr

시놀로지 Docker로 Nodejs 웹서버 설치하고 띄우기.mhtml
4.09MB

 

위의 글대로 하면 nodejs로 서버 구동은 잘 되는데..

cmd나 bash 명령 처리 과정의 복잡성, 그리고 nodemon을 사용할 수 없다는 문제점이 있어서 밤샘 ㅠ.,ㅜ;

 

혹시 nodemon 되는 것을 누가 만들었을까 싶어 레지스트리를 봤더니 역시나 nodemon이 있어서 깔아보기도 했지만 오래되고 불안정하고 업데이트 안되고 있어서 삭제..

 

 

여튼 최종적으로 실제 서비스를 위한 Nodejs Docker와 개발을 위한 Nodejs Test Docker를 만들어서 Test 서버에서는 nodemon으로 구동할 수 있도록 환경구축 완료!!!!!

 

 

최종 모습 (node8000, nodemon9000)

 

 

 

Synology.Docker 가장 골치아팠던 컨테이너  실행 명령 

아니.. 왜?? Why?? 컨테이너로 만들어진 이후에는 실행 명령을 수정할 수 없습니다!!!! 그래서 초반에 경로나 파일 내용이 잘못되거나 하면 Docker의 Nodejs가 실행자체가 안되기 때문에 어떠한 조작도 할수가 없습니다.

 

수십번을 컨테이너 지우고 만들기를 반복.. ㅋㅎ..

일단 좀더 쉽게 설정하도록 준비하여 처리하겠습니다.

 

이미 생성되어 있는 Nodejs 컨테이너 하나를 선택하고 "설정 - 내보내기"

 

"컨테이너 콘텐츠 및 설정 내보내기"는 Nodejs Docker를 전체 내보내기하여 txz 파일로 만들어줍니다. 나중에 실서버 백업을 한다거나 할 때 사용할 수 있겠네요.

한번 전체 내보내기 해보았는데 시간도 오래걸리고 용량도 꽤 큽니다. 200MB가 넘네요. 실제로 사용할 일은 적을 것 같고, 실서버에서라도 NAS의 폴더를 /home/node/app 으로 마운팅하여 사용하기 때문에 /home/node/app 폴더 내에서만 자료를 유지한다면 NAS에 알아서 보관이 되니 전체를 백업할 일이 없는 것이지요.

 

위의 설정으로 [내보내기]를 완료하면, /docker 폴더 안에 nodejsApp.syno.json과 같은 파일이 만들어져 있을겁니다.

 

 

 

폴더 구성 (node8000, nodemon9000)

일단 저는 실서버 구동을 위해 node8000 Nodejs 서버와 테스트 개발을 위한 nodemon9000 Nodejs 서버를 돌릴 예정입니다. 따라서 nodejsApp.syno.json 파일을  node8000.syno.json 으로 이름 변경하고,  nodemon9000.syno.json 으로 복사하여 한 개 더 만들어줍니다.

 

Visual Studio Code로 /docker를 열어서 node8000.syno.json을 열고 다음과 같이 수정합니다.

 

 node8000.syno.json 
- 수정이 필요한 부분은 "cmd"와 "port_bindings", "volume_bindings'입니다.
{
   "cap_add" : [],
   "cap_drop" : [],
   "cmd" : "node /home/node/app/index.js",
   "cpu_priority" : 50,
   "devices" : null,
   "enable_publish_all_ports" : false,
   "enable_restart_policy" : false,
   "enabled" : true,
   "entrypoint_default" : "docker-entrypoint.sh",
   "env_variables" : [
      {
         "key" : "PATH",
         "value" : "/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
      },
      {
         "key" : "NODE_VERSION",
         "value" : "18.0.0"
      },
      {
         "key" : "YARN_VERSION",
         "value" : "1.22.18"
      }
   ],
   "exporting" : false,
   "id" : "a29fb23a7b9f43b7645b72301a24ecb6f1265c99a78167d31ad2aa9efab198bd",
   "image" : "node:latest",
   "is_ddsm" : false,
   "is_package" : false,
   "links" : [],
   "memory_limit" : 0,
   "name" : "node",
   "network" : [
      {
         "driver" : "bridge",
         "name" : "bridge"
      }
   ],
   "network_mode" : "bridge",
   "port_bindings" : [
      {
         "container_port" : 8000,
         "host_port" : 8000,
         "type" : "tcp"
      }
   ],
   "privileged" : false,
   "shortcut" : {
      "enable_shortcut" : false
   },
   "use_host_network" : false,
   "volume_bindings" : [
      {
         "host_volume_file" : "/docker/node8000",
         "mount_point" : "/home/node/app",
         "type" : "rw"
      }
   ]
}

 "cmd" : "node /home/node/app/index.js" 

즉 Nodejs Docker가 실행되자마자 NAS의 /docker/node8000 폴더를 /home/node/app으로 마운팅시키고,

/home/node/app/index.js 파일을 node로 실행하도록 됩니다. 따라서 경로가 틀리거나 index.js 파일 내 에러가 존재한다면 해당 nodejs docker는 실행되지 않습니다.

 

상관없습니다. 왜냐면 해당 index.js는 일단 테스트 서버에서 돌려보고 업로드해주면 되니까요.

 

그럼 더 중요한 node9000.syno.jon을 다음과 같이 작성합니다.

 

 node9000.syno.json 
{
   "cap_add" : [],
   "cap_drop" : [],
   "cmd" : "node",
   "cpu_priority" : 50,
   "devices" : null,
   "enable_publish_all_ports" : false,
   "enable_restart_policy" : false,
   "enabled" : true,
   "entrypoint_default" : "docker-entrypoint.sh",
   "env_variables" : [
      {
         "key" : "PATH",
         "value" : "/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
      },
      {
         "key" : "NODE_VERSION",
         "value" : "18.0.0"
      },
      {
         "key" : "YARN_VERSION",
         "value" : "1.22.18"
      }
   ],
   "exporting" : false,
   "id" : "4335cbd6c4d99a72d5112dd374ffa21ae29c3f208d7c0259593d19d983a03be7",
   "image" : "node:latest",
   "is_ddsm" : false,
   "is_package" : false,
   "links" : [],
   "memory_limit" : 0,
   "name" : "nodemon8080",
   "network" : [
      {
         "driver" : "bridge",
         "name" : "bridge"
      }
   ],
   "network_mode" : "bridge",
   "port_bindings" : [
      {
         "container_port" : 9000,
         "host_port" : 9000,
         "type" : "tcp"
      }
   ],
   "privileged" : false,
   "shortcut" : {
      "enable_shortcut" : false
   },
   "use_host_network" : false,
   "volume_bindings" : [
      {
         "host_volume_file" : "/docker/nodemon9000",
         "mount_point" : "/home/node/app",
         "type" : "rw"
      }
   ]
}

NAS이 마운팅 폴더가 /docker/nodemon9000이며,

"cmd" : "node"로 원래 처음 Nodejs를 생성했을 때의 코드를 사용합니다. 그렇기에 실행이 안될일은 없는 것이지요.

 

/docker 폴더안에

 /docker/node8000, /docker/nodemon9000  폴더도 생성합니다.

 

이제 불필요한 컨테이너를 삭제합니다. 왜냐면 컨테이너는 실행하지 않더라도 포트가 동일하면 컨테이너로서 만들어지지도 않습니다. (사실 이건좀 애매 -_-; 시놀로지에서 그렇게 관리되도록 한듯한데.. 실행되지 않으면 상관없잖우?? 실행할 때 체크하도록 허지..)

 

그리고 "설정 - 가져오기"를 클릭하여,

/docker에서 node8000.syno.json과 node9000.syno.json을 각각 가져오기 합니다. (한번에 안되요)

 

node8000은 실행해도 바로 정지됩니다. /home/node/app/index.js 가 없기 때문입니다.

 

node8000을 더블클릭하여 세부사항을 보면 내용을 확인할 수 있습니다.

 

네 index.js 모듈을 찾을 수 없다고 하네요.. (근데 시간이 왜 안맞을까요 -_-; NAS 시스템 시간은 맞음.)

 

일단 무시해주고요.. nodemon9000을 실행합니다.

 

 

 nodemon9000 실행

그러면 잘 실행됩니다. 단지 nodemon이 아니라 node라는 것.

nodemon9000 더블클릭하여 여기서  터미널  탭을 클릭합니다.

nodemon9000이 있고 터미널창이 떠 있지만 이건 무시하고, [생성] 버튼을 클릭합니다.

그르면 "bash"가 생성되는데 이걸 클릭합니다.

 

아래와 같이,

 cd /home/node/app  으로 이동하여,

 npm install -g nodemon  실행합니다. (-g는 전역으로 설정하는 옵션입니다.)

 

추가적으로 express 프레임워크를 돌릴 것이라 미리 설치해줍니다.

(추가적인 module을 PC에서 설정하여 설치하는 것은 맨아래에 추가)

 

이제 Visual Studio Code에서 /docker/nodemon9000/index.js 파일을 생성하고 다음을 작성합니다.

 

 /docker/nodemon9000/index.js 
const express = require('express')
const app = express()
const HOST = '0.0.0.0'
const PORT = 9000

app.use(express.static('static'))

// URL 라우팅
app.get('/', (req, res) => {
	res.json({
		message: "This is TEST Nodemon Server.",
		port: PORT,
        success: true,
    });
	console.log('Hello World Sent.')
})

app.listen(PORT, () => {
	console.log(`TEST Server running at http://${HOST}:${PORT}`);
})

 

이제 터미널 화면에서  nodemon index.js 로 서버를 실행합니다.

 

잘 실행되었습니다!!!!!

 

로컬주소 http://192.168.0.4:9000 이나

DDNS 설정되어 있다면 해당 주소로 접근하면 다음과 같이 웹브라우저로 볼 수 있습니다.

콘솔창에도 잘 출력됩니다.

 

이렇게 실행된 상태로 두면, nodemon으로 구동되는 테스트 서버를 실행시켜둘 수 있습니다.

 

이제 index.js 파일을 수정하면 nodemon이 알아서 node를 재실행해주기 때문에 테스트 서버는 놔두고 개발에만 전념할 수 있게 됩니다.

 

이제 터미널을 닫아도 프로세스로 nodemon이 실행되고 있게 됩니다.

=> 터미널을 닫았을 때 nodemon이 실행은 되고 있지만 index.js 코드를 수정했을 때 프로세스가 죽어버리고 마네요 ㅠ.,ㅜ;;; 결국 터미널을 개발하는 동안 지속 켜놓아야 하니 역시 불편하네요. 다른 해결방법을 찾기 전까지는 켜놓아야 할 상황이네요.

 

그래서 또 이걸보고 처음부터 "node /usr/loca/bin/nodemon index.js"로 시작하면 되잖아!?!? 싶지만..

다시 syno.json 설정파일을 변경하고 새로 컨테이너를 만들면, 해당 컨테이너에는 nodemon이 설치되어 있지 않기 때문에 Error!!! 결국 방법이 없네요. 아시는 분 답변 좀 주세요 ㅠ.,ㅜ;

 

 

 

Node8000 실서버 돌리기

 

이제 해당 index.js 파일을 /docker/node8000 폴더에 복사하고 다음과 같이 수정해줍니다.

 

 /docker/node8000/index.js 
const express = require('express')
const app = express()
const HOST = '0.0.0.0'
const PORT = 8000

app.use(express.static('static'))

// URL 라우팅
app.get('/', (req, res) => {
	res.json({
		message: "This is REAL Node Server.",
		port: PORT,
        success: true,
    });
	console.log('Hello World Sent.')
})

app.listen(PORT, () => {
	console.log(`REAL Server running at http://${HOST}:${PORT}`);
})

 

그리고 node8000 도커 컨테이너를 실행하면 또 정지되어 버립니다. 왜냐면 express를 설치하지 않아 없는 모듈이기 때문입니다.

그렇다면 실행도 되지 않는 컨테이너에 어떻게 express를 설치할 수 있을까요?? 터미널 bash도 컨테이너가 켜져서 돌아야 npm 명령이라도 입력할텐데 말입니다.

 

이제 필요한 것이 PC에서 해당 폴더에 npm 설치하기입니다.

 

 

 

PC cmd 창에서 npm 패키지 설치하는 방법

cmd를 실행하고 해당 폴더로 이동하여 작업을 하면 될 것 같지만,

 

UNC 경로를 지원하지 않아 네트워크 드라이브 접속이 안됩니다. UNC로 접근하는 방법을 써도 되겠지만..

좀더 간편하고 작업하기도 편한 네트워크 드라이브 할당으로 연결하여 작업하였습니다.

 

Z:로 Nas의 docker 폴더를 연결해줍니다.

cmd에서 Z:로 이동하여 보면 /docker 폴더로 연결된 것을 볼 수 있습니다.

 

node8000에 express를 설치할 것이므로,

이렇게 하면 해당 프로젝트 폴더에 node_modules 폴더를 가지게 되고, 해당 프로젝트에서는 해당 module을 사용할 수 있게 됩니다. 즉 현재 node8000 폴더에 한해서 index.js에서 express를 사용할 수 있게 된다는 것이지요.

 

이제 다시 node8000을 실행시켜 봅니다. 오~오~ 죽지않고 살아있습니다.

잘 설정되었다는 것이지요.

 

더블클릭해서 보면

로그도 잘 남았고..

 

프로세스도 잘 실행되고 있습니다.

 

브라우저 접속해 봅니다.

 

실서버는 index.js 파일이 수정되었다면, 컨테이너를 반드시 재시작해주어야 정상 동작합니다.

 

 

 

  1. ㅇㅇ 2022.06.22 11:48

    안녕하세요 게시글 도움이 많이 되었습니다!

    저도 node 프로젝트를 도커에 올려서 사용 중인데 터미널로(ssh가 아닌 시놀로지 ui 에서의 터미널) node 프로젝트를 실행시키고 도커 창을 끌 때 '터미널을 종료하시겠습니까?'라는 알람창에 아니오를 누르면 터미널 창이 계속 켜져있어서

    이후에도 웹 호출이 잘 되는데, 그로부터 한 5분 뒤에 다시 호출해보면 서버가 응답하지 않더라구요

    그래서 다시 도커 접속해서보면 터미널이 종료가 되어있더라구요.. 혹시 이와 같은 현상에 대해서는 어떻게 조치해야할지 질문드려도 될까요?? ㅜㅜ

ko.wikipedia.org/wiki/Node.js

 

 

 Node.js  개념

Node.js는 구글 크롬 V8 JavaScript 엔진으로 빌드된 JavaScript 런타임입니다!? (공식설명)

Node.js는 서버 사이드 어플리케이션 개발을 위한 소프트웨어 플랫폼입니다.

Node.js는 웹서버와 같은 확장성 있는 네트워크 프로그램 제작을 위해 고안되었습니다.

Node.js는 서버 사이드에서 구동되는 자바스크립트 엔진입니다.

 

더 자세한 개념등을 알고 싶으면, 하기와 같은 다른 블로그를 참고하세요.

 

 

Node.js 노드 개념 이해하기 자바스크립트 JavaScript 런타임 이벤트

Node.js 노드 개념 이해하기 JavaScript 런타임 - 노드는 다양한 자바스크립트 애플리케이션을 실행할 수 있으며, 서버를 실행하는데 제일 많이 사용된다. 이벤트 기반 이벤트 루프 논블로킹 I/O 싱글

hanamon.kr

 

하나의 Task가 무거운 일(Load가 많이 걸리는)을 해야할 때에는 Node.js는 적합하지 않으며,

개수가 많고 작은 Task가 빈번히 발생하는 데에는 Node.js가 적합합니다.

현재 하고자 하는 대부분의 작업들이 이해 해당됩니다.

단발적인 Load가 걸리는 일든은 별도 Python 등으로 구동할 예정입니다.

 

 

 

갑자기  npm ?? (Node.js Package Manager)

node.js를 설치하면 같이 설치됩니다.

확장성이 고려되어 있어 Node.js를 위해 추가적인 패키지들을 설치할 수 있는데, 이를 관리해주는 녀석입니다.

쉽게 node.js는 무조건 npm과 함께라고 생각하면 됩니다.

이렇게 마구잡이식 가져다 사용이 정말 익숙하지 않은데.. 적응해 나아가는 중..

편하긴 정말 편함. 현재는 배포자들을 믿고 가는 세상..

 

 

 

윈도우에서 Node.js 설치

 

 

Node.js

Node.js® is a JavaScript runtime built on Chrome's V8 JavaScript engine.

nodejs.org

무엇인지 모른다면,  LTS(대다수 사용자에게 추천) 를 다운로드 하면 됩니다.

Windows Installer (.msi)를 자신의 윈도우 버전에 맞는 (32-bit, 64-bit) 설치 파일을 다운로드하여 설치하세요.

Node.js 설치시 같이 설치되는 npm

 

설치가 완료되었으면, cmd 명령프롬프트를 실행하고 다음과 같이 실행..

node 버전 확인

 

그렇다 이제 어디에서든 실행되는  node 라는 명령어 하나를 얻은 셈!!!

node를 실행하면 아래와 같이 javascript 문법을 바로 사용할 수 있습니다.

종료할 때에는  Ctrl + C 를 두번 누르면 됩니다.

 

마찬가지로 다음도 해보자.

npm 버전 확인

역시 어디에서든 실행되는  npm 이라는 명령어를 얻었습니다.

 

그럼 이것으로 무얼할 수 있는데?? 기본적으로 서버를 만들 수 있지.. 어떻게?? 오케이.. 진행해봅시다.

 

 

 

Node.js 로 웹서버 시작하기

Node.js 프로젝트를 구동하기 위해 코딩을 할 텐데, 파일을 만드려면 폴더가 있어야겠지요.

D:/Nodejs 등의 위치에 폴더를 만듭니다.

바로 프로그래밍을 해도 되지만 일반적인 절차로 설명..

 

D:/Nodejs 폴더로 이동하여  npm init  실행. 커서 깜빡일 때 내용을 입력하고 엔터를 치거나 그냥 엔터를 치면 다음으로 넘어간다. 마지막에는  yes  입력하고 엔터.

그럼 package.json 파일이 생성되는데, 나중에 추가 패키지를 설치하거나 관리하는데 도움이 되는 것이라서 보통 생성해두고 진행합니다. 생성된 내용은 위에 표시된 내용이 전부!

 

이제 웹서버를 돌릴텐데, Node.js 공식홈페이지의 About에 나와있는 내용으로 진행하겠습니다.

 

 

 D:/Nodejs/index.js 

파일을 만들고 아래 내용을 입력하고 저장. (Visual Studio Code를 사용하면 편합니다.)

const http = require('http');

const hostname = '127.0.0.1';
const port = 3000;

const server = http.createServer((req, res) => {
  res.statusCode = 200;
  res.setHeader('Content-Type', 'text/plain');
  res.end('Hello World');
});

server.listen(port, hostname, () => {
  console.log(`Server running at http://${hostname}:${port}/`);
});

 

Visual Studio Code를 사용하면 편하게 코딩하면서 아래처럼 터미널 창도 바로 쓸수 있어서 좋습니다.

 

 

Visual Studio Code - Code Editing. Redefined

Visual Studio Code is a code editor redefined and optimized for building and debugging modern web and cloud applications.  Visual Studio Code is free and available on your favorite platform - Linux, macOS, and Windows.

code.visualstudio.com

 

Visual Studio Code가 설치되었다면,

D:/Nodejs 폴더에서 우클릭으로 나타나는 "Code(으)로 열기"로 Visual Studio Code를 실행하여 연동해 줍니다.

 

터미널 - 새 터미널을 만들고  node index.js  명령을 입력하여 서버를 실행시킵니다.

터미널 - 새 터미털 - "node index.js" 입력하고 엔터

Server running at http://127.0.0.1:3000/ 이라고 나오며 서버가 실행되고 접속자를 기다리게 됩니다.

터미널창에서 http://127.0.0.1:3000 주소를 Ctrl 누르고 클릭하면 바로 브라우저가 열립니다.

그럼 크롬으로 해당 주소를 열어보자.

127.0.0.1:3000

멋지다. 나만의 웹서버 완성!!!

실행중인 Node 서비스를 종료할 때에는 터미널 창에서  Ctrl + C 를 입력하면 정지됩니다.

 

 

 

npm을 이용하여 express, nodemon 설치

이제 Node.js에서 돌아가는 Express라는 웹서버 프레임워크를 설치하고 만들어보겠습니다.

아니 Node.js가 웹서버라며, 근데 또 express라는 웹서버를 설치하고 만든다고???

 

자세한 설명은 패스하고, Node.js로 웹서버를 만들면 페이지 관리 등의 복잡한 문제들이 생기는데 이를 편하게 관리해주는 녀석이라고 생각하면 됩니다.

 

이렇게 생각하면 좀 낫습니다.

이제 Node.js는 그냥 웹서버만을 돌리기 위한 단순한 프레임워크가 아니라.. npm 등으로 여러 패키지들을 설치하고 구동하게 해주는 전체 통합 프레임워크이고, 웹서버를 위해 특화된 express를 돌리는 것이 좀더 좋다라고 말이지요.

Node.js + express 조합은 현재 가장 많이 사용되고 있습니다.

 

그래서 express 프레임워크 패키지를 설치할 것이고, 추가적으로 nodemon 패키지를 설치할 것입니다.

 

node.js는 구동 js 파일의 변경과 무관하게 처음 실행될 때의 js 파일 내용으로 구동하게 되고, 변경내용을 적용하려면 node를 종료하고 다시 node를 실행해야만 한다. 개발 시점에서는 얼마나 귀찮은 일인가!?

그래서 nodemon이 등장하였다.

nodemon이 내부에서 node를 실행하고, 파일 변경이 발생하면 알아서 node를 재시작해주는 것입니다.

 

 

npm express 설치 명령
 > npm install express 

> npm install express 설치완료. 0개의 취약점.

express 공식 홈페이지

 

Express - Node.js web application framework

Fast, unopinionated, minimalist web framework for Node.js $ npm install express --save

expressjs.com

 

 

 

 

npm nodemon 설치 명령
 > npm install -g nodemon 

npm install -g nodemon 설치 완료.

-g는 global로 어디에서는 nodemon을 실행할 수 있도록 전역 설정해주는 옵션이다.

D:/Nodejs>에서만 nodemon을 사용하겠다면 -g를 붙일 필요는 없다.

 

 

 

Nodejs.express로 웹서버 구동하기

 

 전체 구성  (index.js, test.html, test.css, test.js, cat.jpg)

 /template  폴더 안에 test.html을 하나 만들고..

 /static  폴더 안에 test.js, test.css 파일과 cat.jpg 이미지 하나를 넣어줍니다.

 

template에는 html 파일을 보관해 둘것이고, static은 고정 경로로 참조할 파일들을 넣어둘 곳입니다.

 

 

 

 

 index.js 
const express = require('express')
const app = express()
const HOST = '127.0.0.1'
const PORT = 3000

app.use(express.static('static')) // 고정 폴더 사용

//
app.get('/', (req, res) => { // / 메인 페이지
	res.send("Hello World!!! <a href='/test'>Test Page</a>") // 바로응답
	console.log('Hello World Sent.')
})
app.get('/test', (req, res) => { // /test 페이지
	res.sendFile(__dirname + "/template/test.html") // 파일전송
})

app.listen(PORT, () => { // 서버실행
	console.log(`Nodejs.express Server running at http://${HOST}:${PORT}`);
})

 

 test.html 
<html>
<head>
    <title>Test Page</title>
    <link rel="stylesheet" href="test.css"/>
    <script src="test.js"></script>
</head>
<body>
    <a href="/">Home</a><br/>
    <img class="mycat" onclick="testAlert()" src="cat.jpg"/><br/>
    한번 가면 끝인 없는 인생 멀그리 힘들게 사니..
</body>
</html>

 

 test.css 
* {
    background-color: rgb(193, 226, 241);
}
.mycat {
    border-radius: 30px;
}

 

 test.js 
function testAlert() {
    alert('할거면 목숨바쳐 해봐!')
}

 

cat.jpg

 

 

 

nodemon으로 index.js 실행
 > nodemon index.js 

 

이제 모두 끝났습니다. 터미널 창에서 아래와 같이 입력합니다.

 

> nodemon index.js

서버가 잘 실행되었습니다.

이 상태에서 index.js 파일 내용을 변경하고 저장을 하면..

 

위와 같이 nodemon이 변경사항으로 인해 node를 알아서 재실행해주는 것을 볼 수 있습니다.

이제 편하게 개발에 집중할 수 있겠네요.

 

http://127.0.0.1:3000  접속해봅니다.

/ 메인페이지
/test 테스트페이지
고양이클릭 - testAlert()

 

이제 무언가 그럴싸한 html + css + javascript와 이미지로 이루어진 웹페이지를 구성할 수 있게 되었습니다.

 

* VSCode

 

 

* Node, Npm, Javascript, React Native & Expo를 이용하여 나만의 꿀팁 페이지 꾸미기

 

 

 

 

* Expo AboutPage.js 만들어보기

 

 

예전에 일일이 불안정한 프로그램들 설치하며 찾아다니며, 공부하고 바꾸고 힘들던 그때.. 는 갔다..

물론 지금은 너무 많기 때문에 잘 찾아서 사용해보고 나에게 맞는 프레임워크를 구축하는 것도 일이긴 할 것 같다.

 

 

 

1. FileZilla

 + AWS FTP 접속용

 

2. 가비아

 + shop 도메인 500원 할인중

 

3. 무비스타 프로젝트 완성

 

4. AWS

 

5. Flask 서버 구동

 

6. 원페이지 쇼핑몰 DB연동 도메인 연동하여 실행

http://innosoft.shop 

 

원페이지쇼핑몰

내가 만든 원페이지쇼핑몰 테스트

innosoft.shop

 

 

음 재미있는 웹개발이었다..

예전에 php, javascript, css로 노가다 개발하던 것과 크게 다른 건 없는 듯 하면서도..

각각 잘 구성된 프레임워크라는 이름으로 잘 가져다 쓰도록 구성되었다는 점이 좋은 듯..

 

확실히 특정 정보를 보기 위해 페이지를 넘기며 매번 페이지가 바뀌는 형태보다는

Ajax로 백엔드와 연동하여 UI를 갱신하는 것이 사람이 인식함에 지속적인 정보의 유지가 된다는 느낌이 든다.

 

조금 아쉬운 것은

생각하는 아이디어들을 구현해낼 정도의 결과물들은 아니라서 ㅠ.,ㅜ;

완전 겉핥기가 끝난것이고, 또 공부할 내용들이 많을 듯하다.

 

 

1. Flask 서버 사용하기

 

2. Flask 서버로 Ajax 이용하여 GET, POST 등 요청

 

3. 모두의 책 리뷰. 요청정보 MongoDB 저장하고 List 불러와서 보여주기

 

4. 나홀로메모장. 글쓰기 -> 웹크롤링하여 DB저장하고 -> 목록 보여주기

 

5. 원페이지 쇼핑몰 - 주문하고 목록보여주기

 

 

Flask 서버와 Ajax를 활용하여 백그라운드 정보 요청 및 표시 처리 등의 반복 작업..

마지막 원페이지쇼핑몰은 오히려 웹크롤링 등이 연동되지는 않음.

 

 

 

1. OpenAPI로 Ajax 연동

 

2. Python List, Dictionary 기본 사용

+ JQuery와 거의 유사하네.

 

 

3. Naver 영화 랭크 페이지 크롤링하여 MongoDB에 저장

 

 

4. 지니 뮤직 사이트 랭크 크롤링 및 MongoDB 저장

 

 

이젠 정말 하나하나 이해하고 개발하는 시대는 끝났다..

무엇을 어떻게 잘 활용하여 서비스를 만드는가가 중요한 것이다.

 

 

 

1. 서울시 미세먼지 OpenAPI 이용하기

 

2. 서울시 따릉기 OpanAPI 이용하기

 

3. 랜덤 고양이 사진 API

 

 

4. 환율 API 이용하여 환율 표시

 

 

 

Ajax를 쓰기위해 JQuery를 import 해주면 되고..

 

OpenAPI가 일 다 하네.. 결국 데이터를 처리해주는 백엔드의 공개 API인것..

 

 

 

 

1. PyCharm.. - Html + CSS 핫한 개발툴..

 

 

2. Html + CSS를 이용하여 간단한 로그인 페이지를 뚝딱 만들기

 

 

3. 구글 웹 폰트 - 많지는 않지만 바로 사용하기 편하다.

https://fonts.google.com/?subset=korean 

 

Google Fonts

Making the web more beautiful, fast, and open through great typography

fonts.google.com

 

 

4. 부트스트랩 - 워낙 유명한데.. 이렇게 편하게 사용하는 것이었는지는 이번에 알게됨.

https://getbootstrap.com/docs/4.0/components/alerts/

 

Alerts

Provide contextual feedback messages for typical user actions with the handful of available and flexible alert messages.

getbootstrap.com

 

 

5. 부트스트랩을 이용하여 간단한 링크메모장 만들기..

 

 

6. Javascript 연습

+ 크롬 브라우저 F12 - 콘솔 에서 Javascrip 연습

 

 

7. HTML+CSS를 이용한 원페이지 쇼핑몰

 

 

 

아직도 모든 걸 직접 개발해야 할 것 같은 알 수 없는 중압감이 있지만..

이제는 벗어나야 하는 시대이지 않을까 합니다.

 

어렵지만 한발자국씩 전진해 봅니다.

장비 업체도 언젠가는 개발 방향이 모두 바뀌게 되겠지요.

 

 

패스트캠퍼스에서 진행한 "올인원 패키지 : 유니티 포트폴리오 완성 올인원 패키지 Online." 과정을 수강하였습니다.

예전부터 유니티에 관심도 있었고, 관련 업무에서 Unity를 활용하는 일이 생겨 겸사겸사 수강을 하게되었습니다.

매일 연속 50일 작성.. 사실 못할줄 알고 시작한건데 끝을 보게 되네요 ^^;
블로그도 열심히 해보려했지만 업무등에 치이게 되면 멈춰버리는 경우가 많아, 내 자신에 대한 도전이라는 마음으로 진행을 했는데 마음은 뿌듯합니다. ㅎㅎ

특히 Unity 업무를 진행하고 있었기 때문에 하나라도 더 듣고 내것으로 만들자는 마음으로 더 열심히 했던 것 같습니다. 사실 시작한 김에 꾸준히 더 작성을 하려는 욕심은 있었는데 연말이라 ㅠ.,ㅜ; 쉽지 않네요..

 

자~ 유니티 게임 포트폴리오 완성 강의에 대한 전반적인 내용을 작성해 봅니다.

 

 

 



제가 수강한 강좌입니다.

"올인원 패키지 : 유니티 포트폴리오 완성 올인원 패키지 Online."은 기초 과정이 아닙니다.
기초 과정은 "C#과 유니티로 배우는 게임 개발 올인원 패키지 Online"라는 과정이 따로 있습니다.
저는 C#은 오랜 기간 사용을 해왔었고, Unity는 책을 보고 따라해본 경험이 있어서 초급 과정은 건너 뛰었습니다.
초급에서 중급을 넘어가시려는 분들이나 중급인데 디아블로나 배틀로얄과 같은 게임을 실무적으로 구현하는 방법을 알고 싶다하시는 분들에게 추천드립니다.


게임 포트폴리오라는 제목으로도 유추할 수 있듯이 "취업준비생"분들을 위해 실무에서 게임 개발시 필요한 지식들을 많이 알려줍니다.
사실 저는 취업준비생도 아니고 포트폴리오를 구성할 것은 아니었지만, "포트폴리오"라는 말처럼 Unity의 다양한 부분들을 접할 수 있을 것이라고 생각하고 접근을 하였습니다.

처음에 목차를 볼 때에는 여러 가지 게임을 만드는 포트폴리오 구성을 생각했었는데..
실제로는 "디아블로"와 "배틀로얄" 2가지 게임을 집중적으로 구현해 보게 됩니다.



디아블로 구현 모습입니다.

한 단계씩 정리가 잘 되어 있습니다.
Rigidbody를 시작으로 해서 Character Controller, NavMeshAgent를 활용하여 AI 이동 등을 구현해보게 됩니다.
Animation에 대해서도 설명이 이어지지만 Unity 설정에 대해서는 자세하게 진행하지는 않습니다. 기초강좌가 아니기 때문입니다.
Animation의 Transition에 대해서 자세한 설명이 이어집니다.
TopDown Camera를 구현하여 어떻게 화면을 구성하는지를 구현해봅니다.
이 외에도 Light, FSM, AI, 시야, 전투시스템, 원거리공격, 인벤토리 구현, 문/함정 구현 등을 진행하게 됩니다.


이것이 끝이 아니라 위와 같이 Firebase를 활용하여 LeaderBoard를 구현하고 서버를 통해 연동해보는 실습도 포함되어 있습니다.
사실 디아블로에서는 그렇게 중요한 비중을 차지하는 부분은 아니지만 간단한 캐쥬얼 게임을 만들때는 많이 사용하게 되지 유용하다고 볼 수 있습니다.




이어서 배틀로얄(=배틀그라운드) 구현 모습입니다.

배틀로얄은 따라가기 조금 버거울 수 있습니다. 다만 인내심을 가지고 꾸준히 따라하시는 분은 굉장히 유용한 실무에서도 많이 사용될 Tool등을 만들어 볼 수 있습니다.

강의 시작에서는 취업준비생분들을 타겟으로 하여 실무 관련 많은 이야기를 합니다.
저는 지금은 다른 필드에서 먹고살고 있는 프로그래머이지만, 소프트웨어 업계의 공통적인 어려움과 문제점들은 비슷하다고 봐야겠지요.
그렇기 때문에 꼭 게임의 구현에 집중된 것이 아니라, 게임 개발에 플러스적으로 필요한 요소들 즉 관리 툴 같은 것들이 필요하게 됩니다.
저 또한 어떤 소프트웨어 업종에서 일하건간에 간단하게 구현하여 도움을 주는 툴들은 많이 개발을 해왔습니다.
실무에서 귀찮다고 안 하시는 분들이 대다수라고 봐야겠지요.. 너무 잘하셔서 안하시는 분들은 예외겠지만.. 여튼..

EffectTool, SoundTool에 이어 Behaviour 구현, Weapon 구현, Health, Alert, Shoot, Health 등 배틀로얄 게임을 구동하기 위한 다양한 클래스와 함수들을 구현해볼 수 있습니다.

조금 아쉬웠던 부분은 너무 많은 기능, 옵션을 설명해주시려고 하다보니 변수 선언, 초기화, 사용 등 따라해야할 코딩량이 너무 많았다는 느낌입니다.
최종적으로 배틀로얄 구현을 위해서 다 알아야 하는 부분도 맞고, 직접 코딩을 계속 여러번 해보면서 자신만의 코드가 되는 것이 맞습니다..
하지만 온라인 강의이므로 최소 옵션으로 해서 코딩을 진행하고 다른 부분은 완성된 코드를 가지고 설명에 집중해주셨더라면 더 좋지 않았을까 싶은 개인적인 아쉬움을 남겨봅니다.
그래도 적은 강의 시간에 담기에 쉽지 않은 내용이라 충분히 감안하고 시청하였습니다.
특히 실무에서 사용되는 알찬 정보들을 원하신다면 강력 추천드립니다.


현재 Unity 업무를 진행함에 많은 도움을 받았습니다.
특히 NavMesh 개념과 Transition 처리 등은 참 멋진 개념이며 멋진 설명이었습니다.

앞으로도 좋은 강의 많이 부탁드립니다.

감사합니다.


패스트캠퍼스 - 올인원 패키지 : 유니티 포트폴리오 완성 bit.ly/2R561g0

 

유니티 게임 포트폴리오 완성 올인원 패키지 Online. | 패스트캠퍼스

게임 콘텐츠 프로그래머로 취업하고 싶다면, 포트폴리오 완성은 필수! '디아블로'와 '배틀그라운드' 게임을 따라 만들어 보며, 프로그래머 면접에 나오는 핵심 개념까지 모두 잡아 보세요!

www.fastcampus.co.kr

 

  1. 유니티맨 2021.02.03 03:41

    리스펙합니다!

    • BOOX 2021.02.11 01:14 신고

      감사합니다 ^^~
      즐거운 명절 보내시고,
      행복한 2021년 한 해 되십시오.

[패스트캠퍼스 수강 후기] 올인원 패키지 : 유니티 포트폴리오 완성 100% 환급 챌린지 50회차 미션 시작합니다.

05. 배틀그라운드 - 03, 04, 05 번을 진행합니다.




Enemy Data 준비에 대한 시작입니다.

구글 스프레드 시트는 좋기는 한데 너무 느려서 애매하고, 엑셀은 정말 많이 사용하고, 툴은 좋긴 하지만 지속 누군가가 수정을 해줘야 하는데 그렇게 여유로는 모바일 게임 개발사는 없을 것이기에.. 결국 Table of Data를 처리하기 위한 방법들이 필요합니다.




GeneralStats 스크립트를 해당 위치에 생성하고 작성을 시작합니다.

[CreateAssetMenu(menuName="PluggableAI/GeneralStats")]
public class GeneralStats : ScriptableObject
{
    [Header("General")]
    [Tooltip("npc 정찰 속도 clear state")]
    public float patrolSpeed = 2f;
    [Tooltip("npc 따라오는 속도 warning state")]
    public float chaseSpeed = 5f;
    [Tooltip("npc 회피하는 속도 engage state")] // 교전시
    public float evadeSpeed = 15;
    [Tooltip("웨이포인트에서 대기하는 시간")]
    public float patrolWaitTime = 2f;
    [Header("Animation")]
    public LayerMask obstacleMask; // 장애물 레이어 마스크
    public float angleDeadZone = 5f; // 조준시 깜빡임을 피하기 위한 최소 확정 앵글
    public float speedDampTime = 0.4f; // 속도 댐핑 시간
    public float angularSpeedDampTime = 0.2f; // 각속도 댐핑 시간
    public float angleResponseTime = 0.2f; // 각속도 안에서 각도 회전에 따른 반응 시간
    [Header("Cover")]
    public float aboveCoverHeight = 1.5f; // 장애물에 숨었을 때 고려해야할 최소높이값
    public LayerMask coverMask; // 장애물 레이어마스크
    public LayerMask shotMask; // 사격 레이어마스크.
    public LayerMask targetMask; // 타겟 레이어마스크.
}




위의 CreateAssetMenu 함수를 통해 생성된 메뉴를 볼 수 있으며, 이를 클릭합니다.



생성된 파일 이름을 EnemyCommonStats라고 지정하고, 우측의 Inspector에 설정값들을 적용해 줍니다.



EntityTable을 클릭해보면 엑셀 파일이 열리는데 무기에 대한 설정값들이 적용되어 있는 것을 볼 수 있습니다.

 



EntityTable에서 우클릭하여 "XLS Import Settings..."를 클릭합니다.
그러면 엑셀 파일을 읽어서 보여주는 ExcelImporterMaker 창이 나타납니다.

AimOffset 값을 Float으로 설정하고 불필요한 것의 [ ]enable을 꺼주는 등의 설정을 해주고, [create] 버튼을 클릭합니다.




EntityTable에서 다시 우클릭하여 Reimport를 클릭하여 줍니다.




그러면 위와 같이 EntityTable 데이터 셋이 생성된 것을 확인할 수 있습니다.

복잡한 듯 하지만 엑셀을 잘 활용하여 다양한 데이터들을 처리하는 것이 여러가지 확장성에서 좋다라고 보면 됩니다.

사실 엑셀은 이제 실무에서 어떠한 형태로는 사용안되는 경우가 없는 듯해요 ^^. 데이터 관리, 로그, 레포팅, 분석 등 정말 다양한 형태로 활용되죠.. ㅎㅎ





Enemy AI 기본 클래스들 생성입니다.




StateMachine 폴더를 만들고, 하위 폴더로 Action, Decision, State, Transition 폴더를 만듭니다.
그리고 각각의 폴더 안애 위와 같이 스크립트들을 미리 생성해 둡니다.
이렇게 한 이유는 어떤 스크립트들이 만들어지고 어떻게 사용될지를 미리 보기 위함입니다.

우선 StateController를 더블클릭하여 코딩을 시작합니다 ^^~
(Enemy AI 기본 클래스 생성을 마치기 위하여 하나 더 진행..)


/// <summary>
/// state -> actions update -> transition (decision) check..
/// state에 필요한 기능들. 애니메이션 콜백들..
// 시야 체크, 찾아놓은 엄폐물 장소중 가장 가까운 위치를 찾는 기능.
/// </summary>
public class StateController : MonoBehaviour
{
    public GeneralStats generalStats;
    public ClassStats statData;
    public string classID; // PISTAL, RIFLE, AK
    
    public ClassStats.Param classStats {
        get {
            foreach (ClassStats.Sheet sheet in statData.sheets)
                foreach (ClassStats.Param parm in sheet.list)
                    if (parm.ID.Equals(classID)) return parm;
            return null;
        }
    }
    
    public State currentState;
    public State remainState;
    public Transition aimTarget;
    public List<Transition> patrolWaypoints;
    public int bullets;
    [Range(0,50)]
    public float viewRadius;
    [Range(0,360)]
    public float viewAngle;
    [Range(0,25)]
    public float perceptionRadius;
   
    [HideInInspector] public float nearRadious;
    [HideInInspector] public NavMeshAgent nav;
    [HideInInspector] public int wayPointIndex;
    [HideInInspector] public maximumBurst = 7;
    [HideInInspector] public float blindEngageTime = 30f;
    [HideInInspector] public bool targetInSight;
    [HideInInspector] public bool focusSight;
    [HideInInspector] public bool reloading;
    [HideInInspector] public bool hadClearShot; // before
    [HideInInspector] public bool haveClearShot; // now
    [HideInInspector] public int coverHash = -1; // 장애물마다 고유코드가 있어서 캐릭터들이 몰리지 않고 적당한 장애물을 찾도록 하기 위해..
    [HideInInspector] public EnemyVariables variables;
    [HideInInspector] public Vector3 personalTarget = Vector3.zero;
    
    private int magBullets;
    private bool aiActive;
    private static Dictionary<int, Vector3> coverSpot; // static
    private bool strafing;
    private bool aiming;
    private bool checkedOnLoop, blockedSight;
    
    [HideInInspector] public EnemyAnimation enemyAnimation;
    [HideInInspector] public CoverLookUp coverLookUp;
    
    public Vector3 CoverSpot {
        get { return coverSpot[GetHashCode()]; }
        set { coverSpot[GetHashCode()] = value; }
    }
    
    public void TransitionToState(State nextState, Decision decision) {
        if (nextState != remainState) currentState = nextState;
    }
}




strafing에 대해 구글에서 검색하여 내용을 찾아본 설명입니다..

 

50회 챌린지 미션은 할 수 있을까 싶었는데 결국 완료는 하였네요 ^^;

50일 동안 하루도 거르지 않고 무언가를 한다는 것이 어려울거라 예상은 했지만 생각보다 훨씬 어렵네요. 일단 뿌듯합니다. ㅎㅎ



<위의 코드들은 제가 보면서 주요한 함수, 코드를 확인하기 위해 타이핑한 용도로, 전체 소스코드가 아님에 주의해 주세요. 전체 코드는 교육 수강을 하면 완벽하게 받으실 수가 있답니다 ^^>

패스트캠퍼스 - 올인원 패키지 : 유니티 포트폴리오 완성 bit.ly/2R561g0

 

유니티 게임 포트폴리오 완성 올인원 패키지 Online. | 패스트캠퍼스

게임 콘텐츠 프로그래머로 취업하고 싶다면, 포트폴리오 완성은 필수! '디아블로'와 '배틀그라운드' 게임을 따라 만들어 보며, 프로그래머 면접에 나오는 핵심 개념까지 모두 잡아 보세요!

www.fastcampus.co.kr

 

+ Recent posts