目录
什么是Dockerfile
-
Dockerfile是一个包含用于组合映像的命令的文本文档。可以使用在命令行中调用任何命令。 Docker通过读取Dockerfile中的指令自动生成映像
-
docker build命令用于从Dockerfile构建映像。可以在docker build命令中使用-f标志指向文件系统中任何位置的Dockerfile
-
Dockerfile其内部包含了一条条的指令,每一条指令构建一层,因此每一条指令的内容,就是描述该层应当如何构建。
-
请注意,每条指令都是独立运行的,并会导致创建新映像-因此RUN cd /tmp对下一条指令不会有任何影响。
-
Docker Dockerfile按顺序运行指令。一个Dockerfile 必须用FROM指令开始。这可能在解析器指令,注释和全局范围的 ARG之后。该FROM指令指定要从中构建父图像。FROM 只能在一个或多个ARG指令之前,这些指令声明在中的FROM行中使用的参数Dockerfile
1.Dockerfile常用命令
指令 | 含义 |
---|---|
FROM 镜像 | 指定新镜像所基于的镜像,第一条指令必须为FROM指令, 每创建一个镜像就需要一条FROM指令 |
MAINTAINER 名字 | 说明新镜像的维护人信息 |
RUN 命令 | 在所基于的镜像执行命令,并提交到新的镜像中 |
CMD [ “要运行的程序”,“参数1”,“参数2”] | 指令启动容器时要运行的命令或者脚本,Dockerfile只能 有一条CMD命令,如果指定多条则只能执行最后一条 |
EXPOSE 端口号 | 指定新镜像加载到Docker时要开启的端口 |
ENV 环境变量 变量值 | 设置一个环境变量的值,会被后面的RUN使用 |
ADD 源文件/目录 目标文件/目录 | 将源文件复制到目标文件,源文件要与Dockerfile位于 相同目录中,或者是一个URL |
COPY 源文件/目录 目标文件/目录 | 将本地主机上的文件/目录复制到目标地点,源文件/目录 要与Dockerfile在相同的目录中 |
VOLUME [“目录”] | 在容器中创建一个挂载点 |
USER 用户名/UID | 指定运行容器时的用户 |
WORKDIR 路径 | 为后续的RUN、CMD、ENTRYPOINT指定工作目录 |
ONBUILD 命令 | 指定所生成的镜像作为一个基础镜像时所要运行的命令 |
HEALTHCHECK | 健康检查 |
Dockerfile构建容器
创建任何Dockerfile之前,良好的习惯是为这个Dockerfile创建专门的目录
1.构建Apache镜像
- 创建目录,编写Dockerfile文件
[root@docker ~]# mkdir apache
[root@docker ~]# cd apache/
[root@docker apache]# vim Dockerfile
FROM centos:7 ##基于的基础镜像
MAINTAINER ZZT ##维护人信息
RUN yum -y update ##更新镜像中的yum仓库
RUN yum -y install httpd ##yum安装httpd
EXPOSE 80 ##镜像中暴露的端口号
ADD index.html /var/www/html/index.html ##添加httpd首页
ADD run.sh /run.sh ##添加脚本
RUN chmod 755 /run.sh ##修改脚本权限
CMD ["./run.sh"] ##运行脚本
##制作ADD需要的脚本##
[root@docker apache]# vim run.sh
#!/bin/bash
##如果原来有运行apache,会将http的所有缓存文件清空
rm -rf /run/httpd/*
##exec表示执行,FOREGROUND表示强制启动
exec /usr/sbin/apachectl -D FOREGROUND
[root@docker apache]# echo "123" > index.html
###构建镜像,并基于构建的镜像生成容器##
# build:如果本地有镜像则使用本地镜像,如果没有会从仓库去下载,httpd:centos这个是随便启的名字,-t 分配一个伪终端#
[root@docker apache]# docker build -t httpd:centos .
Sending build context to Docker daemon 4.096kB
Step 1/9 : FROM centos:7
7: Pulling from library/centos
2d473b07cdd5: Downloading 21MB/76.1MB
[root@docker apache]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
httpd centos 2ec761c6e8b2 49 seconds ago 394MB
centos 7 8652b9f0cb4c 11 hours ago 204MB
##-d守护进程,-p端口映射,宿主机端口:容器端口 ##
[root@docker apache]# docker run -d -p 1111:80 httpd:centos
dbd894b852293060c81e90e37660d5e1f5597dfe6a2c6e031b07139fafde7208
[root@docker apache]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
dbd894b85229 httpd:centos "./run.sh" 2 minutes ago Up 2 minutes 0.0.0.0:1111->80/tcp sharp_jang
这个时候我们笔记本的浏览器访问一下试试,可以访问到容器
2.构建sshd镜像
-
我们下载一个centos:7的镜像,进去发现无法使用sshd服务,我们需要手工添加
-
1、创建目录,编写Dockerfile文件
[root@docker apache]# cd ~
[root@docker ~]# mkdir sshd
[root@docker ~]# cd sshd/
[root@docker sshd]# vim Dockerfile
FROM centos:7 //指定基础镜像
MAINTAINER build image sshd <tang> //描述信息
RUN yum -y update //更新容器yum源
RUN yum -y install openssh* net-tools lsof telnet passwd //部署环境工具
RUN echo "123123" | passwd --stdin root //设置root登录密码
RUN sed -i 's/UsePAM yes/UsePAM no/g' /etc/ssh/sshd_config //禁用ssh中的pam验证
RUN ssh-keygen -t rsa -f /etc/ssh/ssh_host_rsa_key //创建非对称密钥,并指定文件路径
RUN sed -i '/^session\s\+required\s\+pam_loginuid.so/ s/^/#/' /etc/pam.d/sshd //禁用pam的ssh的pam会话模块
RUN mkdir -p /root/.ssh && chown root.root /root && chmod 700 /root/.ssh //创建ssh工作目录和权限设置
EXPOSE 22 //开放22端口
CMD ["/usr/sbin/sshd","-D"] //容器加载时启动sshd服务'
[root@docker sshd]# docker build -t sshd:new .
[root@docker sshd]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
sshd new faa2e4ffc7d9 About a minute ago 457MB
httpd centos 2ec761c6e8b2 9 minutes ago 394MB
centos 7 8652b9f0cb4c 11 hours ago 204MB
##基于镜像创建容器并使用sshd验证##
# -P 表示由系统自带分配端口映射,会从32768开始分配
[root@docker sshd]# docker run -d -P sshd:new
1c59d6719ea4bb57b7e9211a3f9373bb84539e5f99efbe8cc902d269414820ef
[root@docker sshd]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
1c59d6719ea4 sshd:new "/usr/sbin/sshd -D" About a minute ago Up About a minute 0.0.0.0:32768->22/tcp gallant_bell
[root@docker sshd]# ssh localhost -p 32768
The authenticity of host '[localhost]:32768 ([::1]:32768)' can't be established.
RSA key fingerprint is SHA256:Jncy3p5jwvCJMLkJIXxpO3G4mexCw0gRjswdJg6pWpc.
RSA key fingerprint is MD5:4e:1a:b5:67:05:4c:c2:ed:72:43:5a:e5:96:40:79:60.
Are you sure you want to continue connecting (yes/no)? yes //连接
Warning: Permanently added '[localhost]:32768' (RSA) to the list of known hosts.
root@localhost's password: //密码123456
[root@1c59d6719ea4 ~]# ##已经通过ssh进入容器##
##这个时候我们发现无法使用systemctl命令##接下来我们构建##
[root@1c59d6719ea4 ~]# systemctl status sshd
Failed to get D-Bus connection: Operation not permitted
3.构建systemctl镜像
[root@1c59d6719ea4 ~]# exit
logout
Connection to localhost closed.
[root@docker sshd]#
[root@docker sshd]# cd ~
[root@docker ~]# mkdir systemctl
[root@docker ~]# cd systemctl/
[root@docker systemctl]# vim Dockerfile
[root@docker sshd]# mkdir /systemctl
[root@docker sshd]# cd /systemctl
[root@docker systemctl]# vim Dockerfile
FROM sshd:new
####声明一个变量
ENV container docker
####使用循环操作,将sysinit.target.wants/下的所有删除,只留下核心文件temfiles-setep
####为什么删除这些文件,因为这些文件保留的不够完整,我们也不需要使用到它
RUN (cd /lib/systemd/system/sysinit.target.wants/; for i in *; do [ $i == \
systemd-temfiles-setep.service ] || rm -f $i; done); \
rm -f /lib/systemd/system/mutil-user.target.wants/*;\
rm -f /etc/systemd/system/*.wants/*;\
rm -f /lib/systemd/ststem/local-fs.target.wants/*;\
rm -f /lib/systemd/system/sockets.target.wants/*udev*;\
rm -f /lib/systemd/system/sockets.target.wants/*initctl*;\
rm -f /lib/systemd/system/basic.target.wants/*;\
rm -f /lib/ststemd/system/anaconda.target.wants/*;
####/sys/fs/cgroup这是真正需要的文件,cgroup做的是一个资源限制的文件
####VOLUME将宿主机文件直接挂载在容器当中使用
VOLUME [ "/sys/fs/cgroup" ]
####在容器启动时进行初始化
CMD ["/usr/sbin/init"]
[root@docker systemctl]# docker build -t systemd:111 .
##创建容器##&一定要加,不然你进入容器后退不出来
[root@docker systemctl]# docker run --privileged -ti -v /sys/fs/cgroup/:/sys/fs/cgroup:ro systemd:111 &
+[28169]
[root@docker systemctl]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
a84839b38290 systemd:111 "/usr/sbin/init" 54 seconds ago Up 52 seconds 22/tcp thirsty_feynman
a0c3c6c229d9 sshd:new "/usr/sbin/sshd -D" 2 minutes ago Up 2 minutes 0.0.0.0:32768->22/tcp affectionate_hamilton
[root@docker systemctl]# docker exec -it a84839b38290 /bin/bash
##可以看到systemctl可以正常使用##
[root@c824889465e6 ~]# systemctl status sshd
● sshd.service - OpenSSH server daemon
Loaded: loaded (/usr/lib/systemd/system/sshd.service; disabled; vendor preset: enabled)
Active: inactive (dead)
Docs: man:sshd(8)
man:sshd_config(5)
[root@a84839b38290 /]# exit
exit
4.nginx镜像(手工编译安装的方法)
[root@docker ~]# mkdir nginx
[root@docker ~]# cd nginx/
[root@docker nginx]# vim Dockerfile
FROM centos:7
MAINTAINER ZZT
RUN yum -y update
RUN yum -y install pcre-devel zlib-devel gcc gcc-c++ make
RUN useradd -M -s /sbin/nologin nginx
ADD nginx-1.15.9.tar.gz /usr/local/src
WORKDIR /usr/local/src/nginx-1.15.9
RUN ./configure \
--prefix=/usr/local/nginx \
--user=nginx \
--group=nginx \
--with-http_stub_status_module && make && make install
ENV PATH /usr/local/nginx/sbin:$PATH
EXPOSE 80
EXPOSE 443
RUN echo "daemon off;">>/usr/local/nginx/conf/nginx.conf
ADD run.sh /run.sh
RUN chmod 755 /run.sh
CMD ["/run.sh"]
[root@docker nginx]# vim run.sh
#!/bin/bash
/usr/local/nginx/sbin/nginx
##注意,这里我们有一个ADD,所以需要将包源上传进去##
[root@docker nginx]# rz -E
rz waiting to receive.
[root@docker nginx]# docker build -t nginx:new .
[root@docker nginx]# docker run -d -P nginx:new
[root@docker nginx]# docker ps -a
[root@docker nginx]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
f007f6aa33d9 nginx:new "/run.sh" 5 seconds ago Up 3 seconds 0.0.0.0:32770->80/tcp, 0.0.0.0:32769->443/tcp tender_mendel
这个时候使用浏览器访问一下
5.tomcat镜像构建
[root@docker nginx]# cd ~
[root@docker ~]# mkdir tomcat
[root@docker ~]# cd tomcat/
[root@docker tomcat]# vim Dockerfile
FROM centos:7
MAINTAINER ZZT:
ADD jdk-8u144-linux-x64.tar.gz /usr/local/
WORKDIR /usr/local/
RUN mv jdk1.8.0_144 /usr/local/java
ENV JAVA_BIN /usr/local/java/bin
ENV JAVA_HOME /usr/local/java
ENV JRE_HOME /usr/local/java/jre
ENV CLASSPATH $JAVA_HOME/lib/tools.jar:$JAVA_HOME/lib/dt.jar
ENV PATH $JAVA_HOME/bin:$PATH
ADD apache-tomcat-8.5.23.tar.gz /usr/local/
RUN mv /usr/local/apache-tomcat-8.5.23 /usr/local/tomcat
EXPOSE 8080
##run运行的一个参数ENTRYPOINT,这个参数指的是/usr/local/tomcat/bin/catalina.sh
##ENTRYPOINT与CMD的区别:如果docker run 不会覆盖ENTRYPOINT的指令
ENTRYPOINT ["/usr/local/tomcat/bin/catalina.sh","run"]
将两个包拖入到tomcat目录下
[root@docker tomcat]# docker build -t tomcat:new .
[root@docker tomcat]# docker run -d -P tomcat:new
[root@docker tomcat]# docker ps -a
[root@docker tomcat]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
a20abf3d4239 tomcat:new "/usr/local/tomcat/b…" 2 minutes ago Up 2 minutes 0.0.0.0:32771->8080/tcp sweet_vaughan
用笔记本浏览器访问试试,可以看到启动了
6.构建mysql镜像
- 这里我做了一个安装脚本,软件版本:mysql-5.7.20
##NYSQL的shell安装脚本##
[root@docker tomcat]# cd ~
[root@docker ~]# mkdir mysql
[root@docker ~]# cd mysql/
[root@docker mysql]# vim run.sh
#!/bin/bash
yum -y install \
ncurses \
ncurses-devel \
bison \
cmake \
make \
gcc \
gcc-c++
cd /opt
cd mysql-5.7.20/
cmake \
-DSYSCONFDIR=/etc \
-DSYSTEMD_PID_DIR=/usr/local/mysql \
-DDEFAULT_CHARSET=utf8 \
-DDEFAULT_COLLATION=utf8_general_ci \
-DWITH_INNOBASE_STORAGE_ENGINE=1 \
-DWITH_ARCHIVE_STORAGE_ENGINE=1 \
-DWITH_BLACKHOLE_STORAGE_ENGINE=1 \
-DWITH_PERFSCHEMA_STORAGE_ENGINE=1 \
-DMYSQL_DATADIR=/usr/local/mysql/data \
-DWITH_BOOST=boost \
-DWITH_SYSTEMD=1
make -j3 && make install -j3 ##注意此处的-j3根据核数定义,不要盲目跟从
useradd -s /sbin/nologin mysql
chown -R mysql:mysql /usr/local/mysql/
echo "[client]
port = 3306
default-character-set=utf8
socket = /usr/local/mysql/mysql.sock
[mysql]
port = 3306
default-character-set=utf8
socket = /usr/local/mysql/mysql.sock
[mysqld]
user = mysql
basedir = /usr/local/mysql
datadir = /usr/local/mysql/data
port = 3306
character_set_server=utf8
pid-file = /usr/local/mysql/mysqld.pid
socket = /usr/local/mysql/mysql.sock
server-id = 1
sql_mode=NO_ENGINE_SUBSTITUTION,STRICT_TRANS_TABLES,NO_AUTO_CREATE_USER,NO_AUTO_VALUE_ON_ZERO,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,PIPES_AS_CONCAT,ANSI_QUOTES" > /etc/my.cnf
chown mysql:mysql /etc/my.cnf
##MYSQL的Dockerfile##
将mysql-boost-5.7.20.tar.gz这个包拖进mysql/下
[root@docker mysql]# vim Dockerfile
FROM centos:7
MAINTAINER ZZT
ADD mysql-boost-5.7.20.tar.gz /opt
ADD run.sh /opt
WORKDIR /opt
RUN chmod +x run.sh
RUN ./run.sh
ENV PATH=/usr/local/mysql/bin:/usr/local/mysql/lib:$PATH
WORKDIR /usr/local/mysql/
RUN bin/mysqld \
--initialize-insecure \
--user=mysql \
--basedir=/usr/local/mysql \
--datadir=/usr/local/mysql/data
##这里遇到个坑,start不起来,所以我使用开机自启最后交给容器帮我启动
RUN cp usr/lib/systemd/system/mysqld.service /usr/lib/systemd/system/
EXPOSE 3306
RUN echo -e "#!/bin/bash \n systemctl enable mysqld" > /1.sh
RUN chmod 755 /1.sh
RUN sh /1.sh
##这里初始化,将mysql启动起来,对应前面的enable
CMD ["init"]
[root@docker mysql]# docker build -t mysql:new .
###privileged表示root账户访问容器不降权,如果不加进不去mysql###
[root@docker mysql]# docker run -d -P --name=mysql_root --privileged mysql:new
[root@docker ~]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
8a6380eb103b mysql:new "init" 19 minutes ago Up 19 minutes 0.0.0.0:32772->3306/tcp mysql_root
[root@docker ~]# docker exec -it 8a6380eb103b /bin/bash
[root@8a6380eb103b mysql]#
[root@8a6380eb103b mysql]# mysqladmin -uroot -p password
Enter password: //回车,然后输入两次密码
[root@8a6380eb103b mysql]# mysql -uroot -p
Enter password:
Welcome to the MySQL monitor. Commands end with ; or \g.
Your MySQL connection id is 8
Server version: 5.7.20 Source distribution
Copyright (c) 2000, 2017, Oracle and/or its affiliates. All rights reserved.
Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
mysql>
####数据库登录成功,容器正常运行###
普通java进程
#列子1
[qt@dbus-n1 ]# cat Dockerfile
FROM java:8
MAINTAINER FAN
VOLUME /opt
RUN cp /usr/share/zoneinfo/Asia/Shanghai /etc/localtime && echo 'Asia/Shanghai'>/etc/timezone
ADD xxxx.jar /opt/xxxx.jar
EXPOSE 8000
ENTRYPOINT ["nohup","java","-jar","/opt/ruoyi-admin.jar"]