Java 整合常用docker Api

整合环境:

  • 与docker 版本差异不大,基本都可以
 API version:     1.26

开放docker api ,两种方式

  • /etc/sysconfig/docker ,最后一行添加;开放端口:2375
    -H tcp://0.0.0.0:2375
  • systemctl status docker 查询 docker.service 路径
    vi /lib/systemd/system/docker.service
    -H tcp://0.0.0.0:2375
    Java 整合常用docker Api_第1张图片

重启docker

  • systemctl daemon-reload && systemctl restart docker
    开放端口:
  • irewall-cmd --zone=public --add-port=2375/tcp --permanent
    测试API:
  • GET ip:2375/images/json

Java client 对接 docker api

<dependency>
      <groupId>com.github.docker-javagroupId>
      <artifactId>docker-javaartifactId>
      <version>3.3.0version>
 dependency>

初始化client

import com.github.dockerjava.api.DockerClient;
import com.github.dockerjava.core.DockerClientBuilder;
import lombok.extern.slf4j.Slf4j;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;
import javax.annotation.Resource;

/**
 * @author xiaoshu
 * @description docker client初始化
 * @date 2023年03月19日 15:31
 */
@Slf4j
@Component
public class DockerApiConfig {

    @Resource
    private VirtualProperties virtualProperties;

    @Bean
    public DockerClient dockerClient(){
        String url=virtualProperties.getDockerUrl();
        //String url="tcp://192.168.1.250:2375";
        DockerClient dockerClient = DockerClientBuilder.getInstance(url).build();
        log.info("docker API初始化成功");
        return dockerClient;
    }

}

常用api封装

import com.github.dockerjava.api.model.Container;
import com.github.dockerjava.api.model.Image;
import com.param.ImageParam;
import com.vo.DockerBuildImageVo;
import com.vo.DockerContainerVo;
import com.vo.DockerPushVo;
import java.io.InputStream;
import java.util.List;

/**
 * java-client docker-api 相关接口
 *
 * @author heyonghao
 * @date 2023/4/12
 */
public interface DockerService {

    /**
     * 容器列表
     * @return List
     */
    List<Container> listContainer(Boolean showAll);

    /**
     * 查询容器日志信息
     * @param containerId 容器id
     * @param tail 行数
     * @return List
     */
    List<String> logContainer(String containerId,Integer tail);

    /**
     * 查询容器详情,返回vo待定
     * @param containerId
     * @return
     */
    String infoContainer(String containerId);

    /**
     * 删除容器
     * @param containerId 容器id
     * @return Boolean
     */
    Boolean removeContainer(String containerId);

    /**
     * 停止容器
     * @param containerId 容器id
     * @return Boolean
     */
    Boolean stopContainer(String containerId);

    /**
     * 启动容器
     * @param containerId 容器id
     * @return Boolean
     */
    Boolean startContainer(String containerId);

    /**
     * 创建容器
     * @param dockerContainerVo dockerContainerVo
     * @return Boolean
     */
    Boolean createContainer(DockerContainerVo dockerContainerVo);

    /**
     * 镜像列表
     * @param imageParam
     * @return List
     */
    List<Image> images(ImageParam imageParam);

    /**
     * 镜像详情
     * 返回vo待封装
     * @param imageId 镜像id
     * @return Image
     */
    String imageInfo(String imageId);

    /**
     * 导入镜像文件
     * @param tarInputStream 镜像tar文件流
     * @return Boolean
     */
    Boolean importImage(InputStream tarInputStream);

    /**
     * 镜像构建vo
     * @param dockerBuildImageVo 构建参数
     * @return Boolean
     */
    Boolean buildImage(DockerBuildImageVo dockerBuildImageVo);

    /**
     * 推送本地镜像到 harbor 仓库
     * @param dockerPushVo 推送参数
     * @return Boolean
     */
    Boolean pushDockerImageToHarbor(DockerPushVo dockerPushVo);

}
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.StrUtil;
import com.config.VirtualProperties;
import com.github.dockerjava.api.DockerClient;
import com.github.dockerjava.api.command.*;
import com.github.dockerjava.api.model.*;
import com.github.dockerjava.core.command.LogContainerResultCallback;
import com.param.ImageParam;
import com.service.DockerService;
import com.vo.DockerBuildImageVo;
import com.vo.DockerContainerVo;
import com.vo.DockerPushVo;
import com.vo.LabelsOrKvVo;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.io.File;
import java.io.InputStream;
import java.util.*;

/**
 * xxx
 *
 * @author heyonghao
 * @date 2023/4/12
 */
@Slf4j
@Service
public class DockerServiceImpl implements DockerService {
    @Resource
    private DockerClient dockerClient;

    @Resource
    private VirtualProperties virtualProperties;

    @Override
    public List<Container> listContainer(Boolean showAll) {
        ListContainersCmd listContainersCmd = dockerClient.listContainersCmd();
        ListContainersCmd containersCmd = listContainersCmd.withShowAll(showAll);
        return containersCmd.exec();
    }

    @Override
    public List<String> logContainer(String containerId, Integer tail) {
        List<String> logs = new LinkedList<>();
        LogContainerCmd logContainerCmd = dockerClient.logContainerCmd(containerId);
        logContainerCmd.withStdOut(true).withStdErr(true);
        //显示行数
        logContainerCmd.withTail(10);
        try {
            logContainerCmd.exec(new LogContainerResultCallback() {
                @Override
                public void onNext(Frame item) {
                    logs.add(item.toString());
                }
            }).awaitCompletion();
        } catch (InterruptedException e) {
            throw new RuntimeException("Failed to retrieve logs of container " + containerId, e);
        }
        return logs;
    }

    @Override
    public String infoContainer(String containerId) {
        InspectContainerCmd inspectContainerCmd = dockerClient.inspectContainerCmd(containerId);
        InspectContainerResponse response = inspectContainerCmd.exec();
        return response.toString();
    }

    @Override
    public Boolean removeContainer(String containerId) {
        RemoveContainerCmd removeContainerCmd = dockerClient.removeContainerCmd(containerId);
        try {
            removeContainerCmd.exec();
        }catch (Exception e){
            e.printStackTrace();
            return Boolean.FALSE;
        }
        return Boolean.TRUE;
    }

    @Override
    public Boolean stopContainer(String containerId) {
        StopContainerCmd stopContainerCmd = dockerClient.stopContainerCmd(containerId);
        try {
            stopContainerCmd.exec();
        }catch (Exception e){
            e.printStackTrace();
            return Boolean.FALSE;
        }
        return Boolean.TRUE;
    }

    @Override
    public Boolean startContainer(String containerId) {
        StartContainerCmd startContainerCmd = dockerClient.startContainerCmd(containerId);
        try {
            startContainerCmd.exec();
        }catch (Exception e){
            e.printStackTrace();
            return Boolean.FALSE;
        }
        return Boolean.TRUE;
    }

    @Override
    public Boolean createContainer(DockerContainerVo dockerContainerVo) {
        //会在服务器目录: home/dockerdata/docker/tmp ,上传打包容器文件
        String containerName = dockerContainerVo.getContainerName();
        if (StrUtil.isEmpty(containerName)){
            return Boolean.FALSE;
        }
        CreateContainerCmd containerCmd = dockerClient.createContainerCmd(containerName);
        containerCmd.withImage(dockerContainerVo.getImageName());
        containerCmd.withName(containerName);
        HostConfig hostConfig=HostConfig.newHostConfig();

        List<LabelsOrKvVo> exposePorts = dockerContainerVo.getExposePorts();
        exposePorts.forEach(e->{
            ExposedPort tcp8300 = ExposedPort.tcp(Integer.parseInt(e.getValue()));
            Ports portBindings = new Ports();
            portBindings.bind(tcp8300, Ports.Binding.bindPort(Integer.parseInt(e.getKey())));
            hostConfig.withPortBindings(portBindings);
            containerCmd.withExposedPorts(tcp8300);
        });
        List<LabelsOrKvVo> volumePaths = dockerContainerVo.getVolumePath();
        if (CollectionUtil.isEmpty(volumePaths)){
            return Boolean.FALSE;
        }
        List<Bind> binds = new LinkedList<>();
        volumePaths.forEach(e->{
            Bind bind = new Bind(e.getKey(),new Volume(e.getValue()));
            binds.add(bind);
        });
        containerCmd.withHostConfig(hostConfig);
        hostConfig.setBinds(binds.toArray(new Bind[]{}));
        try {
            containerCmd.exec();
        }catch (Exception e){
            e.printStackTrace();
            return Boolean.FALSE;
        }
        return Boolean.TRUE;
    }

    @Override
    public List<Image> images(ImageParam imageParam) {
        ListImagesCmd imagesCmd = dockerClient.listImagesCmd();
        List<LabelsOrKvVo> labelsOrKvVo = imageParam.getLabelsOrKvVo();
        if (CollectionUtil.isNotEmpty(labelsOrKvVo)){
            Map<String,String> lables = new HashMap<>(labelsOrKvVo.size());
            labelsOrKvVo.forEach(e->{
                lables.put(e.getKey(), e.getValue());
            });
            imagesCmd.withLabelFilter(lables);
        }
        if (StrUtil.isNotEmpty(imageParam.getName())){
            imagesCmd.withImageNameFilter(imageParam.getName());
        }
        ListImagesCmd all = imagesCmd.withShowAll(false);
        return all.exec();
    }

    @Override
    public String imageInfo(String imageId) {
        InspectImageCmd imageCmd = dockerClient.inspectImageCmd(imageId);
        InspectImageResponse response = imageCmd.exec();
        return response.toString();
    }

    @Override
    public Boolean importImage(InputStream tarInputStream) {
        dockerClient.loadImageCmd(tarInputStream).exec();
        return Boolean.TRUE;
    }

    @Override
    public Boolean buildImage(DockerBuildImageVo dockerBuildImageVo) {
        boolean flag =true;
        try {
            String dockerFilePath = dockerBuildImageVo.getDockerFilePath();
            if (StrUtil.isEmpty(dockerFilePath)){
                return false;
            }
            List<LabelsOrKvVo> tagsVo = dockerBuildImageVo.getTags();
            Set<String> tags = new HashSet<>();
            if (CollectionUtil.isNotEmpty(tagsVo)){
                tagsVo.forEach(e->{
                    String curTag = String.format("%s:%s", e.getKey(), e.getValue());
                    tags.add(curTag);
                });
            }
            List<LabelsOrKvVo> labelsVo = dockerBuildImageVo.getLabels();
            Map<String,String> labels = new HashMap<>(2);
            if (CollectionUtil.isNotEmpty(labelsVo)){
                //添加元数据,user-id 或者 xxx-id 与本地数据绑定起来
                labelsVo.forEach(e->{
                    labels.put(e.getKey(),e.getValue());
                });
            }
            BuildImageCmd buildImageCmd = dockerClient
                    .buildImageCmd(new File(dockerFilePath))
                    .withLabels(labels)
                    .withTags(tags);
            BuildImageResultCallback callback = new BuildImageResultCallback();
            buildImageCmd.exec(callback);
            String imageId = callback.awaitImageId();
            System.out.println("镜像创建成功,镜像id:"+imageId);
        } catch (Exception e) {
            flag=false;
            e.printStackTrace();
        }
        return flag;
    }

    @Override
    public Boolean pushDockerImageToHarbor(DockerPushVo dockerPushVo) {
        AuthConfig autoConfig = new AuthConfig().withRegistryAddress(virtualProperties.getHarborUrl())
                .withUsername(virtualProperties.getHarborUname()).withPassword(virtualProperties.getHarborPwd());
        String localImg=dockerPushVo.getImageName()+":"+dockerPushVo.getImageTag();
        String pushImg=virtualProperties.getHarborUrl()+"/"+dockerPushVo.getPushProject()+"/"+dockerPushVo.getImageName();
        dockerClient.tagImageCmd(localImg,pushImg,dockerPushVo.getPushImgVersion()).exec();
        String pushTo=virtualProperties.getHarborUrl()+"/"+dockerPushVo.getPushProject()+"/"+dockerPushVo.getImageName()+":"+dockerPushVo.getPushImgVersion();
        try {
            dockerClient.pushImageCmd(pushTo).withAuthConfig(autoConfig).start().awaitCompletion();
        } catch (InterruptedException e) {
            log.info(e.getMessage());
            return Boolean.FALSE;
        }
        return Boolean.TRUE;
    }
}

涉及vo

import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.io.Serializable;
import java.util.List;

/**
 * @author xiaoshu
 * @description
 * @date 2023年05月01日 15:23
 */
@Data
@ApiModel(value = "镜像构建Vo")
public class DockerBuildImageVo implements Serializable {
    private static final long serialVersionUID = -6058239843827052127L;

    @ApiModelProperty(value = "tags")
    List<LabelsOrKvVo> tags;

    @ApiModelProperty(value = "labels")
    List<LabelsOrKvVo> labels;

    @ApiModelProperty(value = "镜像文件路径;最后是 docker与镜像文件单独放一个目录")
    private String dockerFilePath;

}
@ApiModel(value = "docker 容器创建VO")
@Data
public class DockerContainerVo implements Serializable {
    private static final long serialVersionUID = 5791026160216793895L;

    @ApiModelProperty(value = "容器名称")
    private String containerName;

    @ApiModelProperty(value = "镜像名称:tag")
    private String imageName;

    @ApiModelProperty(value = "暴露端口 容器端口 :内部端口")
    private List<LabelsOrKvVo> exposePorts;

    @ApiModelProperty(value = "挂载路径  主机路径 :容器路径")
    private List<LabelsOrKvVo> volumePath;
}
@ApiModel(value = "k-v Vo")
@Data
public class LabelsOrKvVo implements Serializable {

    @ApiModelProperty(value = "标签key")
    private String key;
    @ApiModelProperty(value = "标签value")
    private String value;

}
@ApiModel(value = "docker 镜像推送VO")
@Data
public class DockerPushVo implements Serializable {

    @ApiModelProperty(value = "原镜像名称")
    private String imageName;

    @ApiModelProperty(value = "原镜像tag")
    private String imageTag;

    @ApiModelProperty(value = "推送项目名称")
    private String pushProject;

    @ApiModelProperty(value = "推送后镜像版本号")
    private String pushImgVersion;

}

yml 配置

virtual:
  docker-url: tcp://192.168.2.207:8088
  k8s-url: https://192.168.2.207:6443
  k8s-token: xxx
  server-url: 192.168.2.207
  server-name: root
  server-pwd: 123456
  harbor-url: core.harbor.domain
  harbor-uname: admin
  harbor-pwd: Harbor12345
@Data
@ConfigurationProperties(prefix = "virtual")
@Configuration
public class VirtualProperties {

    /**
     * docker服务地址
     */
    private String dockerUrl;
    /**
     * k8s服务地址
     */
    private String k8sUrl;
    /**
     * k8s服务token
     */
    private String k8sToken;
    /**
     * 服务器地址
     */
    private String serverUrl;
    /**
     * 服务器账号
     */
    private String serverName;
    /**
     * 服务器账号密码
     */
    private String serverPwd;
    /**
     * harbor私有仓库地址
     */
    private String harborUrl;
    /**
     * harbor 账号
     */
    private String harborUname;
    /**
     * harbor 密码
     */
    private String harborPwd;

}

你可能感兴趣的:(java,docker)