恢弘志士之气,不宜妄自菲薄。这篇文章主要讲述kubernetes下的Nginx加Tomcat三部曲之二:细说开发相关的知识,希望能为你提供帮助。
欢迎访问我的GitHub
本篇概览
- 本文是《kubernetes下的nginx加Tomcat三部曲》的第二章,在《kubernetes下的Nginx加Tomcat三部曲之一:极速体验》一文我们快速部署了Nginx和Tomcat,达到以下效果:
文章图片
- 本文我会详细说明在kubernetes部署上述网络服务时,需要做哪些具体的工作;
- 需要以下操做才能在kubernetes上部署Nginx加Tomcat的服务:
- 开发Tomcat上的web工程和Docker镜像;
- 让kubernetes的机器用上web工程的Docker镜像;
- 开发Tomcat对应的deployment脚本;
- 开发Tomcat对应的service脚本;
- 开发Nginx对应的Docker镜像;
- 让kubernetes的机器用上Nginx的Docker镜像
- 开发Nginx对应的deployment脚本;
- 开发Nginx对应的service脚本;
- 开发启动上述pod和service的脚本;
- 开发停止并清除上述pod和service的脚本
- 本次体验所需的deployment和service资源是通过脚本创建的,这个脚本可以通过GitHub下载,地址和链接信息如下表所示:
名称 | 链接 | 备注 |
---|---|---|
项目主页 | https://github.com/zq2599/blog_demos | 该项目在GitHub上的主页 |
git仓库地址(https) | https://github.com/zq2599/blog_demos.git | 该项目源码的仓库地址,https协议 |
git仓库地址(ssh) | git@github.com:zq2599/blog_demos.git | 该项目源码的仓库地址,ssh协议 |
- 这个git项目中有多个目录,本次所需的资源放在k8s_nginx_tomcat_resource,如下图红框所示:
文章图片
- 下到的k8stomcatcluster20180201.tar是个压缩包,复制到可以执行kubectl命令的ubuntu电脑上,然后解压开,是个名为k8stomcatcluster的文件夹;
- GitHub下载,地址和链接信息如下表所示:
名称 | 链接 | 备注 |
---|---|---|
项目主页 | https://github.com/zq2599/blog_demos | 该项目在GitHub上的主页 |
git仓库地址(https) | https://github.com/zq2599/blog_demos.git | 该项目源码的仓库地址,https协议 |
git仓库地址(ssh) | git@github.com:zq2599/blog_demos.git | 该项目源码的仓库地址,ssh协议 |
- 这个git项目中有多个目录,本次的web工程源码放在k8stomcatdemo,如下图红框所示:
文章图片
- 接下来我们开始实战开发吧;
- 本次实战开发环境的具体信息如下:
- 操作系统:Ubuntu16;
- Docker版本:17.03.2-ce;
- JDK:1.8.0_151;
- maven:3.3.3;
- web工程用来提供http服务,返回当前机器的IP地址给浏览器,完整源码请参照前面下载的k8stomcatdemo工程,这里我们还是重新创建一次;
- 创建一个springboot工程,pom.xml内容如下:
< ?xml version="1.0" encoding="UTF-8"?> < project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> < modelVersion> 4.0.0< /modelVersion> < groupId> com.bolingcavalry< /groupId> < artifactId> k8stomcatdemo< /artifactId> < version> 0.0.1-SNAPSHOT< /version> < packaging> jar< /packaging> < name> k8stomcatdemo< /name> < description> Demo project for Spring Boot< /description> < parent> < groupId> org.springframework.boot< /groupId> < artifactId> spring-boot-starter-parent< /artifactId> < version> 1.5.9.RELEASE< /version> < relativePath/> < !-- lookup parent from repository --> < /parent> < properties> < project.build.sourceEncoding> UTF-8< /project.build.sourceEncoding> < project.reporting.outputEncoding> UTF-8< /project.reporting.outputEncoding> < java.version> 1.8< /java.version> < /properties> < dependencies> < dependency> < groupId> org.springframework.boot< /groupId> < artifactId> spring-boot-starter-web< /artifactId> < /dependency> < dependency> < groupId> org.springframework.boot< /groupId> < artifactId> spring-boot-starter-test< /artifactId> < scope> test< /scope> < /dependency> < /dependencies> < build> < plugins> < plugin> < groupId> org.springframework.boot< /groupId> < artifactId> spring-boot-maven-plugin< /artifactId> < /plugin> < !--新增的docker maven插件--> < plugin> < groupId> com.spotify< /groupId> < artifactId> docker-maven-plugin< /artifactId> < version> 0.4.12< /version> < !--docker镜像相关的配置信息--> < configuration> < !--镜像名,这里用工程名--> < imageName> bolingcavalry/$project.artifactId< /imageName> < !--TAG,这里用工程版本号--> < imageTags> < imageTag> $project.version< /imageTag> < /imageTags> < !--镜像的FROM,使用java官方镜像--> < baseImage> java:8u111-jdk< /baseImage> < !--该镜像的容器启动后,直接运行spring boot工程--> < entryPoint> ["java", "-jar", "/$project.build.finalName.jar"]< /entryPoint> < !--构建镜像的配置信息--> < resources> < resource> < targetPath> /< /targetPath> < directory> $project.build.directory< /directory> < include> $project.build.finalName.jar< /include> < /resource> < /resources> < /configuration> < /plugin> < /plugins> < /build> < /project>
- 可以看到这是个普通的springboot的web工程,唯一不同的是多了一个maven插件:docker-maven-plugin,使用该插件我们可以将maven工程制作成docker镜像;
- 整个工程只有一个Controller,开通一个http接口,将当前服务器IP地址返回,源码如下:
@RestController public class ServerInfo @RequestMapping(value = "https://www.songbingjia.com/getserverinfo", method = RequestMethod.GET) public String getUserInfoWithRequestParam() return String.format("server : %s, time : %s", getIPAddr(), new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date())); /** * 获取本机IP地址 * @return */ private static String getIPAddr() String hostAddress = null; try InetAddress address = InetAddress.getLocalHost(); hostAddress = address.getHostAddress(); catch (UnknownHostException e) e.printStackTrace(); return hostAddress;
- 以上就是工程的关键源码;
- 在pom.xml所在目录执行mvn clean package -DskipTests docker:build,会编译构建工程,并且在本地制作好镜像文件,如下:
root@maven:/usr/local/work/github/blog_demos# docker images REPOSITORYTAGIMAGE IDCREATEDSIZE bolingcavalry/k8stomcatdemolatest1d41d9980a0b43 hours ago658 MB bolingcavalry/k8stomcatdemo0.0.1-SNAPSHOTc91bc368a72946 hours ago658 MB
- 想了解更多maven制作docker镜像的细节,请看《maven构建docker镜像三部曲之二:编码和构建镜像》
- 现在的镜像只存在于开发和构建web工程的电脑上,为了让kubernetes的node机器能用上这个镜像,可以用以下几种方式实现:
- 用docker push命令将本机镜像推送到hub.docker.com网站,这样其他机器都可以通过docker pull命令取得了,我就是用的这种方法,需要在hub.docker.com上注册;
- 用docker save命令导出镜像文件,再用docker load命令导入;
- kubernetes所在机器安装java和maven环境,将工程在这里编译构建;
- 使用docker私有仓库,例如搭建局域网私有仓库或者阿里云私有仓库,参考《maven构建docker镜像三部曲之三:推送到远程仓库(内网和阿里云)》;
- 用yaml文件将详情配置好,再用kubectl命令执行这个配置就能创建pod,这个web应用镜像的配置文件名为tomcat.yaml,内容如下:
apiVersion: extensions/v1beta1 kind: Deployment metadata: name: tomcathost spec: replicas: 3 template: metadata: labels: name: tomcathost spec: containers: - name: tomcathost image: bolingcavalry/k8stomcatdemo:0.0.1-SNAPSHOT tty: true ports: - containerPort: 8080
- 将上述脚本的几个关键点列举一下:
- version用extensions/v1beta1;
- kind用Deployment,支持升级镜像和滚动升级;
- 使用的镜像bolingcavalry/k8stomcatdemo:0.0.1-SNAPSHOT,是我从本地push到hub.docker.com上去的;
- 创建的容器对外暴露了8080端口;
- 创建了tomcat的pod之后,为了能在kubernetes环境中给其他service使用,需要将这些pod包装为service,这里是通过tomcat-svc.yaml文件来配置的,内容如下:
apiVersion: v1 kind: Service metadata: name: tomcathost spec: type: ClusterIP ports: - port: 8080 selector: name: tomcathost
- 将上述脚本的几个关键点列举一下:
- 服务对应的pod是tomcathost;
- type用ClusterIP,为内部service调用提供统一IP地址;
- 服务对外暴露了pod的8080端口;
- 定制的Nginx镜像和Nginx官方镜像相比,唯一的区别就是nginx.conf文件不同,我们用的nginx.conf内容如下:
usernginx; worker_processes1;
pid/var/run/nginx.pid;
events
worker_connections1024;
http
include/etc/nginx/mime.types;
default_typeapplication/octet-stream;
log_formatmain$remote_addr - $remote_user [$time_local] "$request"
$status $body_bytes_sent "$http_referer"
"$http_user_agent" "$http_x_forwarded_for";
access_log/var/log/nginx/access.logmain;
sendfileon;
#tcp_nopushon;
keepalive_timeout65;
#gzipon;
#include /etc/nginx/conf.d/*.conf;
upstream tomcat_client
server tomcathost:8080;
server
server_name "";
listen 80 default_server;
listen [::]:80 default_server ipv6only=on;
location /
proxy_pass http://tomcat_client;
proxy_redirect default;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
- 以上配置中,新增的upstream对应的IP地址是**tomcathost**,这是tomcat的service名称,在Nginx运行的时候,通过tomcathost就能访问到tomcat的Pod;- 制作Docker镜像的Dockerfile文件内容如下,每行都有注释就不再多说了:
```shell
# First docker file from bolingcavalry
# VERSION 0.0.1
# Author: bolingcavalry#基础镜像
FROM nginx:stable#作者
MAINTAINER BolingCavalry <
zq2599@gmail.com>
#定义工作目录
ENV WORK_PATH /etc/nginx#定义conf文件名
ENV CONF_FILE_NAME nginx.conf#删除原有配置文件
RUN rm $WORK_PATH/$CONF_FILE_NAME#复制新的配置文件
COPY ./$CONF_FILE_NAME $WORK_PATH/#给shell文件赋读权限
RUN chmod a+r $WORK_PATH/$CONF_FILE_NAME
- 将nginx.conf和Dockerfile放在同一个目录,然后执行命令docker build -t bolingcavalry/nginx-with-tomcat-host:0.0.1 .,就能构建镜像文件了,如下:
root@maven:/usr/local/work/nginx# docker build -t bolingcavalry/nginx-with-tomcat-host:0.0.1 . Sending build context to Docker daemon 14.51 MB Step 1/7 : FROM nginx:stable ---> dfe062ee1dc8 Step 2/7 : MAINTAINER BolingCavalry < zq2599@gmail.com> ---> Using cache ---> 93f4bf154c55 Step 3/7 : ENV WORK_PATH /etc/nginx ---> Using cache ---> d0158757fc9c Step 4/7 : ENV CONF_FILE_NAME nginx.conf ---> Using cache ---> 7a18a8b417d6 Step 5/7 : RUN rm $WORK_PATH/$CONF_FILE_NAME ---> Using cache ---> f6f27d25539d Step 6/7 : COPY ./$CONF_FILE_NAME $WORK_PATH/ ---> Using cache ---> 33075a2b0379 Step 7/7 : RUN chmod a+r $WORK_PATH/$CONF_FILE_NAME ---> Using cache ---> 58ce530e160b Successfully built 58ce530e160b
- 这一步和之前的web工程的镜像放到kubernetes一样,有多种方式,我用的还是通过docker push推送到hub.docker.com网站,再在kubernetes上pull下来;
- 用yaml文件将详情配置好,再用kubectl命令执行这个配置就能创建pod,这个web应用镜像的配置文件名为nginx.yaml,内容如下:
apiVersion: extensions/v1beta1 kind: Deployment metadata: name: ng spec: replicas: 1 template: metadata: labels: name: ng spec: containers: - name: ng image: bolingcavalry/nginx-with-tomcat-host:0.0.1 ports: - containerPort: 80
- 以上配置中有几点要注意:
- 使用镜像是刚才创建的nginx镜像bolingcavalry/nginx-with-tomcat-host:0.0.1;
- pod容器创建后,对外暴露80端口;
- 通过service定义的yaml文件nginx-svc.yam,将前面创建的nginx的pod包装为service:
apiVersion: v1 kind: Service metadata: name: ng spec: type: NodePort ports: - port: 80 nodePort: 30006 selector: name: ng
- 以上配置中有几点要注意:
- type使用NodePort,这样可以通过节点机器的IP访问此service;
- 将节点机器的30006端口和pod的80端口绑定,因此,外部访问节点IP+30006端口就能访问到此Nginx服务了;
- 接下来我们创建一个shell脚本start_all.sh,将上述的tomcat和nginx的pod以及service全部创建和启动:
kubectl create -f tomcat.yaml kubectl create -f tomcat-svc.yaml kubectl create -f nginx.yaml kubectl create -f nginx-svc.yaml echo "" echo "nginx and tomcat running now"
- 如上所示,通过kubectl create -f加文件名,就能创建好yaml文件中定义的pod和service;
- 创建一个shell脚本stop_all.sh,能够将上述的tomcat和nginx的pod以及service全部清除掉:
kubectl delete service tomcathost kubectl delete deployment tomcathost kubectl delete service ng kubectl delete deployment ng echo "nginx and tomcat stop now"
- 如上所示,其实就是通过kubectl delete命令将指定的pod和service资源删除;
- 下一章,我们会在此环境的基础上实战Tomcat服务的扩容,并修改web工程的代码,再创建新的镜像,并且将kubernetes环境下在线升级新的web工程服务;
推荐阅读
- H3CERG2系列路由器端口映射(虚拟服务器)
- 银行卡API接口的功能与作用
- 关于数据一致性的理论
- 如何做一个泡泡龙游戏
- C语言实现井字棋
- 大厂的优惠券系统是如何设计的()
- Python 散列表查询_进入<哈希函数;为结界的世界
- 可观测性(运维风向标!)
- 手把手教你安装Ubuntu