package com.mini.capi.utils;

import com.jcraft.jsch.*;
import com.mini.capi.biz.domain.DockerContainerInfo;
import com.mini.capi.biz.domain.SshInfo;
import lombok.Data;

import java.io.*;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class docker {

    @Data
    public static class DockerInfo implements Serializable {
        private String containerId;
        private String imageName;
        private String command;
        private String createdAt;
        private String status;
        private String ports;
        private String names;

        @Override
        public String toString() {
            return "DockerContainerInfo{" +
                    "containerId='" + containerId + '\'' +
                    ", imageName='" + imageName + '\'' +
                    ", command='" + command + '\'' +
                    ", createdAt='" + createdAt + '\'' +
                    ", status='" + status + '\'' +
                    ", ports='" + ports + '\'' +
                    ", names='" + names + '\'' +
                    '}';
        }
    }

    public static List<DockerInfo> getDockerInfo(String host, Long port, String username, String password) {
        List<DockerInfo> containers = new ArrayList<>();
        JSch jsch = new JSch();
        Session session = null;
        try {
            // 1. 创建SSH会话
            session = jsch.getSession(username, host, Math.toIntExact(port));
            session.setPassword(password);
            session.setConfig("StrictHostKeyChecking", "no");
            session.connect();

            // 2. 执行docker ps命令获取所有容器信息
            String command = "docker ps -a --no-trunc --format \"{{.ID}}|{{.Image}}|{{.Command}}|{{.CreatedAt}}|{{.Status}}|{{.Ports}}|{{.Names}}\"";
            ChannelExec channel = (ChannelExec) session.openChannel("exec");
            channel.setCommand(command);
            channel.setInputStream(null);
            InputStream in = channel.getInputStream();
            BufferedReader reader = new BufferedReader(new InputStreamReader(in));

            channel.connect();

            // 3. 解析输出
            String line;
            while ((line = reader.readLine()) != null) {
                if (!line.trim().isEmpty()) {
                    DockerInfo container = parseContainerInfo(line);
                    if (container != null) {
                        containers.add(container);
                    }
                }
            }

            channel.disconnect();
        } catch (JSchException | IOException e) {
            System.out.println(e.getMessage());
        } finally {
            if (session != null && session.isConnected()) {
                session.disconnect();
            }
        }

        return containers;
    }

    private static DockerInfo parseContainerInfo(String line) {
        // 使用正则表达式分割管道分隔的字段
        Pattern pattern = Pattern.compile("([^|]*)\\|([^|]*)\\|([^|]*)\\|([^|]*)\\|([^|]*)\\|([^|]*)\\|([^|]*)");
        Matcher matcher = pattern.matcher(line);
        if (matcher.find()) {
            DockerInfo container = new DockerInfo();
            container.setContainerId(matcher.group(1).trim());
            container.setImageName(matcher.group(2).trim());
            container.setCommand(matcher.group(3).trim());
            container.setCreatedAt(vDate.getDockerCreate(matcher.group(4).trim()));
            container.setStatus(getStatus(matcher.group(5).trim()));
            container.setPorts(matcher.group(6).trim());
            container.setNames(matcher.group(7).trim());
            return container;
        }
        return null;
    }

    private static String dockerCommand(String host, Long port, String username, String password, String command) {
        JSch jsch = new JSch();
        Session session = null;
        ChannelExec channel = null;
        // 读取输出
        StringBuilder output = new StringBuilder();
        try {
            // 创建SSH会话
            session = jsch.getSession(username, host, Math.toIntExact(port));
            session.setPassword(password);
            session.setConfig("StrictHostKeyChecking", "no");
            session.connect();
            // 执行Docker命令
            channel = (ChannelExec) session.openChannel("exec");
            channel.setCommand(command);
            channel.setInputStream(null);
            InputStream in = channel.getInputStream();
            BufferedReader reader = new BufferedReader(new InputStreamReader(in));
            channel.connect();
            String line;
            while ((line = reader.readLine()) != null) {
                output.append(line).append("\n");
            }
            channel.disconnect();
        } catch (JSchException | IOException e) {
            System.out.println(e.getMessage());
        } finally {
            if (session != null && session.isConnected()) {
                session.disconnect();
            }
        }
        return output.toString();
    }

    public static DockerContainerInfo getDockerContainerInfo(String dockerHostId, docker.DockerInfo dockerInfo, SshInfo sshInfo) {
        DockerContainerInfo info = new DockerContainerInfo();
        info.setContainerId(dockerInfo.getContainerId());
        info.setImageName(dockerInfo.getImageName());
        info.setCreatedAt(dockerInfo.getCreatedAt());
        info.setUstatus(dockerInfo.getStatus());
        info.setPorts(dockerInfo.getPorts());
        info.setUnames(dockerInfo.getNames());
        info.setHostIp(sshInfo.getHostIp());
        info.setDokerHostId(dockerHostId);
        info.setGetTime(vDate.getNow());
        info.setFTenantId("0");
        return info;
    }


    public static String startDocker(String host, Long port, String username, String password, String containerId) {
        return dockerCommand(host, port, username, password, "docker start " + containerId);
    }

    public static String stopDocker(String host, Long port, String username, String password, String containerId) {
        return dockerCommand(host, port, username, password, "docker stop " + containerId);
    }

    private static String getStatus(String start) {
        if (start.toUpperCase().startsWith("UP")) {
            return "1";
        }
        return "0";
    }
}
