인프런 커뮤니티 질문&답변

안근창님의 프로필 이미지

작성한 질문수

따라하며 배우는 도커와 CI환경 [2023.11 업데이트]

도커 볼륨을 이용한 소스 코드 변경

소스를 바꿔도 반영이 되지 않습니다.

작성

·

5.3K

8

도커에 볼륨을 넣어서 했는데
소스를 바꿔도 바로 반영되지 않습니다.

혹시 볼륨 바인드가 잘못되었나 해서
docker exec -it <컨테이너> /bin/sh
로 들어가서 src/app.js 를 cat으로 열어보면 
제대로 볼륨바인딩이 되어있는것이 확인되고
내용도 바뀐 내용입니다.

하지만 브라우저에서는 캐시비우고 접해도 여전히
처음 run했을때의 내용입니다.

혹시나 해서 exec로 들어간 상태에서
vi로 app.js를 바꿔서 저장하면
vscode의 App.js도 바뀌는 것을 보아서
바인딩 되는 것은 맞는데..

확인 부탁드립니다....

혹시 몰라서 package.json 내용도 올려드립니다.

{
  "name": "reactapp",
  "version": "0.1.0",
  "private": true,
  "dependencies": {
    "@testing-library/jest-dom": "^4.2.4",
    "@testing-library/react": "^9.5.0",
    "@testing-library/user-event": "^7.2.1",
    "react": "^16.13.1",
    "react-dom": "^16.13.1",
    "react-scripts": "3.4.3"
  },
  "scripts": {
    "start": "react-scripts start",
    "build": "react-scripts build",
    "test": "react-scripts test",
    "eject": "react-scripts eject"
  },
  "eslintConfig": {
    "extends": "react-app"
  },
  "browserslist": {
    "production": [
      ">0.2%",
      "not dead",
      "not op_mini all"
    ],
    "development": [
      "last 1 chrome version",
      "last 1 firefox version",
      "last 1 safari version"
    ]
  }
}

답변 20

33

안근창님의 프로필 이미지
안근창
질문자

자문 자답

- stackoverflow에 보니 이미 질의와 답변이 있어서 해결하였습니다.. (허탈..)

- 리액트 핫로딩 작동을 위해선 도커 실행에 에 다음 옵션이 필요합니다.  

  • -e CHOKIDAR_USEPOLLING=true

- 이제 아주 잘 작동합니다.....

- chokidar 모듈은 WebPack과 Babel이 파일들의 모니터링을 하기 위해 사용하는 모듈로

  create-react-app에도 포함되어있는 모듈입니다.

- 혹시 저처럼 일주일 날리는 사람 없도록 올립니다.

- Dockerfile 안에 ENV로 CHOKIDAR_USEPOLLING=true를 넣어줘도 동작한다고 합니다.

15

안근창님의 프로필 이미지
안근창
질문자

약간 더 상세 설명 ㅎ

  • chokidar는 NodeJS의 fs.watch/fs.watchFile/FSEvents의 wrapper입니다.
  • Mac에서 chokidar는 Darwin FSEvents API 확장 구현체가 사용되며,
    매우 효율적인 watch 효율을 보여준다고 합니다.
  • MacOS 외의 플랫폼에서는 fs.watch 기반 구현체가 기본값인데,
    polling을 최대한 피해서 cpu 부하를 낮추는 구현을 갖추고 있습니다.
  • 그래서 usePolling 기본값이 MacOS에선 true이고, 나머지는 false입니다.
  • 출처 : https://www.npmjs.com/package/chokidar#performance
  • VM으로 도커를 돌리는 Mac/Win과 달리 linux Native 위에서 도커를 
    돌릴때는 네트워크를 통한 바인드가 아니어서 polling을 안해도
    정상적인 watch가 가능 합니다.
  • 결론적으로 이 문제는 윈도우 도커를 쓰시는 분들에 한해서 문제가 되는 것입니다.
  • 많은 공부 했습니다.

2

안근창님의 프로필 이미지
안근창
질문자

@Kihun Kim

안녕하세요
저도 해당 부분에 다시 막혀서 한 이틀 고민했었다가 결국 그냥
WSL위의 우분투에서 작업하면서 그냥 넘어갔었습니다 ^^

리액트의 테스트는 jest라는 것을 사용하는 것 같은데 거기서 watch code 부분은
제가 위에서 설명한 npm start에서 사용하는 chokidar를 사용하는 것이 아니라
jest-haste-map에 해당되는 부분인건 알아서
해당부분을 검색해봤는데 뚜렷한 해답을 찾지 못했습니다.(다른 분에게 바톤을 넘기겠습니다!)

' docker-windows-volume-watcher'나 'docker-windows-notifier'등 
윈도우 도커를 쓰는 많은 사람들이 이 이슈를 해결하기위해
써드 파티 프로그램까지  사용하는 부분이 있었는데 ..
리액트 수업도 아닌데 그건 아닌 것 같아서 ..걍 여기서 포기했습니다.ㅎㅎ

강사님도 모르는 부분인것 같아서 물어볼 수도 없고..
저도 너무 답답하네요..ㅎ
부디 누군가 답변을 찾아주시면 저도 앓는 속이 내려가겠네요 ㅎ

혹시 wsl 위 우분투로 compose-up --build 했을 때

permission denied, mkdir node_modules/.cache

이런 오류 발생하신 적 있을까요?

저도 동일하게 우분투에 올리는데 이부분에서 막히고

스택오버플로우 등 검색(USER node 지정, chown -R 권한부여, 등등)

해도 전혀 해결되지 않네요

혹시 우분투 설치한 버전을 알 수 있을까요?

저는 이렇게하면 해결되더군요 :)

2

John Ahn님의 프로필 이미지
John Ahn
지식공유자

앗   저도 모르는 부분이였네요 ㅠㅠ  !!  
수고하셨습니다  그리고 다른분들을 위해서 공유해주셔서 감사합니다 ~ ! 

CHOKIDAR_USEPOLLING=true  사용에도 해결되지 않는 경우도 있습니다... windows 사용자들을 위해서 이부분에 대해서 정보 반영 요청드립니다. 

1

굿잡맨!

1

많은 도움 되었습니다!!

1

공유해주셔서  감사합니다 도움이 많이 되었어요! 

1

안녕하세요.

같은 강의를 수강하면서 리액트 핫 로딩 부분에 대해서 도움을 받아서 감사 인사 드리러 왔습니다.

안근창님 감사드립니다^^

0

고생하셨습니다!

덕분에 하나 더 알아갑니다 :)

0

안근창님의 프로필 이미지
안근창
질문자

@전윤회
도움이 되었다니 너무 기쁘네요.. 제가 더 감사합니다 ^^

부디 누가 jest테스트까지 해결해주셔서 종결되길  바랍니다 ^^

0

감사합니다. 저도 해결했네요

한기지 질문있는데요 이게 그 다음 강의에 나오는 react app test에도 적용이 되는 내용인가요?? 

이렇게도 해보고 Dockerfile.dev  에도 

ENV CHOKIDAR_USEPOLLING=true

넣어봤는데 App.js 소스 바뀐거는 반영하는데 App.test.js 가 변경된거는 감지를 못하네요... 

제가 설정을 잘못한 부분이 있나요? 

0

안근창님의 프로필 이미지
안근창
질문자

@이성준

계속적으로 이렇게 감사를 받으니 뿌듯하네요 ^^ 열공화이팅입니다!

0

감사합니다.

0

안근창님의 프로필 이미지
안근창
질문자

@대배랙

도움이 되셨다니 뿌듯합니다 ^^

0

와 안되던부분인데 보고 바로해결했습니다 감사합니다.

0

안근창님의 프로필 이미지
안근창
질문자

@ 윌던

도움이 되셨다니 매우 기쁘네요. ~~

0

안근창님의 프로필 이미지
안근창
질문자

>소스에 들어가니까 파일과 폴더만 보이고 그안에 소스는 안보이네요

--> 이게 무슨 말씀이신지 모르겠습니다. 강의 처음부터 계속 따라했던 파일들입니다.

>그래서 사실 VOLUME을 이용한다면 COPY 부분을 빼버려도 앱을 돌아갑니다. 

--> 맞습니다. 실제로도 해보았습니다. 다만 변경을 해도 반영이 안될 뿐입니다.

계속 바인딩의 실패를 전제하고 설명하고 계셔서..

아예 처음부터 설명을 드리겠습니다.

1. 위 소스 파일 풀어놓은 디렉토리입니다.

package.json은 다음과 같습니다.

{
  "name""reactapp",
  "version""0.1.0",
  "private"true,
  "dependencies": {
    "@testing-library/jest-dom""^4.2.4",
    "@testing-library/react""^9.5.0",
    "@testing-library/user-event""^7.2.1",
    "react""^16.13.1",
    "react-dom""^16.13.1",
    "react-scripts""3.4.3"
  },
  "scripts": {
    "start""react-scripts start",
    "build""react-scripts build",
    "test""react-scripts test",
    "eject""react-scripts eject"
  },
  "eslintConfig": {
    "extends""react-app"
  },
  "browserslist": {
    "production": [
      ">0.2%",
      "not dead",
      "not op_mini all"
    ],
    "development": [
      "last 1 chrome version",
      "last 1 firefox version",
      "last 1 safari version"
    ]
  }
}

Dockerfile.dev는 다음과 같습니다.

FROM node:alpine
WORKDIR /usr/src/app
COPY package.json ./
RUN npm install

# 카피부분 주석처리
# COPY ./ ./

CMD [ "npm","run","start"]

실행했던 부분은 다음과 같습니다.

### 빌드 부분
docker build -f Dockerfile.dev -t rkaehdaos/react1 .

### volume 사용하기 <== 여기가 안되는 부분
docker run --rm -it -p 3000:3000 -v /usr/src/app/node_modules -v %cd%:/usr/src/app rkaehdaos/react1:latest

빌드 성공하는 부분입니다

```

c:\dev\reactapp>docker build -f Dockerfile.dev -t rkaehdaos/react1 .

Sending build context to Docker daemon  629.8kB

Step 1/5 : FROM node:alpine

 ---> b85fc218c00b

Step 2/5 : WORKDIR /usr/src/app

 ---> Running in 36ee76c8f1fc

Removing intermediate container 36ee76c8f1fc

 ---> f86527e7d3fc

Step 3/5 : COPY package.json ./

 ---> 0b7f4d049254

Step 4/5 : RUN npm install

 ---> Running in 85954865dd12

npm WARN deprecated urix@0.1.0: Please see https://github.com/lydell/urix#deprecated

npm WARN deprecated chokidar@2.1.8: Chokidar 2 will break on node v14+. Upgrade to chokidar 3 with 15x less dependencies.

npm WARN deprecated @types/testing-library__dom@7.5.0: This is a stub types definition. testing-library__dom provides its own type definitions, so you do not need this installed.

npm WARN deprecated request@2.88.2: request has been deprecated, see https://github.com/request/request/issues/3142

npm WARN deprecated request-promise-native@1.0.9: request-promise-native has been deprecated because it extends the now deprecated request package, see https://github.com/request/request/issues/3142

npm WARN deprecated resolve-url@0.2.1: https://github.com/lydell/resolve-url#deprecated

npm WARN deprecated @hapi/joi@15.1.1: joi is leaving the @hapi organization and moving back to 'joi' (https://github.com/sideway/joi/issues/2411)

npm WARN deprecated fsevents@1.2.13: fsevents 1 will break on node v14+ and could be using insecure binaries. Upgrade to fsevents 2.

npm WARN deprecated har-validator@5.1.5: this library is no longer supported

npm WARN deprecated @hapi/address@2.1.4: This version has been deprecated and is no longer supported or maintained

npm WARN deprecated @hapi/hoek@8.5.1: This version has been deprecated and is no longer supported or maintained

npm WARN deprecated @hapi/bourne@1.3.2: This version has been deprecated and is no longer supported or maintained

npm WARN deprecated @hapi/topo@3.1.6: This version has been deprecated and is no longer supported or maintained

npm WARN deprecated left-pad@1.3.0: use String.prototype.padStart()

npm WARN deprecated core-js@2.6.11: core-js@<3 is no longer maintained and not recommended for usage due to the number of issues. Please, upgrade your dependencies to the actual version of core-js@3.

 

> core-js@2.6.11 postinstall /usr/src/app/node_modules/babel-runtime/node_modules/core-js

> node -e "try{require('./postinstall')}catch(e){}"

 

Thank you for using core-js ( https://github.com/zloirock/core-js ) for polyfilling JavaScript standard library!

 

The project needs your help! Please consider supporting of core-js on Open Collective or Patreon:

> https://opencollective.com/core-js

> https://www.patreon.com/zloirock

 

Also, the author of core-js ( https://github.com/zloirock ) is looking for a good job -)

 

 

> core-js@3.6.5 postinstall /usr/src/app/node_modules/core-js

> node -e "try{require('./postinstall')}catch(e){}"

 

Thank you for using core-js ( https://github.com/zloirock/core-js ) for polyfilling JavaScript standard library!

 

The project needs your help! Please consider supporting of core-js on Open Collective or Patreon:

> https://opencollective.com/core-js

> https://www.patreon.com/zloirock

 

Also, the author of core-js ( https://github.com/zloirock ) is looking for a good job -)

 

 

> core-js-pure@3.6.5 postinstall /usr/src/app/node_modules/core-js-pure

> node -e "try{require('./postinstall')}catch(e){}"

 

Thank you for using core-js ( https://github.com/zloirock/core-js ) for polyfilling JavaScript standard library!

 

The project needs your help! Please consider supporting of core-js on Open Collective or Patreon:

> https://opencollective.com/core-js

> https://www.patreon.com/zloirock

 

Also, the author of core-js ( https://github.com/zloirock ) is looking for a good job -)

 

npm notice created a lockfile as package-lock.json. You should commit this file.

npm WARN optional SKIPPING OPTIONAL DEPENDENCY: fsevents@2.1.2 (node_modules/react-scripts/node_modules/fsevents):

npm WARN notsup SKIPPING OPTIONAL DEPENDENCY: Unsupported platform for fsevents@2.1.2: wanted {"os":"darwin","arch":"any"} (current: {"os":"linux","arch":"x64"})

npm WARN optional SKIPPING OPTIONAL DEPENDENCY: fsevents@^1.2.7 (node_modules/jest-haste-map/node_modules/fsevents):

npm WARN notsup SKIPPING OPTIONAL DEPENDENCY: Unsupported platform for fsevents@1.2.13: wanted {"os":"darwin","arch":"any"} (current: {"os":"linux","arch":"x64"})

npm WARN notsup Unsupported engine for watchpack-chokidar2@2.0.0: wanted: {"node":"<8.10.0"} (current: {"node":"14.11.0","npm":"6.14.8"})

npm WARN notsup Not compatible with your version of node/npm: watchpack-chokidar2@2.0.0

npm WARN optional SKIPPING OPTIONAL DEPENDENCY: fsevents@^1.2.7 (node_modules/watchpack-chokidar2/node_modules/chokidar/node_modules/fsevents):

npm WARN notsup SKIPPING OPTIONAL DEPENDENCY: Unsupported platform for fsevents@1.2.13: wanted {"os":"darwin","arch":"any"} (current: {"os":"linux","arch":"x64"})

npm WARN optional SKIPPING OPTIONAL DEPENDENCY: fsevents@^1.2.7 (node_modules/webpack-dev-server/node_modules/chokidar/node_modules/fsevents):

npm WARN notsup SKIPPING OPTIONAL DEPENDENCY: Unsupported platform for fsevents@1.2.13: wanted {"os":"darwin","arch":"any"} (current: {"os":"linux","arch":"x64"})

npm WARN tsutils@3.17.1 requires a peer of typescript@>=2.8.0 || >= 3.2.0-dev || >= 3.3.0-dev || >= 3.4.0-dev || >= 3.5.0-dev || >= 3.6.0-dev || >= 3.6.0-beta || >= 3.7.0-dev || >= 3.7.0-beta but none is installed. You must install peer dependencies yourself.

 

added 1620 packages from 785 contributors and audited 1624 packages in 29.19s

 

69 packages are looking for funding

  run `npm fund` for details

 

found 0 vulnerabilities

 

Removing intermediate container 85954865dd12

 ---> 48270b53a99a

Step 5/5 : CMD [ "npm","run","start"]

 ---> Running in b0776177bfd5

Removing intermediate container b0776177bfd5

 ---> c5cfc2c7c368

Successfully built c5cfc2c7c368

Successfully tagged rkaehdaos/react1:latest

SECURITY WARNING: You are building a Docker image from Windows against a non-Windows Docker host. All files and directories added to build context will have '-rwxr-xr-x' permissions. It is recommended to double check and reset permissions for sensitive files and directories.

 

c:\dev\reactapp>

```

카피 없이 이미지를 만들었지만 정상적인 데모 리액트를 볼 수 있습니다.

이제 소스를 고친 후 새로 고침을 해도 바뀌지 않습니다.

정리

- 계속적으로 제가 볼륨 바인딩을 못했을 경우를 예를 드셔서 아예 처음부터 보여드렸습니다.

- 이미지 자체에 COPY를 주석처리를 하고 다시 빌드를 했으니 이 이미지가 볼륨 바인딩이 안되어있으면
  아예 리액트 화면 자체가 안나을 것입니다.

- 볼륨바인딩이 되었는데 바뀌지 않는 부분이 있어서 계속 질문을 드리고 있습니다.

부디 해결책을 알려주시면 감사하겠습니다 

0

John Ahn님의 프로필 이미지
John Ahn
지식공유자

소스에 들어가니깐  파일과 폴더만 보이고  그안에 소스는 안보이네요 ㅠ ~ 

컨테이너에 변경된 파일은 COPY 로 인해서 일어납니다. 
하지만 볼륨을 이용할떄는   컨테이너에 바뀐 코드를 이용해서 애플리케이션을 실행하는것이아닌 
로컬에 바뀐 코드를 이용해서 애플리케이션을 실행하게 됩니다.

그래서 사실 VOLUME을 이용한다면 COPY 부분을 빼버려도 앱을 돌아갑니다. 

그러기에 exec으로 컨테이너 안에 들어가서 소스가 바뀐다고 해도 
그것이 볼륨이 잘 설정되었다고 볼수는 없습니다 ~~ 

0

안근창님의 프로필 이미지
안근창
질문자

안녕하세요. 답변 주셔서 감사합니다.

제가 첫 질문에 다 내용을 써놨는데  정확히 전달이 안된 것 같아서 다시 정리해드리겠습니다.

  • vscode로 로컬쪽 코드를 열어놓고 있습니다.
  • 실습을 따라 했고 vscode에서 소스를 바꿈에도
    바뀌지 않았습니다.
  • 혹시나 해서 exec로 컨테이너 안에 들어가서
    cat 으로 열어보면 바꾼 소스가 보입니다.
  • 마지막으로 혹시나해서 exec로 들어간 컨테이너
    에서 vi로 소스 바꾸니 vscode로 열어놓은
    Local의 App.js도 내용이 바뀝니다.

혹시나해서 소스 공유드립니다.

[소스]

0

John Ahn님의 프로필 이미지
John Ahn
지식공유자

안녕하세요  

볼륨을 사용할 때   참조하는 소스코드는  로컬쪽 코드입니다.  그래서 컨테이너안에  copy된 소스가 바뀌어 있다 해도 로컬쪽 소스를 제대로 참조하고있지 않다면  자동으로 안바뀌게 됩니다.   

혹시  볼륨설정한곳 소스 올려주시겠나요???