k8s series 7: Deployment部署应用

702 阅读4分钟

这是我参与更文挑战的第4天,活动详情查看: 更文挑战

  Pod控制器中管理无状态应用,特别是业务类型应用,大多采用deployment控制器,接下来以一个简单的例子实际部署一下。

java项目Demo

使用springboot写了一个简单查询hive数据的demo,打成jar包。

hive配置

hive:
  url: jdbc:hive2://ip:10000/default
  driver-class-name: org.apache.hive.jdbc.HiveDriver
  type: com.alibaba.druid.pool.DruidDataSource
  username: hive
  password: hive

配置类

@Configuration
public class HiveDataSource {
    @Autowired
    private Environment environment;

    public HiveDataSource() {
    }

    @Bean(
        name = {"hiveDruidJdbcDataSource"}
    )
    @Qualifier("hiveDruidJdbcDataSource")
    public DataSource dataSource() {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setUrl(this.environment.getProperty("hive.url"));
        dataSource.setDriverClassName(this.environment.getProperty("hive.driver-class-name"));
        dataSource.setUsername(this.environment.getProperty("hive.username"));
        dataSource.setPassword(this.environment.getProperty("hive.password"));
        return dataSource;
    }

    @Bean(
        name = {"hiveDruidJdbcTemplate"}
    )
    public JdbcTemplate hiveJdbcTemplate(@Qualifier("hiveDruidJdbcDataSource") DataSource dataSource) {
        return new JdbcTemplate(dataSource);
    }
}

控制类

@RestController
@RequestMapping({"/hive"})
public class HiveController {
    private static final Logger logger = LoggerFactory.getLogger(HiveController.class);
    @Autowired
    @Qualifier("hiveJdbcTemplate")
    private JdbcTemplate hiveJdbcTemplate;

    public HiveController() {
    }

    @GetMapping({"/create"})
    public Map create() {
        StringBuffer sql = new StringBuffer("create table IF NOT EXISTS ");
        sql.append("HIVE_TEST");
        sql.append("(KEY INT, VALUE STRING)");
        sql.append("PARTITIONED BY (CTIME DATE)");
        sql.append("ROW FORMAT DELIMITED FIELDS TERMINATED BY '\t' LINES TERMINATED BY '\n' ");
        sql.append("STORED AS TEXTFILE");
        logger.info(sql.toString());
        this.hiveJdbcTemplate.execute(sql.toString());
        return new 1(this);
    }

    @GetMapping({"/insert"})
    public Map insert() {
        this.hiveJdbcTemplate.execute("set hive.exec.dynamic.partition.mode=nonstrict");
        this.hiveJdbcTemplate.execute("insert into HIVE_TEST (key, value) values  (1,'Chen')");
        return new 2(this);
    }

    @GetMapping({"/select"})
    public String select() {
        String sql = "select * from test_order_sample3";
        List<Map<String, Object>> rows = this.hiveJdbcTemplate.queryForList(sql);
        Iterator it = rows.iterator();

        while(it.hasNext()) {
            Map<String, Object> row = (Map)it.next();
            System.out.println(String.format("%s\t%s", row.get("key"), row.get("value")));
        }

        return "Done";
    }

    @GetMapping({"/delete"})
    public String Delete() {
        StringBuffer sql = new StringBuffer("DROP TABLE IF EXISTS");
        sql.append("HIVE_TEST");
        logger.info(sql.toString());
        this.hiveJdbcTemplate.execute(sql.toString());
        return "Done";
    }
}

打包

mvn clean package -Dmaven.test.skip=true 

制作docker image

编写Dockerfile配置将jar包制作成docker image

FROM java:8
VOLUME /tmp
ADD springboot-hive.jar app.jar 
ENTRYPOINT ["java","-Djava.security.egd=file:/dev/./urandom","-jar","/app.jar"]

上传私有仓库

将本地docker image上传到私有镜像仓库harbor, harbor部署见后续文章

docker tag springboot-hive:v1 harbor-test.libaigo.cn/dev/springboot-hive:v1
docker push harbor-test.libaigo.cn/dev/springboot-hive:v1

创建namespace

kubectl create namespace devops

 deployment yaml配置

apiVersion: apps/v1
kind: Deployment
metadata:
  name: springboot-hive
  namespace: devops
  labels:
    app: springboot
    version: "1.0"
spec:
  replicas: 3
  selector:
    matchLabels:
      app: springboot
  template:
    metadata:
      labels:
        app: springboot
        version: "1.0"
    spec:
      terminationGracePeriodSeconds: 30
      containers: 
      - name: springboot-hive
        image: harbor-test.libaigo.cn/dev/springboot-hive:v1
        imagePullPolicy: IfNotPresent
        resources:
          requests:
            cpu: 100m
            memory: 1Gi
        livenessProbe:
          tcpSocket:
            port: 8080
          initialDelaySeconds: 10
          periodSeconds: 60
        ports:
        - containerPort: 8080
          name: web
          protocol: TCP
  • 项目使用devops namespace

  • labels 标明了 app名称 和版本,也可以加上项目名称和以及相关特点,加以区分

  • 加了入优雅关闭策略(terminationGracePeriodSeconds),宽限期30s来优雅关闭pod,可视情况延长时间

  • 镜像拉取策略 选择使用本地镜像,不拉取,避免镜像更新自动拉取

  • 资源限制使用requests,CPU和内存 最大请求资源,这里没有写最小请求,也没有限制最大最小

  • 检查容器存活状态(livenessProbe),使用tcp协议和8080端口探测

  • 最后声明服务在pod中的端口和协议

运行以下命令创建部署

kubectl apply -f springboot-hi-deployment.yaml

查看deploy和pods状态

kubectl get deploy,po  -n devops -o wide

应用已经成功部署了(如果状态不是Running,可使用describe查看具体情况)

kubectl describe deploy/springboot-hive  -n devops

因为应用在k8s内部,如果你在k8s集群节点上,可以通过IP访问,但是外部是无法访问的

k8s集群内部访问

外部访问

为了让外部能够访问到,这里我们需要用到service 对象

Service yaml配置

apiVersion: v1
kind: Service
metadata:
  name: springboot-hive-service
  namespace: devops
  labels:
    app: springboot
    version: "1.0"
spec:
  type: NodePort
  ports:
    - port: 8080
      protocol: TCP
      nodePort: 30112
  selector:
    app: springboot
    version: "1.0"

这边我们使用NodePort类型来将 应用的8080端口映射到 k8s集群的 30112端口

运行以下命令创建部署

kubectl apply -f springboot-hive-service.yaml
kubectl get svc -o wide -n devops

可以看到service 已经生效, 访问集群任意节点  ip:30112 既可访问服务

查看日志

kubectl logs -f springboot-hive-7c844584f9-2v256 -n devops

登陆到容器

kubectl exec -it springboot-hive-7c844584f9-2v256 bash -n devops

查看deployment配置

kubectl get  deploy/springboot-hive -n devops  -o yaml

执行上述命令会在终端 以yaml格式输出 配置,也支持json

在线更改deployment配置

kubectl edit deploy/springboot-hive -n devops -o json

以json格式在线更改配置,保存既生效

动态扩缩容

kubectl scale deploy/springboot-hive --replicas=5 -n devops

在线镜像升级和回滚

kubectl set image deploy/springboot-hive springboot-hive=harbor-test.qupeiyin.cn/dev/springboot-hive:v2 -n devops

更新执行完成后,查看一下历史的部署记录

kubectl rollout history deploy/springboot-hive

如果历史部署记录没有或缺少,说明没有记录,在更新时加上--record

kubectl set image deploy/springboot-hive springboot-hive=harbor-test.qupeiyin.cn/dev/springboot-hive:v2 -n devops --record

如果记录条数较少,可以设置记录 多少次history

revisionHistoryLimit属性增加reviseion数量  revisionHistoryLimit: 10 和replicas同级

回滚操作,回滚到上一次版本

kubectl rollout undo deployment/springboot-hive -n devopskubectl rollout status deployment/springboot-hive -n devops

回滚指定版本

kubectl rollout undo deployment/springboot-hive --to-revision=2 -n devops

Rancher

 Rancher是个强大的k8s集群管理软件,上述所有操作 全部可以在界面上完成,见下图