如何配置 `ng serve` 来捕获在 Docker 容器中运行的 Angular 2 应用程序的更改?

11

我正在“dockersizing”(我希望这是正确的术语)一款现有的Angular 2应用程序,运行在angular-cli(1.0.0-beta.31)上。

我正在努力寻找一种方法,使得ng serve可以在我更新工作目录中的文件时进行捕捉,因此可以像往常一样刷新我的应用程序。否则,每当我更改文件时,我都需要运行docker-compose up --build...

编辑:我正在探索添加一个卷的想法。

以下是我的Dockerfile

# Dockerizing Angular 2 Client App
# @link: https://scotch.io/tutorials/create-a-mean-app-with-angular-2-and-docker-compose

# Create image based on the official Node 7 image from dockerhub
FROM node:7

# Create a directory where our app will be placed
RUN mkdir -p /usr/src/app

# Change directory so that our commands run inside this new directory
WORKDIR /usr/src/app

# Copy dependency definitions
COPY package.json /usr/src/app

# Install dependecies
RUN npm install

# Get all the code needed to run the app
# **EDIT**: comment out this, so I can set-up a volume
# COPY . /usr/src/app

# Expose the port the app runs in
EXPOSE 4200

# Serve the app
CMD ["npm", "start"]

这是我的 docker-compose.yml 文件:

# specify docker-compose version
version: '2'

# Define the services/containers to be run
services:
  angular2app: # name of the service
    build: ./ # specify the directory of the Dockerfile
    ports:
      - "4200:4200" # specify port forewarding
    # **EDIT**: Setting-up the volume here
    volumes:
      - .:/usr/src/app

编辑:没有音量配置时,应用程序可以成功构建和运行。设置音量后,会输出错误信息:


Building angular2app
Step 1/7 : FROM node:7
 ---> b3a95b94bd6c
Step 2/7 : RUN mkdir -p /usr/src/app
 ---> Using cache
 ---> 2afb01ffe055
Step 3/7 : WORKDIR /usr/src/app
 ---> Using cache
 ---> 44d08fdb4a19
Step 4/7 : COPY package.json /usr/src/app
 ---> Using cache
 ---> 87bb4f71c13c
Step 5/7 : RUN npm install
 ---> Using cache
 ---> ba88a0e1e480
Step 6/7 : EXPOSE 4200
 ---> Using cache
 ---> 4fddacae8486
Step 7/7 : CMD npm start
 ---> Using cache
 ---> c5ac29bf85fc
Successfully built c5ac29bf85fc
Creating minterface_angular2app_1

ERROR: for angular2app  Cannot start service angular2app: Mounts denied: closed
ERROR: Encountered errors while bringing up the project.

如何配置ng serve以便捕捉当前工作目录中的更改并重新构建我的Angular 2应用程序?

PS:我使用的是Docker for Mac,版本为1.11.1(build 7c5d5e4),在Mac(Sierra 10.12.3)上运行docker-compose


你当前的工作目录是什么?在Docker for Mac中,只有来自主机系统的少数位置可用作卷。 - Alexander Block
/Users/<my-user>/Sites/<my-project> 是我的当前工作目录。 - Kaloyan Kosev
你可以尝试从同一目录下运行 docker run --rm -ti -v $(pwd):/usr/src/app debian ls -lah 并检查输出吗?它应该像本地调用 ls -lah 一样查看访问权限。如果你在Docker上有一般问题,它应该会显示一个类似的错误信息。 - Alexander Block
@AlexanderBlock 我遇到了一个错误:docker: Error response from daemon: Mounts denied: closed. / ERRO[0013] error getting events from daemon: net/http: request canceled. 或许这是一个线索? - Kaloyan Kosev
看起来你的Docker for Mac安装出了一些问题。请尝试另一个命令:docker run --rm -ti -v /:/host debian ls -lah /host/Users,然后再尝试 docker run --rm -ti -v /:/host debian ls -lah /host/Users/<my-user>/Sites/<my-project>。如果两者都失败了,我建议重新安装Docker for Mac。 - Alexander Block
3个回答

2
我遇到了一个类似的问题。 Webpack没有监视文件的变化。 请参考https://webpack.js.org/configuration/watch/。 在webpack.common.js中,您可以添加以下内容:
watchOptions: {
   poll: 1000, // a poll interval in milliseconds
},

2
你可以使用这个npm包:https://www.npmjs.com/package/supervisor。只需使用该监管进程启动进程,然后指定它应监视哪些文件夹-w进行更改和重启即可。希望这能帮到你!

这个解决方案不能解决我的核心问题。我的实际问题是如何调整Docker配置以达到我的目标。 - Kaloyan Kosev
你使用的是哪个版本的Docker和Docker Compose?是在Windows、Mac还是Linux上? - Jacek Lawniczak
docker-compose版本为1.11.1(构建的编号为7c5d5e4),在Mac(Sierra 10.12.3)上通过Docker for Mac运行。 - Kaloyan Kosev
你能把你当前的docker-compose粘贴过来吗? - Jacek Lawniczak
让我们在聊天中继续这个讨论 - Jacek Lawniczak
显示剩余8条评论

2
这可能不是你想要的答案,但这是我们在开发工作流程中解决此问题的方法:
  1. Don't run ng serve in docker. Run it on your host. This way you avoid all the bugs of file sharing with docker. And you will hit them for sure, there are known issues with file changes on host propagating to Docker VM.

  2. Setup a reverse proxy in docker-compose that proxies requests to your backend and angular project. Most probably, you already are doing that.

    web:
      image: nginx
      ports:
        - "80:80"
      links:
        - backend
      extra_hosts:
        - "frontend:192.168.99.1"
    

    Note that, instead of linking to frontend, we specify extra_hosts to point to our host IP address.

  3. Add the IP address to your lo0 interface on host, so that it is accessible from inside docker VM.

    sudo ifconfig lo0 inet 192.168.99.1/32 add
    

    This setting doesn't persist on a restart, so you will do it again.

唯一需要注意的是选择一个合理的IP地址,以避免与您的本地网络和任何可能使用的VPN软件发生冲突。

希望这可以帮到您。


我无法实现您的建议。也许如果您分享一个完整的配置示例,包括 Dockerfiledocker-compose.yml 等等,我可能会做到。不管怎样,我仍然在想这里的最佳实践是什么。我看到 Angular 2 团队计划通过 Docker 为用户添加方便,以容器化和部署他们的 Angular 应用程序。我期待着它的到来。感谢您的回复,@Tair - Kaloyan Kosev
@KaloyanKosev,你为什么想在Docker中运行Angular应用程序?从你的配置中可以看出,你直接从Docker暴露了端口4200,为什么不在主机上只使用ng serve呢?这样你的应用程序仍然可以通过http://localhost:4200访问。 - Tair

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接