我已经设置了一个docker django容器,并使用教程here使用build构建了它的图像。本教程展示了如何制作基本的django应用程序并将应用程序安装到 “/ code” ,据我所知,它包含在数据卷中。
但是,我想了解我将如何更新和开发此代码,并能够发布/部署它。因为当我进行提交时,它不会考虑代码中的任何更改,因为它是数据卷的一部分。
有什么方法可以让django代码成为图像的一部分,或者用更新的代码更新图像?
答案 0 :(得分:4)
以我的经验,Docker有两个用途:
在开发代码时,应该挂载源代码/卷,以便您的更改始终反映在容器内。当您要将应用打包打包以进行部署时,应将源COPY
放入容器并将其适当打包。
这是一个docker-compose文件,我用来(1)建立要开发的映像,(2)开发我的代码,(3)交付它(我使用的是Spring Boot):
version: '3.7'
services:
dev:
image: '${MVN_BUILDER}'
container_name: '${CONTAINER_NAME}'
ports:
- '8080:8080'
volumes:
- './src:/build/src'
- './db:/build/db'
- './target:/build/target'
- './logs:/build/logs'
command: 'mvn spring-boot:run -Drun.jvmArguments="-Xmx512m" -Dmaven.test.skip=true'
deploy:
build:
context: .
dockerfile: Dockerfile-Deploy
args:
MVN_BUILDER: '${MVN_BUILDER}'
image: '${DEPLOYMENT_IMAGE}'
container_name: '${CONTAINER_NAME}'
ports:
- '8080:8080'
maven:
build:
context: .
dockerfile: Dockerfile
image: '${MVN_BUILDER}'
container_name: '${CONTAINER_NAME}'
docker-compose build maven
来构建我的基本映像。这是必需的,以便当我在容器中运行代码时,所有依赖项都安装在映像中。用于此目的的Dockerfile实际上复制到映像中的pom.xml
并下载应用程序所需的依赖项。请注意,只要依赖项发生更改,就需要执行此操作。这是用于构建maven
服务中引用的映像的Dockerfile:### BUILD a maven builder. This will contain all mvn dependencies and act as an abstraction for all mvn goals
FROM maven:3.5.4-jdk-8-alpine as builder
#Copy Custom Maven settings
#COPY settings.xml /root/.m2/
# create app folder for sources
RUN mkdir -p /build
RUN mkdir -p /build/logs
# The WORKDIR instruction sets the working directory for any RUN, CMD, ENTRYPOINT, COPY and ADD instructions that follow it in the Dockerfile.
WORKDIR /build
COPY pom.xml /build
#Download all required dependencies into one layer
RUN mvn -B dependency:go-offline dependency:resolve-plugins
RUN mvn clean install
接下来,我将运行docker-compose up dev
以启动我的dev
服务并开始开发我的应用程序。该服务将我的代码安装到容器中,并使用Maven启动Spring Boot应用程序。每当我更改代码时,Spring Boot都会重新启动服务器,并反映出我的更改。
最后,一旦我对我的应用程序感到满意,我将构建一个映像,该映像将我的应用程序打包为使用docker-compose build deploy
进行部署。我使用两个阶段的构建过程,首先将源复制到容器中并打包为Jar
进行部署,然后将Jar
放入第二阶段,我可以简单地运行{{1} }(在容器中)启动我的应用程序,并且第一阶段已删除。而已!现在,您可以在安装了Docker的任何地方部署此最新映像。
这是最后一个Dockerfile(Dockerfile-Deploy)的样子:
java -jar build/app.jar
将ARG MVN_BUILDER
### Stage 1 - BUILD image
FROM $MVN_BUILDER as builder
COPY src /build/src
RUN mvn clean package -PLOCAL
### Stage 2 - Deploy Jar
FROM openjdk:8
RUN mkdir -p /build
COPY --from=builder /build/target/*.jar /build/app.jar
EXPOSE 8080
ENTRYPOINT ["java","-jar","build/app.jar"]
文件放在与.env
文件相同的目录中。我使用它来抽象图像/容器名称,并在需要新图像时将版本号简单地放在一个位置。
docker-compose
答案 1 :(得分:0)
如果您想更新图片,可以说由于您的应用程序代码更改,您在构建图片时使用COPY
,因此在Dockerfile
中您可以执行类似
COPY /you/code/on/the/host /var/www
另请参阅我对“卷”和图像构建https://stackoverflow.com/a/39314602/3625317的回答,以阐明构建中缺少代码的原因
答案 2 :(得分:0)
我认为现在回答您的问题为时已晚,但是,这对其他伸出援手的人可能是有益的。
您提到的教程对于初学者来说有些棘手,因此,我对结构进行了一些更改。我假设您有一个Docker注册表帐户(例如Dockerhub),用于将映像发布到该帐户。如果要访问远程主机上的图像,这是必需的(可以复制实际的图像文件,但不建议这样做)。
假设您要使用Django创建一个网站并对其进行dockerize,首先,您需要执行以下操作:
django-admin startproject samplesite
它将创建一个包含以下内容的目录samplesite
(我添加了requirements.txt):
db.sqlite3 manage.py requirements.txt samplesite
对于Dockerfile
,如您所见,与Dockerfile
相比,没有任何改变。
FROM python:3
ENV PYTHONUNBUFFERED 1
RUN mkdir /code
WORKDIR /code
COPY requirements.txt /code/
RUN pip install -r requirements.txt
COPY . /code/
但是对于docker-compose.yml
:
version: '3'
services:
db:
image: postgres
web:
build: .
image: yourUserNameOnDockerHub/mywebsite:0.1 # this line is added
command: python manage.py runserver 0.0.0.0:8000
#volumes:
# - .:/code
ports:
- "8000:8000"
depends_on:
- db
docker-compose.yml
也几乎与本教程中提到的相同,只是注释了体积,并添加了一行image: mywebsite:0.1
。这行代码使我们可以跟踪构建的映像并在需要时进行部署。卷安装与无关,与您编写的代码无关,它被放置在其中取出 Django更改的动态内容(sqlite,上传的文件等)。
如果您第一次运行docker-compose up
,则一切正常,但是,由于添加了新行,因此在您第一次更改代码后,所做的更改将不会反映在运行的容器中。这是因为compose会在每个docker-compose up
上寻找mywebsite:0.1
(已经存在),并且不会构建新的映像,而是基于旧映像创建容器。由于我们需要该图像名称和标签来发布/部署我们的图像,因此我们需要使用:
docker-compose up --build
它将重新构建反映了更改的图像 。每次进行一些更改时,都运行它,并创建一个新的可见图像(请注意,尽管名称和标记保持不变,但图像ID的更改表明这是一个新图像):
$ docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
yourUserNameOnDockerHub/mywebsite 0.1 033c9d2bfac0 7 seconds ago 974MB
如果您已在Dockerhub(或任何其他注册表)上设置了帐户,则可以发布该映像以供以后使用或部署在远程服务器上:
docker push yourUserNameOnDockerHub/mywebsite:01
如果要将其部署在远程主机上并想再次使用docker-compose,只需将docker-compose.yml
更改为:
version: '3'
services:
db:
image: postgres
web:
image: yourUserNameOnDockerHub/mywebsite:0.1
command: python manage.py runserver 0.0.0.0:8000
#volumes:
# - .:/code
ports:
- "8000:8000"
depends_on:
- db
请注意,build: .
行已删除(因为我们仅将其运行)。在本地进行开发时,每当您运行docker-compose up --build
时,都将创建并标记一个新映像,并且基于该映像的容器将在compose堆栈中运行。如果您认为自己对所做的更改感到满意,请按照发布步骤将其发布到服务器上。
答案 3 :(得分:-1)
在tutorial的第9步中设置了音量。该卷将链接当前目录和容器/code
目录。换句话说,它们将是相同的。
因此,对本地文件的任何更新都将更改容器中的文件。请记住,您需要重新启动应用,以便进行更改。
在部署映像之前,您需要创建第二个docker compose文件。此文件将删除卷,因此代码将保留在容器内,并且不会从外部更改。您可以按照docker compose documentation中提供的步骤进行操作。