docker——发布一个应用程序

本文介绍了如何使用Docker发布一个Java应用程序,包括编写Dockerfile、创建docker镜像、运行容器、设置端口映射、挂载卷以及常用Docker命令的操作。详细解释了配置文件、日志管理和容器管理等关键步骤。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

docker——发布一个java应用程序

一、安装docker

使用docker之前,需要在物理机上安装docker。安装过程可参考docker官网,安装完成之后,运行docker。不同的操作系统,docker的安装和启动不同。

二、待发布的java程序说明

需要发布的java服务目录结构如下:

docker-test/
    |-bin/
    |  |-server.sh
    |-etc/
    |  |-config.edn
    |  |-logback.xml
    |-target/
    |  |-docker-test.jar
    |  |-docker-test-standalone.jar
    |-Dockerfile
Dockerfile

Dockerfile用来定义一个docker容器(container)的运行环境。

# 指定基础镜像openjdk8,用于运行java程序。
FROM openjdk:8
# 指定容器内的工作目录
WORKDIR /app/
# 将Dockerfile所在目录(docker-test)的bin目录复制到容器内(/app/bin/)
COPY bin bin
# 将docker-test目录下的etc目录复制到容器内(/app/etc/)
COPY etc etc
# 将target下以standalone.jar结尾的jar包复制到容器内的lib目录下(/app/lib/docker-test-standalone.jar).
COPY target/*standalone.jar lib/
# 将docker容器内的lib目录下的jar包名字写入到lib.txt(/app/lib.txt)
RUN ls lib/ > lib.txt
# 在docker容器内新建logs目录(/app/logs/)
RUN mkdir logs
# 将物理机时间时区挂在到容器中,这样容器时间与物理机系统时间一致
RUN ln -snf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
server.sh

server.sh为java服务启动脚本,内容如下:

#!/bin/bash
## java服务启动日志记录文件在容器内的路径
LOGFILE=/app/logs/start.log
## 进入容器内的bin目录
cd /app/bin
## 从/app/lib.txt文件中读取要运行的jar文件。
JAR=$(cat ../lib.txt)
## 运行程序
java ${JAVA_OPTS} -cp ../etc:../lib/${JAR} clojure.main -e "(use 'pay.system)(-main)" >> ${LOGFILE} 2>&1

注意这些目录都是针对docker容器内的目录。

config.edn

java程序运行时所需要的配置文件:

{
 ;; 提供给网页通信的web服务
 :outer-server       {:host "0.0.0.0" :port 8035 :join? false}

 ;; 提供给内部服务,用于接收其他服务器消息的web服务地址
 :inner-server       {:host "0.0.0.0" :port 8042 :join? false}
 }

0.0.0.0表示该docker容器接收访问端口8035和端口8042的所有ip。

logback.xml

logback日志配置:

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
    <appender name="CONSOLE" class="ch.qos.logback.core.ConsoleAppender">
        <encoder>
            <pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %-5level %-10contextName %logger{36} - %msg%n</pattern>
        </encoder>
    </appender>

    <!-- 按照每天生成日志文件 -->
    <appender name="LOG_FILE" class="ch.qos.logback.core.rolling.RollingFileAppender">
        <!-- 拦截debug级别的日志-->
        <filter class="ch.qos.logback.classic.filter.ThresholdFilter">
            <level>debug</level>
        </filter>
        <file>/app/logs/docker-test.log</file>
        <rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
            <fileNamePattern>/app/logs/docker-test.log.%d{yyyy-MM-dd}</fileNamePattern>
            <!-- 日志文件保留天数-->
            <maxHistory>180</maxHistory>
        </rollingPolicy>
        <!-- 这里使用普通的输出格式-->
        <encoder>
            <pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n</pattern>
        </encoder>
    </appender>       

    <!-- 这里是运行日志 -->
    <logger name="app" level="info" additivity="false">
        <appender-ref ref="LOG_FILE" />
    </logger>

    <root level="info">
        <appender-ref ref="LOG_FILE" />
    </root>
</configuration>

注意,日志文件的路径为docker容器内的路径/app/logs/docker-test.log而不是物理机上的文件路径。

三、打包程序的docker镜像

进入到docker-test目录,执行下面命令:

docker build -t docker-test:0.1.0

很多时候,我们会迭代发布好多镜像,就需要为这些镜像打上tag(经常用版本号作为tag),此时要带上-t参数。如果不带tag,则会默认使用latest作为TAG。

这样打包后的镜像被放在本地,可以使用下面命令查看本地镜像:

docker images -a

可以使用命令删除一个本地镜像:

docker rmi docker-test:0.1.0

四、运行docker容器

docker run -itd –name docker-test -e JAVA_OPTS=’-Xmx368m -Dfile.encoding=UTF-8 -Duser.timezone=GMT+08’ -p 8035:8035 -p 8042:8042 -v
/Users/admin/docker-test/logs:/app/logs -v /Users/admin/docker-test/etc:/app/etc
docker-test:0.1.0 /app/bin/server.sh

-d:表示在后台运行该docker容器
-i:表示保留STDIN(标准输入),用于控制台交互 。
-t:分配tty设备,该可以支持终端登录 。
-p:指定端口或ip映射,将物理机上的8035端口与docker容器的8035端口映射;将物理机上的8042端口与docker容器的8042端口映射。
-v:给容器挂载存储卷,挂载到容器的某个目录。这里讲物理机上的/Users/admin/docker-test/logs目录挂载到docker容器的/app/logs目录,这样程序输出的在logback.xml中指定的日志,实际上被写入到物理机/Users/admin/docker-test/logs目录下对应的日志文件中。
-e:用于指定环境变量,比如例子中就设定了jvm运行时的参数(JAVA_OPTS),在启动java程序时用到。注意-Duser.timezone=GMT+08用于解决jvm时区与系统时区不一致,导致日志文件中输出的时间为标准时区的时间,而不是本地时间。

目录挂载的目的

  • 挂载日志目录:因为程序运行的日志文件会非常之大,如果不将物理机的目录挂在容器内,那么日志将存储在容器内,而且是存储在内存中,永不了多久,内存就会爆掉。
  • 挂载配置文件目录:挂载配置文件,使得可以在物理机上修改配置文件,然后重新运行容器,达到改变配置的目的。
  • 注意: 如果docker是部署在集群(如k8s)中,那么无法使用目录挂载,因为你无法确定容器会运行在集群中哪个物理机上。此时,你的配置最好通过环境变量传递,日志则可以输出到标准输出。

docker-test:0.1.0 /app/bin/server.sh:运行docker-test:0.1.0镜像的/app/bin/server.sh脚本。

至此,一个容器便启动成功。可以尝试访问物理机地址的8035或8042端口,验证是否程序是否正常运行。

但这样运行的话,容器其实是阻塞在运行脚本/app/bin/server.sh的状态(因为在脚本中,并没有指定程序在后台运行),此时我们不能通过docker的attch命令进入到容器。

可以通过如下命令运行docker容器:

docker run -itd –name docker-test -e JAVA_OPTS=’-Xmx368m -Dfile.encoding=UTF-8 -Duser.timezone=GMT+08’ -p 8035:8035 -p 8042:8042 -v
/Users/admin/docker-test/logs:/app/logs -v /Users/admin/docker-test/etc:/app/etc
docker-test:0.1.0 /bin/bash

这样容器内会启动/bin/bash终端,通过命令:

docker ps -a

可以找到容器ID(containerID),通过命令:

docker attach containerID

可以进入到该容器,此时界面和普通的unix命令行界面一样。在容器内的命令行界面中,输入命令:

./bin/server.sh

即可启动java程序。

可以使用如下命令查看镜像的容器是否启动成功(在STATUS中如果为up..则启动成功,如果为exit…则未启动成功):

docker ps -a

五、其他常用docker命令

停止容器

docker stop containerID

删除容器

docker rm containerID

进入容器

首先通过docker ps -a命令可以查看到正在运行的容器ID(CONTAINER ID)。如果容器内的进程是以后台运行的方式启动的,则可以使用命令:

docker attach containerId

进入容器。

如果容器内的进程不是以后台方式启动的,那么就无法通过attach命令进入,可使用命令:

docker exec -it containerID /bin/bash

进入。

导出镜像文件

docker save -o [导出后的文件名] [镜像名称]

如,将test-0.1.0:test镜像导出为test-0.1.0.tar:

docker save -o test-0.1.0.tar test-0.1.0:test

导入镜像文件

docker load –input [导出后的文件名]

如,将上面导出的test-0.1.0.tar再导入:

docker load –input test-0.1.0.tar

查看docker容器中标准输出内容

docker logs [容器名称或容器ID]

拉取docker镜像

docker pull [镜像地址]

Docker —— 从入门到实践》是一本介绍Docker技术的书籍。Docker一个开源的容器化平台,可以帮助开发者更方便地构建、部署和运行应用程序。这本书从入门到实践的角度,详细介绍了Docker的基本概念、原理和使用方法。 书中首先介绍了Docker的背景和发展历程,包括为什么需要容器化技术以及Docker的优势。接着,作者详细讲解了Docker的安装和配置,包括在不同操作系统上的安装方法。然后,书中以一个个实例来引导读者学习如何使用Docker进行应用程序的容器化和部署。这些实例包括创建镜像、构建容器、管理数据卷等。 在实践部分,书中介绍了如何使用Docker搭建开发环境和测试环境,以及如何使用Docker进行持续集成和持续部署。另外,还介绍了Docker的监控和日志管理、网络配置以及安全性等方面的内容。 这本书的优点在于它结合了理论和实践,既对Docker的原理和概念进行了深入讲解,又提供了丰富的实践案例。通过学习这本书,读者可以系统地掌握Docker的基础知识,并能够利用Docker来管理和部署应用程序。 总的来说,《Docker —— 从入门到实践》是一本很好的Docker入门书籍,适合有一定编程和系统管理基础的读者。它的内容丰富有趣,通俗易懂,通过读这本书,读者可以快速上手使用Docker,并能够在实践中不断深化对容器化技术的理解和应用。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值