简介
如果您正在积极开发应用程序,使用Docker可以简化您的工作流程和将您的应用程序部署到生产中的过程。在开发中使用容器具有以下好处:
- 环境是一致的,这意味着您可以为项目选择所需的语言和依赖项,而无需担心系统冲突。
- 环境是隔离的,因此可以更轻松地排除故障并加入新的团队成员。
- 环境是可移植的,允许您打包代码并与他人共享。
本教程将介绍如何使用Docker为Node.js应用程序)设置开发环境。您将使用Docker Compose)创建两个容器-一个用于节点应用程序,另一个用于MongoDB.数据库由于该应用程序可以与Node和MongoDB一起使用,因此您的设置将执行以下操作:
- 将宿主机上的应用程序代码与容器中的代码同步,便于开发过程中的更改。
- 确保对应用程序代码的更改无需重新启动即可生效。
- 为应用程序数据创建受用户和密码保护的数据库。
- 将此数据持久化。
在本教程结束时,您将拥有一个在Docker Containers上运行的鲨鱼信息应用程序:
前提条件
要遵循本教程,您需要:
- 运行Ubuntu 18.04的开发服务器,以及具有
sudo
权限和活动防火墙的非超级用户。有关如何设置这些的指导,请参阅初始服务器设置guide. - 您的服务器上安装了Docker,遵循如何在Ubuntu 18.04.上安装和使用Docker》中的 步骤1和2**
- Docker Compose安装在您的服务器上,按照如何在Ubuntu 18.04.上安装Docker Compose》中的 步骤1** 操作
第一步-克隆项目并修改依赖关系
构建此安装程序的第一步将是克隆项目代码并修改其package.json
文件,该文件包含项目的依赖项。您将把nodemon
添加到项目的devDependencies
,中,指定您将在开发期间使用它。使用nodemon
运行应用程序可以确保在您更改代码时自动重启应用程序。
首先,从DigitalOcean社区GitHub账号克隆[nodejs-mongo-mongoose
https://github.com/do-community).该存储库包括如何将MongoDB与您的节点Application,集成》中描述的设置中的代码,其中解释了如何使用Mongoose.)将MongoDB数据库与现有的节点应用程序集成
将仓库克隆到名为node_project
的目录下:
1git clone https://github.com/do-community/nodejs-mongo-mongoose.git node_project
导航到node_project
目录:
1cd node_project
使用Nan
或您喜欢的编辑器打开工程的Package.json
文件:
1nano package.json
在项目依赖项下方和右大括号上方,创建一个新的devDependencies
对象,其中包含nodemon
:
1[label ~/node_project/package.json]
2...
3"dependencies": {
4 "ejs": "^2.6.1",
5 "express": "^4.16.4",
6 "mongoose": "^5.4.10"
7 },
8 "devDependencies": {
9 "nodemon": "^1.18.10"
10 }
11}
编辑完成后,保存并关闭文件。如果您使用的是Nan
,请按CTRL+X
,然后按Y
,然后按Enter
。
准备好项目代码并修改其依赖项后,您可以继续为容器化工作流重构代码。
Step 2 -配置应用使用容器
为容器化工作流修改应用程序意味着使代码更加模块化。容器提供了环境之间的可移植性,您的代码应该通过尽可能与底层操作系统解耦来反映这一点。为了实现这一点,您需要重构代码,以便更好地利用Node的process.env属性。这将返回一个对象,其中包含有关运行时用户环境的信息。可以在代码中使用此对象,以便在运行时通过环境变量动态分配配置信息。
从您的主应用程序入口点app.js
开始。打开文件:
1nano app.js
在内部,您将看到一个[constant](https://andsky.com/tech/tutorials/understanding-variables-scope-hoisting-in-javascript#constants),‘端口的定义,以及一个使用此常量指定应用程序将侦听的端口的[
function](https://expressjs.com/en/4x/api.html app.listen)’端口:
1[label ~/home/node_project/app.js]
2...
3const port = 8080;
4...
5app.listen(port, function () {
6 console.log('Example app listening on port 8080!');
7});
重新定义port
常量,以允许在运行时使用cess.env
对象进行动态分配。对常量定义和listen
函数进行如下更改:
1[label ~/home/node_project/app.js]
2...
3const port = process.env.PORT || 8080;
4...
5app.listen(port, function () {
6 console.log(`Example app listening on ${port}!`);
7});
您的新常量定义使用运行时传入的值或8080
动态分配port
。类似地,您已经重写了literal](https://andsky.com/tech/tutorials/how-to-work-with-strings-in-javascript# string-literals-and-string-values),‘函数,以使用[模板listen
,该模板将在侦听连接时插入端口值。由于您将在其他地方映射您的端口,因此这些修订将使您不必随着环境的变化而不断修订此文件。
编辑完成后,保存并关闭该文件。
接下来,您将修改数据库连接信息以删除所有配置凭据。打开db.js
文件,其中包含以下信息:
1nano db.js
目前,该文件执行以下操作:
- 导入Mongoose,即您用来为应用程序数据创建模式和模型的_Object Document Mapper_(ODM)。
- 将数据库凭据设置为常量,包括用户名和密码。
- 使用
mongoose.Connect
method.连接到数据库
关于文件的更多信息,请参考如何将mongodb与您的节点3集成]的步骤Application.
修改文件的第一步是重新定义包含敏感信息的常量。目前,这些常量如下所示:
1[label ~/node_project/db.js]
2...
3const MONGO_USERNAME = 'sammy';
4const MONGO_PASSWORD = 'your_password';
5const MONGO_HOSTNAME = '127.0.0.1';
6const MONGO_PORT = '27017';
7const MONGO_DB = 'sharkinfo';
8...
您可以使用cess.env
对象来捕获这些常量的运行时值,而不是对这些信息进行硬编码。将块修改为如下所示:
1[label ~/node_project/db.js]
2...
3const {
4 MONGO_USERNAME,
5 MONGO_PASSWORD,
6 MONGO_HOSTNAME,
7 MONGO_PORT,
8 MONGO_DB
9} = process.env;
10...
编辑完成后,保存并关闭文件。
此时,您已经修改了db.js
以处理应用程序的环境变量,但您仍然需要一种方法将这些变量传递给您的应用程序。创建一个.env
文件,其中的值可以在运行时传递给您的应用程序。
打开文件:
1nano .env
该文件将包括您从db.js
中删除的信息:您的应用程序数据库的用户名和密码,以及端口设置和数据库名称。请记住使用您自己的信息更新此处列出的用户名、密码和数据库名称:
1[label ~/node_project/.env]
2MONGO_USERNAME=sammy
3MONGO_PASSWORD=your_password
4MONGO_PORT=27017
5MONGO_DB=sharkinfo
注意,您已经移除 原来出现在db.js
中的host设置。现在,您将在Docker合成文件级别定义您的主机,以及有关您的服务和容器的其他信息。
编辑完成后保存并关闭此文件。
因为您的.env
文件包含敏感信息,所以您需要确保它包含在项目的.dockernore
和.gitignore
文件中,这样它就不会复制到版本控制或容器中。
打开.dockerignore
文件:
1nano .dockerignore
将以下行添加到文件的底部:
1[label ~/node_project/.dockerignore]
2...
3.gitignore
4.env
编辑完成后,保存并关闭文件。
该存储库中的.gitignore
文件已经包含.env
,但请检查是否存在:
1nano .gitignore
1[label ~~/node_project/.gitignore]
2...
3.env
4...
至此,您已经成功地从项目代码中提取了敏感信息,并采取措施控制了这些信息的复制方式和位置。现在,您可以添加到数据库连接代码中,以针对容器化工作流对其进行优化。
第三步-修改数据库连接设置
下一步是通过添加代码来处理应用程序无法连接到数据库的情况,从而使数据库连接方法更加健壮。在使用Compose处理容器时,将这种级别的弹性引入应用程序代码是推荐做法。
打开db.js
进行编辑:
1nano db.js
注意前面添加的代码,以及用于Mongo的连接URI的url
常量和Mongooseconnect
方法:
1[label ~/node_project/db.js]
2...
3const {
4 MONGO_USERNAME,
5 MONGO_PASSWORD,
6 MONGO_HOSTNAME,
7 MONGO_PORT,
8 MONGO_DB
9} = process.env;
10
11const url = `mongodb://${MONGO_USERNAME}:${MONGO_PASSWORD}@${MONGO_HOSTNAME}:${MONGO_PORT}/${MONGO_DB}?authSource=admin`;
12
13mongoose.connect(url, {useNewUrlParser: true});
目前,您的Connect
方法接受一个选项,该选项告诉Mongoose使用Mongo的新URL parser.您可以向此方法添加选项以定义重新连接尝试的参数。除了新的URL解析器选项外,还可以通过创建包含相关信息的options
常量来实现这一点。在您的Mongo常量下面,为options
常量添加以下定义:
1[label ~/node_project/db.js]
2...
3const {
4 MONGO_USERNAME,
5 MONGO_PASSWORD,
6 MONGO_HOSTNAME,
7 MONGO_PORT,
8 MONGO_DB
9} = process.env;
10
11const options = {
12 useNewUrlParser: true,
13 reconnectTries: Number.MAX_VALUE,
14 reconnectInterval: 500,
15 connectTimeoutMS: 10000,
16};
17...
reConnectTries
选项告诉Mongoose继续无限期地尝试连接,而reConnectInterval
则以毫秒为单位定义连接间隔时间。ConnectTimeoutMS
定义Mongo驱动在连接尝试失败之前等待的时间为10秒。
现在您可以在MongooseConnect
方法中使用新的options
常量来微调您的Mongoose连接设置。您还将添加一个promise来处理潜在的连接错误。
目前,Mongoose的Connect
方法如下所示:
1[label ~/node_project/db.js]
2...
3mongoose.connect(url, {useNewUrlParser: true});
删除现有的connect
方法,并将其替换为以下代码,其中包括options
常量和一个promise:
1[label ~/node_project/db.js]
2...
3mongoose.connect(url, options).then( function() {
4 console.log('MongoDB is connected');
5})
6 .catch( function(err) {
7 console.log(err);
8});
在成功连接的情况下,您的函数会记录相应的消息;否则它会catch
并记录错误,以便您进行故障排除。
完成的文件将如下所示:
1[label ~/node_project/db.js]
2const mongoose = require('mongoose');
3
4const {
5 MONGO_USERNAME,
6 MONGO_PASSWORD,
7 MONGO_HOSTNAME,
8 MONGO_PORT,
9 MONGO_DB
10} = process.env;
11
12const options = {
13 useNewUrlParser: true,
14 reconnectTries: Number.MAX_VALUE,
15 reconnectInterval: 500,
16 connectTimeoutMS: 10000,
17};
18
19const url = `mongodb://${MONGO_USERNAME}:${MONGO_PASSWORD}@${MONGO_HOSTNAME}:${MONGO_PORT}/${MONGO_DB}?authSource=admin`;
20
21mongoose.connect(url, options).then( function() {
22 console.log('MongoDB is connected');
23})
24 .catch( function(err) {
25 console.log(err);
26});
编辑完成后,保存并关闭该文件。
现在,您已经为应用程序代码添加了弹性,以处理应用程序可能无法连接到数据库的情况。准备好这些代码后,您可以继续使用Compose定义您的服务。
第四步-用Docker组合定义服务
重构代码后,您就可以编写带有服务定义的docker-compose.yml
文件了。A_SERVICE_IN COMPAGE是一个运行的容器,服务定义--您将包含在您的docker-compose.yml
文件中--包含每个容器镜像将如何运行的信息。组合工具允许您定义多个服务来构建多容器应用程序。
在定义服务之前,您将向项目中添加一个名为wait-for
的工具,以确保应用程序仅在数据库启动任务完成后尝试连接数据库。此包装器脚本使用netcat
轮询特定主机和端口是否接受TCP连接。使用它可以通过测试数据库是否准备好接受连接来控制应用程序连接到数据库的尝试。
打开名为Wait-for.sh
的文件:
1nano wait-for.sh
在文件中输入以下代码以创建轮询函数:
1[label ~/node_project/app/wait-for.sh]
2#!/bin/sh
3
4# original script: https://github.com/eficode/wait-for/blob/master/wait-for
5
6TIMEOUT=15
7QUIET=0
8
9echoerr() {
10 if [ "$QUIET" -ne 1 ]; then printf "%s\n" "$*" 1>&2; fi
11}
12
13usage() {
14 exitcode="$1"
15 cat << USAGE >&2
16Usage:
17 $cmdname host:port [-t timeout] [-- command args]
18 -q | --quiet Do not output any status messages
19 -t TIMEOUT | --timeout=timeout Timeout in seconds, zero for no timeout
20 -- COMMAND ARGS Execute command with args after the test finishes
21USAGE
22 exit "$exitcode"
23}
24
25wait_for() {
26 for i in `seq $TIMEOUT` ; do
27 nc -z "$HOST" "$PORT" > /dev/null 2>&1
28
29 result=$?
30 if [ $result -eq 0 ] ; then
31 if [ $# -gt 0 ] ; then
32 exec "$@"
33 fi
34 exit 0
35 fi
36 sleep 1
37 done
38 echo "Operation timed out" >&2
39 exit 1
40}
41
42while [ $# -gt 0 ]
43do
44 case "$1" in
45 *:* )
46 HOST=$(printf "%s\n" "$1"| cut -d : -f 1)
47 PORT=$(printf "%s\n" "$1"| cut -d : -f 2)
48 shift 1
49 ;;
50 -q | --quiet)
51 QUIET=1
52 shift 1
53 ;;
54 -t)
55 TIMEOUT="$2"
56 if [ "$TIMEOUT" = "" ]; then break; fi
57 shift 2
58 ;;
59 --timeout=*)
60 TIMEOUT="${1#*=}"
61 shift 1
62 ;;
63 --)
64 shift
65 break
66 ;;
67 --help)
68 usage 0
69 ;;
70 *)
71 echoerr "Unknown argument: $1"
72 usage 1
73 ;;
74 esac
75done
76
77if [ "$HOST" = "" -o "$PORT" = "" ]; then
78 echoerr "Error: you need to provide a host and port to test."
79 usage 2
80fi
81
82wait_for "$@"
添加完代码后,保存并关闭该文件。
使脚本可执行:
1chmod +x wait-for.sh
接下来,打开docker-compose.yml
文件:
1nano docker-compose.yml
首先,通过在文件中添加以下代码来定义nodejs
应用服务:
1[label ~/node_project/docker-compose.yml]
2version: '3'
3
4services:
5 nodejs:
6 build:
7 context: .
8 dockerfile: Dockerfile
9 image: nodejs
10 container_name: nodejs
11 restart: unless-stopped
12 env_file: .env
13 environment:
14 - MONGO_USERNAME=$MONGO_USERNAME
15 - MONGO_PASSWORD=$MONGO_PASSWORD
16 - MONGO_HOSTNAME=db
17 - MONGO_PORT=$MONGO_PORT
18 - MONGO_DB=$MONGO_DB
19 ports:
20 - "80:8080"
21 volumes:
22 - .:/home/node/app
23 - node_modules:/home/node/app/node_modules
24 networks:
25 - app-network
26 command: ./wait-for.sh db:27017 -- /home/node/app/node_modules/.bin/nodemon app.js
nodejs
服务定义包括以下选项:
build
:这定义了配置选项,包括context
和dockerfile
,当Compose构建应用程序映像时将应用这些选项。如果你想使用像Docker Hub这样的注册表中的现有镜像,你可以使用image
指令,其中包含关于你的用户名、存储库和镜像标签的信息。context
:这定义了镜像构建的构建上下文-在本例中,是当前项目目录。dockerfile
:指定当前项目目录中的Dockerfile
,因为Compose将使用该文件构建应用程序映像。有关此文件的详细信息,请参阅如何使用Docker构建Node.js应用程序。image
、container_name
:这些将名称应用于图像和容器。restart
:定义重启策略。默认值为no
,但您已将容器设置为除非停止否则将重新启动。env_file
:这告诉Compose你想从一个名为.env
的文件中添加环境变量,该文件位于你的构建上下文中。environment
:使用此选项可以添加您在.env
文件中定义的Mongo连接设置。请注意,您没有将NODE_ENV
设置为development
,因为如果没有设置NODE_ENV
,这是Express的[默认](https://github.com/expressjs/express/blob/dc 538 f6 e810 bd 462 c98 ee 7 e6 ae 24 c64 d4 b1 da 93/lib/application.js# L71)行为。迁移到生产环境时,您可以将其设置为production
以[启用视图缓存和更少的详细错误消息](https://expressjs.com/en/advanced/best-practice-performance.html set-node_env-to-production)。
还要注意,您已经指定了db
数据库容器作为主机,如步骤2.]中所讨论的
ports
:将主机上的80
端口映射到容器上的8080
端口。volumes
:这里包含两种挂载类型: -第一个是绑定mount,将您在宿主机上的应用代码挂载到容器上的/home/node/app
目录中。这将有助于快速开发,因为您对主机代码所做的任何更改都将立即填充到容器中。 -第二个是命名volume,node_modes
。当Docker运行应用程序Dockerfile
中列出的npm install
指令时,npm
会在容器上创建一个新的node_modules
目录,其中包含运行应用程序所需的包。但是,您刚刚创建的绑定挂载将隐藏这个新创建的node_modes
目录。由于主机上的node_modes
为空,绑定会将一个空目录映射到容器,覆盖新的node_modes
目录,并阻止您的应用程序启动。命名为node_modes
的卷通过持久化/home/node/app/node_modes
目录的内容并将其挂载到容器中,隐藏绑定来解决此问题。
<$>[注] 使用此方法时请记住以下几点 :
- 您的绑定将把容器上的
node_modules
目录的内容挂载到主机上,这个目录将由root
拥有,因为命名卷是由Docker创建的。 - 如果主机上已有
node_modules
目录,它将覆盖容器上创建的node_modules
目录。在本教程中构建的设置假定您 ** 没有 预先存在的node_modules
目录,并且您不会在主机上使用npm
。这与应用程序开发的十二因素方法保持一致,该方法最大限度地减少了执行环境之间的依赖性。
<$>
networks
:指定您的应用程序服务将加入app-network
网络,您将在文件底部定义该网络。command
:设置Compose运行镜像时应该执行的命令。请注意,这将覆盖您在我们的应用程序Dockerfile
中设置的CMD
指令。在这里,您正在使用wait-for
脚本运行应用程序,该脚本将轮询端口27017
上的db
服务,以测试数据库服务是否就绪。一旦就绪测试成功,脚本将执行您设置的命令/home/node/app/node_modules/.bin/nodemon app.js
,以nodemon
启动应用程序。这将确保您将来对代码所做的任何更改都可以重新加载,而无需重新启动应用程序。
接下来,通过在应用服务定义下面添加以下代码来创建db
服务:
1[label ~/node_project/docker-compose.yml]
2...
3 db:
4 image: mongo:4.1.8-xenial
5 container_name: db
6 restart: unless-stopped
7 env_file: .env
8 environment:
9 - MONGO_INITDB_ROOT_USERNAME=$MONGO_USERNAME
10 - MONGO_INITDB_ROOT_PASSWORD=$MONGO_PASSWORD
11 volumes:
12 - dbdata:/data/db
13 networks:
14 - app-network
为nodejs
服务定义的一些设置保持不变,但您还对Image
、Environment
和volumes
定义进行了以下更改:
Image
:为了创建该服务,Compose会拉取4.1.8-xiial
[Mongo镜像](来自Docker Hub的https://hub.docker.com/_/mongo))。您正在固定一个特定的版本,以避免将来在Mongo映像更改时可能发生的冲突。有关版本钉住的更多信息,请参阅DockerFILE BEST practices.]上的Docker文档MONGO_INITDB_ROOT_USERNAME
,MONGO_INITDB_ROOT_PASSWORD
:mongo
镜像使这些环境variables]可用,以便您可以修改数据库实例的初始化。MONGO_INITDB_ROOT_USERNAME
和MONGO_INITDB_ROOT_PASSWORD
共同在admin
鉴权数据库中创建一个root
用户,并确保容器启动时开启鉴权。您已经使用.env
文件中的值设置了MONGO_INITDB_ROOT_USERNAME
和MONGO_INITDB_ROOT_PASSWORD
,您可以使用env_file
选项将该文件传递给db
服务。这样做意味着您的sammy
应用程序用户将是数据库实例上的[root
user](https://docs.mongodb.com/manual/reference/built-in-roles/ root)],可以访问该角色的所有管理和操作权限。在生产环境中工作时,您需要创建具有适当作用域权限的专用应用程序用户。
<$>[备注] 注意: 请记住,如果您在已有数据目录的情况下启动容器,这些变量将不会生效。 <$>
dbdata:/data/db
:命名卷dbdata
会持久化Mongo的[默认数据数据/directory](https://docs.mongodb.com/manual/reference/configuration-options/#storage.dbPath),/db
中的数据。这将确保您在停止或删除容器时不会丢失数据。
db
服务也通过networks
选项添加到了app-network
网络中。
最后一步,将卷和网络定义添加到文件底部:
1[label ~/node_project/docker-compose.yml]
2...
3networks:
4 app-network:
5 driver: bridge
6
7volumes:
8 dbdata:
9 node_modules:
用户自定义网桥网络app-network
支持您的容器之间的通信,因为它们位于同一个Docker守护程序主机上。这简化了应用程序内的通信和通信,因为它打开了同一网桥网络上的容器之间的所有端口,而不向外部世界公开任何端口。这样,您的db
和nodejs
容器就可以相互通信了,您只需要公开80
端口就可以前端访问应用程序。
您的顶级volumes
密钥定义了卷dbdata
和node_modes
。当Docker创建卷时,卷的内容存储在由Docker管理的主机文件系统/var/lib/docker/volures/
的一部分中。每个卷的内容都存储在/var/lib/docker/volvures/
下的一个目录中,并挂载到使用该卷的任何容器中。如此一来,即使您移除并重新创建了db
容器,您的用户将创建的Shark信息数据也会保留在dbdata
卷中。
完成的docker-compose.yml
文件如下所示:
1[label ~/node_project/docker-compose.yml]
2version: '3'
3
4services:
5 nodejs:
6 build:
7 context: .
8 dockerfile: Dockerfile
9 image: nodejs
10 container_name: nodejs
11 restart: unless-stopped
12 env_file: .env
13 environment:
14 - MONGO_USERNAME=$MONGO_USERNAME
15 - MONGO_PASSWORD=$MONGO_PASSWORD
16 - MONGO_HOSTNAME=db
17 - MONGO_PORT=$MONGO_PORT
18 - MONGO_DB=$MONGO_DB
19 ports:
20 - "80:8080"
21 volumes:
22 - .:/home/node/app
23 - node_modules:/home/node/app/node_modules
24 networks:
25 - app-network
26 command: ./wait-for.sh db:27017 -- /home/node/app/node_modules/.bin/nodemon app.js
27
28 db:
29 image: mongo:4.1.8-xenial
30 container_name: db
31 restart: unless-stopped
32 env_file: .env
33 environment:
34 - MONGO_INITDB_ROOT_USERNAME=$MONGO_USERNAME
35 - MONGO_INITDB_ROOT_PASSWORD=$MONGO_PASSWORD
36 volumes:
37 - dbdata:/data/db
38 networks:
39 - app-network
40
41networks:
42 app-network:
43 driver: bridge
44
45volumes:
46 dbdata:
47 node_modules:
完成编辑后保存并关闭文件。
服务定义就绪后,您就可以启动应用程序了。
第五步-测试应用程序
准备好docker-compose.yml
文件后,您可以使用docker-compose up
命令创建您的服务。您还可以通过使用docker-compose down
.]停止和移除容器来测试您的数据是否会持久存在
首先构建容器镜像并创建服务,运行带有-d
标志的docker-compose up
,然后在后台运行nodejs
和db
容器:
1docker-compose up -d
输出确认您的服务已创建:
1[secondary_label Output]
2...
3Creating db ... done
4Creating nodejs ... done
您还可以通过显示服务的日志输出来获取有关启动进程的更详细信息:
1docker-compose logs
如果一切正常启动,则输出如下:
1[secondary_label Output]
2...
3nodejs | [nodemon] starting `node app.js`
4nodejs | Example app listening on 8080!
5nodejs | MongoDB is connected
6...
7db | 2019-02-22T17:26:27.329+0000 I ACCESS [conn2] Successfully authenticated as principal sammy on admin
您还可以使用docker-Compose ps
:]检查容器的状态
1docker-compose ps
输出表明您的容器正在运行:
1[secondary_label Output]
2 Name Command State Ports
3----------------------------------------------------------------------
4db docker-entrypoint.sh mongod Up 27017/tcp
5nodejs ./wait-for.sh db:27017 -- ... Up 0.0.0.0:80->8080/tcp
当您的服务正在运行时,您可以在浏览器中访问http://your_server_ip
:
点击获取鲨鱼信息 按钮,进入一个带有条目表格的页面,您可以在其中提交鲨鱼名称和该鲨鱼的一般特征的描述:
的特征
在表格中,添加您选择的鲨鱼。出于演示的目的,在鲨鱼名称 字段中添加Megalodon Shark
,在** 鲨鱼字符** 字段中添加Ancient
:
点击提交 按钮,您将看到一个包含该鲨鱼信息的页面:
的Shark输出
作为最后一步,测试如果删除数据库容器,您刚才输入的数据是否会持续存在。
回到您的终端,键入以下命令以停止并删除您的容器和网络:
1docker-compose down
请注意,您没有包含--volumes
选项;因此,您的dbdata
卷不会被删除。
以下输出确认您的容器和网络已被删除:
1[secondary_label Output]
2Stopping nodejs ... done
3Stopping db ... done
4Removing nodejs ... done
5Removing db ... done
6Removing network node_project_app-network
重新创建容器:
1docker-compose up -d
现在回到鲨鱼信息表:
进入你选择的一只新鲨鱼。本例将使用鲸鲨
和大鲨鱼
:
单击提交 后,您会注意到,新的Shark已添加到数据库的Shark集合中,并且不会丢失您已经输入的数据:
您的应用程序现在运行在已启用数据持久化和代码同步的Docker容器上。
结论
通过学习本教程,您已经使用Docker Containers为您的Node应用程序创建了开发设置。通过提取敏感信息并将应用程序的状态与应用程序代码分离,您的项目变得更加模块化和可移植。您还配置了一个样板docker-compose.yml
文件,您可以根据开发需求和要求的变化进行修改。
在开发过程中,您可能会有兴趣了解更多有关为容器化和云Native工作流]设计应用程序的信息。有关这些主题的更多信息,请参阅构建Kubernetes应用程序和现代化Kubernetes应用程序]。
要了解本教程中使用的代码的更多信息,请参阅如何使用Docker构建Node.js应用程序》和如何将MongoDB与您的节点Application.集成使用容器部署Node应用的相关信息,请参阅如何使用NGINX保护容器化的Node.js应用》、《让我们加密吧》和Docker Compose.