从零开始将项目部署到Kubernetes

从零开始将项目部署到Kubernetes

2019, Dec 02    

一、前言

kubernetes作为一个容器的编排引擎,如今已经相当的火热,日常的工作中也有使用常用的kubernetes的相关的功能,例如滚动发布、扩容等等,但是这都是在公司现成的已经搭建好的kubernetes集群上实践的,因此,本篇文章就是自主探索在本地运行一个kubernetes集群,同时写一个自己的demo,运行到本地的kubernetes集群当中。
本文主要包含如下几个方面:

  • 国内条件下如何安装kubernetes(no vpn)
  • 写一个Spring boot 的demo
  • 使用Docker将demo打包成镜像
  • 将demo部署到本地kubernetes集群当中

二、本地安装kubernetes

选择使用minikube

我们想要学习使用kubernetes,首先就是选择一个平台进行操作,比如阿里云、Azure、Google Kubernetes等等
这里我们选择的就是学习用的minikube

kubernetes官方文档 minikube操作文档 minikube安装文档

安装minikube

1.检查能否虚拟化

sysctl -a | grep -E --color 'machdep.cpu.features|VMX' 


vmx被标注出来有颜色,说明就是ok的,这台电脑是支持virtualization的(一般都是支持的,但是我花了88白菜价在腾讯云上买的1年1核1g服务器是不支持的)

2.安装kubectl

brew install kubernetes-cli

使用kubectl version能够查看到对应的kubectl版本

3.安装Hypervisor(virtual machine monitor)

这个主要就是安装虚拟机了,kvm或者virtualBox二选一

4.安装minikube

有两种方式,第一种方式就是如下的方式

curl -Lo minikube https://storage.googleapis.com/minikube/releases/latest/minikube-linux-amd64 \
	&& chmod +x minikube

将minikube安装包下载下来,手动进行安装

sudo mkdir -p /usr/local/bin/
sudo install minikube /usr/local/bin/


如果是mac用户,直接使用如下的命令就可以了

brew install minikube
brew link minikube

5.启动minikube

minikube start


就会开始根据本地的virtualBox来下载对应的驱动,中间应该会要求输入一次本机电脑的一次密码,然后会出现这样的错误: Error creating machine: Error in driver during machine creation: hyperkit crashed! 我们可以使用minikube start -help查看到这个命令的一些参数: 例如--cpus=2我们可以设置为4,--disk-size等等都可以进行测试。由于按照官网的操作一步一步来做,发现依然会出错?然后我发现本地已经有了hyperkit,装的virtualBox没有什么用,因此我brew reinstall hyperkit重新安装了一下,这时候再来一次minikube start,这一次似乎终于是成功了。


然后就开始下载kubernetes的相关的各种组件dns、kube-proxy\kube-addon-manager等等,但是可能是由于被墙的原因下载不下来,这个时候我进行了以下的几种处理方式:

  1. 科学上网,ok科学上网之后,再来看看,但是发现依然还是不行
  2. 设置国内的代理–image-repository……ok还是一样的错
    minikube start --registry-mirror=https://registry.docker-cn.com
    
  3. 换一个虚拟机来进行安装,改用vmware来进行安装,当然也是没有什么作用的
    brew install docker-machine-driver-vmware
    minikube start --vm-driver=vmware
    
  4. 关键的问题就在于VM is unable to access k8s.gcr.io, you may need to configure a proxy or set --image-repository,因此我找到了kubernetes minikube的github仓库,找到了其issue区,看看有没有仁兄有我一样的情况。功夫不负有心人,找到了issue 3860,我们可以使用国内的阿里云镜像egistry.cn-hangzhou.aliyuncs.com/google_containers
    rm -rf ~/.minikube
    minikube start --image-repository=registry.cn-hangzhou.aliyuncs.com/google_containers --vm-driver=vmware
    


    看一看minikube都有些什么namespace
    成功了!

三、编写Demo

接下来我们新建一个demo,使用Spring框架写一个简单的controller

TestDemo

1.使用官方的Initializer脚手架初始化一个demo

https://start.spring.io/

2.在项目中添加需要的RestController和swagger的依赖

RestController有关的依赖

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
    <version>2.1.8.RELEASE</version>
</dependency>

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-thymeleaf</artifactId>
    <version>2.0.5.RELEASE</version>
</dependency>

与swagger有关的依赖

<dependency>
            <groupId>io.springfox</groupId>
            <artifactId>springfox-swagger2</artifactId>
            <version>${io.springfox.version}</version>
        </dependency>

        <dependency>
            <groupId>io.springfox</groupId>
            <artifactId>springfox-swagger-ui</artifactId>
            <version>${io.springfox.version}</version>
        </dependency>

        <dependency>
            <groupId>io.springfox</groupId>
            <artifactId>springfox-swagger-common</artifactId>
            <version>${io.springfox.version}</version>
        </dependency>


        <dependency>
            <groupId>io.springfox</groupId>
            <artifactId>springfox-spring-web</artifactId>
            <version>${io.springfox.version}</version>
        </dependency>

        <dependency>
            <groupId>io.springfox</groupId>
            <artifactId>springfox-spi</artifactId>
            <version>${io.springfox.version}</version>
        </dependency>

        <dependency>
            <groupId>io.springfox</groupId>
            <artifactId>springfox-schema</artifactId>
            <version>${io.springfox.version}</version>
        </dependency>

        <dependency>
            <groupId>io.springfox</groupId>
            <artifactId>springfox-core</artifactId>
            <version>${io.springfox.version}</version>
        </dependency>

        <dependency>
            <groupId>io.springfox</groupId>
            <artifactId>springfox-bean-validators</artifactId>
            <version>${io.springfox.version}</version>
        </dependency>

        <dependency>
            <groupId>io.swagger</groupId>
            <artifactId>swagger-annotations</artifactId>
            <version>1.5.21</version>
        </dependency>

        <dependency>
            <groupId>io.swagger</groupId>
            <artifactId>swagger-models</artifactId>
            <version>1.5.21</version>
        </dependency>

同时我们还需要在Application类中@EnableSwagger2

3.创建controller

首先在application.properties文件中添加一条配置

version=@project.version@

然后添加controller

package com.example.demo.controller;

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

/**
 * Created by Yangmingkai on 2019-11-11.
 */
@RestController
@Api("用于istio测试")
@RequestMapping("/demo")
public class IstioController {

    @Value("${version}")
    private String version;

    @GetMapping("/version")
    @ApiOperation("获取当前版本")
    public String getVersion() {

        return String.format("This is version %s", version);
    }
}

4.运行

四、将Demo打包成镜像

1.打包成jar包

进入pom.xml文件目录,运行命令mvn clean install -Dmaven.test.skip=true执行打包

2.利用dockerFile打包成镜像

编写docker file

# 拉取JDK11的系统镜像
From openjdk:11
# 设置时区
ENV TZ=Asia/Shanghai
# 时区写入系统文件
RUN ln -snf /usr/share/zoneinfo/$TZ  /etc/localtime && echo $TZ > /etc/timezone

VOLUME /tmp
# 加入打包好的jar文件(xxxxx改为自己文件名)
ADD ./target/demo-0.0.1-SNAPSHOT.jar /

ENTRYPOINT ["java","-Djava.security.egd=file:/dev/./urandom","-jar","/demo-0.0.1-SNAPSHOT.jar"]

运行命令docker build -t 自定义镜像名称 .(注意后面有个 . 不要漏掉),如果需要将该镜像加入我本地的harbor仓库(需要自己搭建),则镜像名称需要为: 仓库地址/名称:v版本号

如:192.168.123.45:8000/library/data_lake:v1.0

这里我们docker builde一下

docker build -t my-demo .

3.在本地docker运行打包好的镜像

使用命令docker run 运行镜像

 docker run -d --name test -p 8080:8080 my-demo

然后可以使用docker ps查看运行中的docker镜像
使用docker stop加上对应的容器的id就能够停止对应的镜像的运行

4.将docker推向镜像仓库

首先我们需要创建一个docker的账号,就能拥有一个docker远端的镜像仓库。我们给我们的镜像打一个tag,使用docker tag将本地原来的镜像推

 docker tag my-demo yangdocker1118/my-demo

然后使用docker push将本地的镜像推向远端

docker push yangdocker1118/my-demo

五、将demo镜像部署到kubernetes集群当中

1.创建一个namespace

创建namespace也有两种方式

  1. 使用yaml文件编写配置来进行创建
    apiVersion: v1
    kind: Namespace
    metadata:
      labels:
     istio-injection: enabled
      name: zelda
    status:
      phase: Active
    

    然后使用kc apply -f namespace.yaml就能创建一个名为zelda的namespace

  2. kubectl create namespace命令直接创建

2.创建deployment

这里我们同样也可以使用yaml配置的方式来创建deployment,也可以直接使用下面命令行的方式直接创建deployment拉取镜像进行部署(推荐还是本地自己重新搭建一个镜像仓库harbor,使用docker官方的镜像仓库拉镜像的速度太慢了)

kubectl create deployment my-demo --image=yangdocker1118/my-demo -n zelda

成功!Done!