基于docker容器化部署微服务

前言

在笔者系列文章中微服务配置隔离已经完成服务之间的配置隔离,服务整体来说是已经通了。

为了方便后续测试已经环境统一,笔者本章节会对服务进行容器化部署。由于服务器性能问题,本次部署采用maven完成镜像构建,结合docker-compose完成容器的创建。

容器化创建步骤

服务器放开2376 端口

我们后续的镜像创建需要基于2376端口,所以我们需要执行下面这段命令,对docker.service进行编辑

go 复制代码
vim /lib/systemd/system/docker.service

可以看到笔者在截图位置处增加了一行-H tcp://0.0.0.0:2376 -H unix:///var/run/docker.sock

完成后重启docker服务并开放2376端口(因为笔者服务器是阿里云服务器所以这一步相对方便一些,就不多做介绍了)

go 复制代码
systemctl daemon-reload
systemctl restart docker.service

为了测试连通性,我们在本地键入

go 复制代码
 curl http://ip:2376/info

若输出下面这样一段文字,则说明当前设置生效了

go 复制代码
{"ID":"IIPN:J265:YCRR:EQVR:FTPY:GBUK:VWES:MWJU:6TBH:NSFP:L7BU:K3RJ","Containers":6,"ContainersRunning":6,"ContainersPaused":0,"ContainersStopped":0,"Images":56,"Driver":"overlay2","DriverStatus":[["Backing Filesystem","extfs"],["Supports d_
type","true"],["Native Overlay Diff","false"],["userxattr","false"]],"Plugins":{"Volume":["local"],"Network":["bridge","host","ipvlan","macvlan","null","overlay"],"Authorization":null,"Log":["awslogs","fluentd","gcplogs","gelf","journald","
json-file","local","logentries","splunk","syslog"]},"MemoryLimit":true,"SwapLimit":true,"KernelMemory":true,"KernelMemoryTCP":true,"CpuCfsPeriod":true,"CpuCfsQuota":true,"CPUShares":true,"CPUSet":true,"PidsLimit":true,"IPv4Forwarding":true,
"BridgeNfIptables":true,"BridgeNfIp6tables":true,"Debug":false,"NFd":74,"OomKillDisable":true,"NGoroutines":72,"SystemTime":"2023-02-05T17:56:16.36473356+08:00","LoggingDriver":"json-file","CgroupDriver":"cgroupfs","CgroupVersion":"1","NEve
ntsListener":0,"KernelVersion":"4.19.91-24.1.al7.x86_64","OperatingSystem":"Alibaba Cloud Linux (Aliyun Linux) 2.1903 LTS (Hunting Beagle)","OSVersion":"2.1903","OSType":"linux","Architecture":"x86_64","IndexServerAddress":"https://index.do
cker.io/v1/","RegistryConfig":{"AllowNondistributableArtifactsCIDRs":[],"AllowNondistributableArtifactsHostnames":[],"InsecureRegistryCIDRs":["127.0.0.0/8"],"IndexConfigs":{"docker.io":{"Name":"docker.io","Mirrors":["https://fy707np5.mirror
.aliyuncs.com/"],"Secure":true,"Official":true}},"Mirrors":["https://fy707np5.mirror.aliyuncs.com/"]},"NCPU":1,"MemTotal":2043502592,"GenericResources":null,"DockerRootDir":"/var/lib/docker","HttpProxy":"","HttpsProxy":"","NoProxy":"","Name
":"iZ8vb7bhe4b8nhhhpavhwpZ","Labels":[],"ExperimentalBuild":false,"ServerVersion":"20.10.23","Runtimes":{"io.containerd.runc.v2":{"path":"runc"},"io.containerd.runtime.v1.linux":{"path":"runc"},"runc":{"path":"runc"}},"DefaultRuntime":"runc
","Swarm":{"NodeID":"","NodeAddr":"","LocalNodeState":"inactive","ControlAvailable":false,"Error":"","RemoteManagers":null},"LiveRestoreEnabled":false,"Isolation":"","InitBinary":"docker-init","ContainerdCommit":{"ID":"5b842e528e99d4d4c1686
467debf2bd4b88ecd86","Expected":"5b842e528e99d4d4c1686467debf2bd4b88ecd86"},"RuncCommit":{"ID":"v1.1.4-0-g5fd4c4d","Expected":"v1.1.4-0-g5fd4c4d"},"InitCommit":{"ID":"de40ad0","Expected":"de40ad0"},"SecurityOptions":["name=seccomp,profile=d
efault"],"Warnings":["WARNING: API is accessible on http://0.0.0.0:2376 without encryption.\n         Access to the remote API is equivalent to root access on the host. Refer\n         to the 'Docker daemon attack surface' section in the do
cumentation for\n         more information: https://docs.docker.com/go/attack-surface/"]}

引入插件

接下来我们就可以对自己的服务进行配置,就以笔者的cloud-gateway为例,模块截图如下所示:

从而完成基于maven打包生成镜像并上传到服务器了,首先在maven插件中引入下面这段依赖,读者只需按需修改下面的dockerHost即可,别的配置若无非必须则可以不动。

go 复制代码
<plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <executions>
                    <execution>
                        <goals>
                            <goal>repackage</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>

            <plugin>
                <groupId>com.spotify</groupId>
                <artifactId>docker-maven-plugin</artifactId>
                <version>1.2.2</version>
                <configuration>
                    <imageName>${project.artifactId}</imageName>
                    <imageTags>
                        <imageTag>latest</imageTag>
                    </imageTags>
                    <!--指定Dockerfile路径-->
                    <dockerDirectory>${project.basedir}/src/main/docker</dockerDirectory>
                    <dockerHost>http://ip:2376</dockerHost>
                    <resources>
                        <resource>
                            <targetPath>/</targetPath>
                            <!--${project.basedir}/target-->
                            <directory>${project.build.directory}</directory>
                            <!--${project.artifactId}-${project.version}-->
                            <include>${project.build.finalName}.jar</include>
                        </resource>
                    </resources>
                </configuration>
            </plugin>

编写Dockerfile

我们上面的配置指明Dockerfile的路径为${project.basedir}/src/main/docker,所以我们要在main目录下创建一个docker文件夹。

在该文件夹下创建Dockerfile文件,以笔者为例笔者的cloud-gateway打包命令,就如下图所示(注意ENTRYPOINT 指定jvm参数笔者采用exec格式的,原本采用数组格式的会报错,笔者也没有去纠结原因)

go 复制代码
FROM openjdk:8-jdk-alpine
VOLUME /tmp
ADD cloud-gateway-0.0.1-SNAPSHOT.jar app.jar
RUN sh -c 'touch /app.jar'
# 调整JVM参数堆区空间大小,节省服务内存空间。
ENTRYPOINT exec java -Xmx32m -Xms32m  -Djava.security.egd=file:/dev/./urandom  -jar /app.jar

基于maven远程完成maven镜像的构建

完成后我们就可以到当前模块的pom文件的目录使用cmd键入下面这条命令,完成镜像构建

go 复制代码
mvn clean package docker:build -DskipTests

如下图所示,一旦出现BUILD SUCCESS就说明镜像构建成功了

注意笔者在打包过程中遇到了一个报错:Execution repackage of goal org.springframework.boot:spring-boot-maven-plugin。查阅网上资料得知,不是spring boot引用不可添加下面这个插件,去掉后即可解决。

go 复制代码
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>

查看镜像是否成功到达服务器

我们到服务器键入

go 复制代码
docker images

可以看到若出现我们打包的镜像名称说明打包成功了。同理我们完成其他服务器的插件引入和dockerfile编写。

启动测试

笔者为了启动方便这里也编写了一个docker-compose文件,文件名为cloud-service.yml内容如下:

go 复制代码
version: "3"
services:
  cloud-gateway:
    container_name: cloud-gateway
    image: cloud-gateway:latest
    ports:
    - "8090:8090"
    restart: always

  account-service:
    container_name: account-service
    image: account-service:latest
    ports:
    - "9000:9000"
    restart: always

到文件cloud-service.yml下键入命令

go 复制代码
docker-compose -f cloud-service.yml up -d

本地键入curl 命令,可以看到请求成功,说明本次服务器部署成功了。

go 复制代码
curl ip:8090/account/getByCode/zsy
{"status":100,"message":"操作成功","data":{"id":1,"accountCode":"zsy","accountName":"zsy","amount":10000.00},"success":true,"timestamp":1675592778302}

参考文献

SpringCloud Alibaba微服务实战十五 - SpringCloud 容器化部署

Dockerfile中ENTRYPOINT指定JVM启动堆内存参数后部署容器启动报错?

相关推荐
码农小白AI16 小时前
AI报告审核加速融入自动化实验室:IACheck破解智能设备时代报告管理新挑战
运维·人工智能·自动化
utf8mb4安全女神16 小时前
克隆的虚拟机怎么更改ip地址
运维
赵民勇16 小时前
fuse-overlayfs命令详解
linux·容器
sulikey16 小时前
个人Linux操作系统学习笔记6 - 操作系统与进程初识
linux·笔记·学习·操作系统·进程
万能的知了17 小时前
服务器托管 vs 云主机 vs 裸金属:一个决策故事
运维·服务器·云计算
qq_3829492217 小时前
推荐:《Spring Cloud Alibaba 微服务架构实战课》—— 从零到一构建企业级微服务系统
微服务·云原生·架构
杨云龙UP18 小时前
Oracle RAC / ODA 生产环境指定 PDB 启动 SOP
linux·运维·数据库·oracle
luweis18 小时前
企智孪生 ETA(3.3 认知算法层:ETA 的思维内核 3.4 基础架构:算力与弹性)【浙江联保网络 卢伟舜】
大数据·运维·线性代数·ai·矩阵·学习方法
极客老王说Agent18 小时前
屏幕理解能力是下一代自动化的关键吗?2026年自动化范式演进深度解析
运维·人工智能·ai·chatgpt·自动化
LT101579744419 小时前
2026年电商RPA选型指南:电商运营全流程自动化测评
运维·自动化·rpa