<template>
    <x-search-bar class="mb-8-2">
        <template #default="{ gutter, colSpan }">
            <a-form :model="searchFormData" layout="inline">
                <a-row :gutter="gutter">
                    <a-col v-bind="colSpan">
                        <a-form-item label="用户ID" name="user_id">
                            <a-input placeholder="请输入用户ID" v-model:value="searchFormData.user_id"></a-input>
                        </a-form-item>
                    </a-col>
                    <a-col v-bind="colSpan">
                        <a-form-item label="实例ID" name="instance_id">
                            <a-input placeholder="请输入实例ID" v-model:value="searchFormData.instance_id"></a-input>
                        </a-form-item>
                    </a-col>
                    <a-col class="align-right" v-bind="colSpan">
                        <a-space>
                            <a-button @click="handleResetSearch">重置</a-button>
                            <a-button ghost type="primary" @click="handleSearch">
                                搜索
                            </a-button>
                        </a-space>
                    </a-col>
                </a-row>
            </a-form>
        </template>
    </x-search-bar>
    <a-row :gutter="8" :wrap="false">
        <a-col flex="auto">
            <a-card type="flex">
                <!-- <x-action-bar class="mb-8-2">
                    <a-button type="primary" @click="handleExportInstances">
                        <template #icon>
                            <ExportOutlined />
                        </template>
                        导出实例列表
                    </a-button>
                </x-action-bar> -->
                <a-table :columns="columns" :data-source="listData" :loading="loading" :pagination="paginationState"
                    :scroll="{ x: 1600 }" rowKey="id" @change="onTableChange">
                    <template #bodyCell="{ column, record }">
                        <!-- 用户名/用户ID -->
                        <template v-if="'user_info' === column.key">
                            <div class="user-info-cell">
                                <div>自己</div>
                                <div class="text-secondary">{{ record.id?.substring(0, 12) || '--' }}</div>
                            </div>
                        </template>

                        <!-- 实例ID/名称 -->
                        <template v-if="'instance_info' === column.key">
                            <div class="instance-info-cell">
                                <div>{{ record.machine_name || '--' }}</div>
                                <div class="text-secondary">{{ record.instance_uuid || '--' }}</div>
                            </div>
                        </template>

                        <!-- 规格详情 -->
                        <template v-if="'spec_detail' === column.key">
                            <div class="spec-detail-cell">
                                <div>{{ formatGPUSpec(record) }}</div>
                                <a-button type="link" size="small" @click="handleViewSpecDetail(record)">
                                    查看详情
                                </a-button>
                            </div>
                        </template>

                        <!-- 状态 -->
                        <template v-if="'status' === column.key">
                            <a-tag :color="getStatusColor(record.status)">
                                {{ getStatusText(record.status) }}
                            </a-tag>
                        </template>

                        <!-- 磁盘使用 -->
                        <template v-if="'disk_usage' === column.key">
                            <div class="disk-usage-cell">
                                <div>系统盘 {{ formatDiskUsage(record) }}</div>
                                <div>数据盘 {{ formatDiskUsage(record) }}</div>
                            </div>
                        </template>

                        <!-- 健康状态 -->
                        <template v-if="'health_status' === column.key">
                            <a-tag :color="getDiskHealthStatusColor(record.disk_health_status)">
                                {{ getDiskHealthStatusText(record.disk_health_status) }}
                            </a-tag>
                        </template>

                        <!-- 创建时间 -->
                        <template v-if="'created_at' === column.key">
                            {{ formatDateTime(record.created_at) }}
                        </template>

                        <!-- SSH登录 -->
                        <template v-if="'ssh_login' === column.key">
                            <div class="ssh-login-cell">
                                <a-space direction="vertical" size="small">
                                    <a-button type="link" size="small" @click="handleOpenJupyterLab(record)">
                                        JupyterLab
                                    </a-button>
                                    <a-button type="link" size="small" @click="handleOpenAutoPanel(record)">
                                        AutoPanel
                                    </a-button>
                                    <a-button type="link" size="small" @click="handleOpenInstanceMonitor(record)">
                                        实例监控
                                    </a-button>
                                </a-space>
                            </div>
                        </template>

                        <!-- 快捷工具 -->
                        <template v-if="'quick_tools' === column.key">
                            <div class="quick-tools-cell">
                                <a-space direction="vertical" size="small">
                                    <a-button type="link" size="small" danger @click="handleShutdownInstance(record)"
                                        :disabled="record.status !== 'running'">
                                        关机
                                    </a-button>
                                </a-space>
                            </div>
                        </template>

                        <!-- 操作 -->
                        <!-- <template v-if="'action' === column.key">
                            <div class="action-cell">
                                <a-space>
                                    <a-button type="link" size="small" @click="handleStartInstance(record)"
                                        :disabled="record.status === 'running'">
                                        启动
                                    </a-button>
                                    <a-button type="link" size="small" @click="handleRestartInstance(record)"
                                        :disabled="record.status !== 'running'">
                                        重启
                                    </a-button>
                                    <a-button type="link" size="small" danger @click="handleStopInstance(record)"
                                        :disabled="record.status !== 'running'">
                                        停止
                                    </a-button>
                                    <a-dropdown>
                                        <template #overlay>
                                            <a-menu>
                                                <a-menu-item @click="handleViewLogs(record)">
                                                    查看日志
                                                </a-menu-item>
                                                <a-menu-item @click="handleTerminal(record)">
                                                    终端连接
                                                </a-menu-item>
                                                <a-menu-item danger @click="handleDeleteInstance(record)">
                                                    删除实例
                                                </a-menu-item>
                                            </a-menu>
                                        </template>
                                        <a-button type="link" size="small">
                                            更多
                                            <DownOutlined />
                                        </a-button>
                                    </a-dropdown>
                                </a-space>
                            </div>
                        </template> -->
                    </template>
                </a-table>
            </a-card>
        </a-col>
    </a-row>
    <a-modal v-model:visible="specModalVisible" title="实例规格详情" width="700px" :footer="null"
        @cancel="specModalVisible = false">
        <div v-html="specDetailContent"></div>
    </a-modal>
</template>

<script setup>
import { message, Modal } from 'ant-design-vue'
import { ref, computed } from 'vue'
import apis from '@/apis'
import { formatUtcDateTime } from '@/utils/util'
import { config } from '@/config'
import { usePagination, useForm } from '@/hooks'
import { ExportOutlined, DownOutlined } from '@ant-design/icons-vue'

defineOptions({
    name: 'instanceManagement',
})

// 表格列定义
const columns = [
    {
        title: '用户名/用户ID',
        key: 'user_info',
        width: 150,
        fixed: 'left'
    },
    {
        title: '实例ID/名称',
        key: 'instance_info',
        width: 180
    },
    {
        title: '规格详情',
        key: 'spec_detail',
        width: 180
    },
    {
        title: '状态',
        key: 'status',
        width: 100
    },
    {
        title: '磁盘使用',
        key: 'disk_usage',
        width: 140
    },
    {
        title: '健康状态',
        key: 'health_status',
        width: 100
    },
    {
        title: '创建时间',
        key: 'created_at',
        width: 160
    },
    {
        title: 'SSH登录',
        key: 'ssh_login',
        width: 140
    },
    {
        title: '快捷工具',
        key: 'quick_tools',
        width: 100
    },
    // {
    //     title: '操作',
    //     key: 'action',
    //     fixed: 'right',
    //     width: 240
    // },
]

// 状态映射
const statusMap = {
    'running': { text: '运行中', color: 'green' },
    'stopped': { text: '已停止', color: 'default' },
    'starting': { text: '启动中', color: 'processing' },
    'stopping': { text: '停止中', color: 'orange' },
    'error': { text: '异常', color: 'red' },
    'creating': { text: '创建中', color: 'processing' },
    'deleting': { text: '删除中', color: 'orange' },
    'paused': { text: '已暂停', color: 'warning' },
    'exited': { text: '已退出', color: 'default' },
}

// 磁盘健康状态映射
const diskHealthStatusMap = {
    'normal': { text: '正常', color: 'green' },
    'warning': { text: '警告', color: 'orange' },
    'error': { text: '异常', color: 'red' },
    'abnormal': { text: '异常', color: 'red' },
}

// 使用分页和数据获取钩子
const { listData, loading, showLoading, hideLoading, paginationState, searchFormData, resetPagination } =
    usePagination()
const { resetForm } = useForm()

// 弹窗相关
const specModalVisible = ref(false)
const currentRecord = ref(null)

// 计算规格详情内容
const specDetailContent = computed(() => {
    if (!currentRecord.value) return ''
    return getSpecDetailContent(currentRecord.value)
})

// 工具函数
function getStatusText(status) {
    return statusMap[status]?.text || status || '未知'
}

function getStatusColor(status) {
    return statusMap[status]?.color || 'default'
}

function getDiskHealthStatusText(status) {
    return diskHealthStatusMap[status]?.text || status || '正常'
}

function getDiskHealthStatusColor(status) {
    return diskHealthStatusMap[status]?.color || 'green'
}

// 格式化日期时间
function formatDateTime(dateTimeStr) {
    if (!dateTimeStr) return ''
    try {
        const date = new Date(dateTimeStr)
        return date.toLocaleString('zh-CN', {
            year: 'numeric',
            month: '2-digit',
            day: '2-digit',
            hour: '2-digit',
            minute: '2-digit',
            second: '2-digit',
            hour12: false
        }).replace(/\//g, '-')
    } catch (e) {
        return dateTimeStr
    }
}

// 格式化资源大小（字节转GB）
function formatBytesToGB(bytes) {
    if (!bytes && bytes !== 0) return '0GB'
    const gb = bytes / (1024 * 1024 * 1024)
    return `${gb.toFixed(2)}GB`
}

// 格式化百分比
function formatPercent(decimal) {
    if (decimal === undefined || decimal === null) return '0.00%'
    return `${(decimal * 100).toFixed(2)}%`
}

// 规格详情相关函数
function formatGPUSpec(record) {
    if (!record.gpu_name) return '--'

    const gpuName = record.gpu_name
    const gpuAmount = record.req_gpu_amount || 1
    return `${gpuName} * ${gpuAmount}`
}

// 磁盘使用格式化
function formatDiskUsage(record) {
    const usedRate = record.root_fs_used_rate || 0
    return `${formatPercent(usedRate)}`
}

// 获取规格详情内容HTML
function getSpecDetailContent(record) {
    const cpuUsage = record.cpu_usage_percent || 0
    const memUsage = record.mem_usage_percent || 0
    const memUsageBytes = record.mem_usage || 0
    const memLimitBytes = record.mem_limit_in_byte || record.mem_limit || 0

    // 计算CPU核心数和内存
    const cpuCores = record.cpu_limit || 0
    const memoryGB = (memLimitBytes / (1024 * 1024 * 1024)).toFixed(1)

    return `
        <div style="margin-top: 16px; line-height: 1.8;">
            
            <div style="background: #f6f8fa; padding: 12px; border-radius: 4px; margin-bottom: 16px;">
                <h5 style="margin: 0 0 8px 0; color: #666;">GPU配置</h5>
                <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 8px 16px;">
                    <div><strong>GPU型号：</strong>${record.gpu_name || '--'}</div>
                    <div><strong>GPU数量：</strong>${record.req_gpu_amount || 1}</div>
                    ${record.gpu_all_num ? `<div><strong>主机总GPU：</strong>${record.gpu_all_num}</div>` : ''}
                    ${record.gpu_idle_num !== undefined ? `<div><strong>主机空闲GPU：</strong>${record.gpu_idle_num}</div>` : ''}
                </div>
            </div>
            
            <div style="background: #f6f8fa; padding: 12px; border-radius: 4px; margin-bottom: 16px;">
                <h5 style="margin: 0 0 8px 0; color: #666;">CPU配置</h5>
                <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 8px 16px;">
                    <div><strong>CPU核心数：</strong>${cpuCores}核</div>
                    <div><strong>CPU使用率：</strong>${formatPercent(cpuUsage)}</div>
                </div>
            </div>
            
            <div style="background: #f6f8fa; padding: 12px; border-radius: 4px; margin-bottom: 16px;">
                <h5 style="margin: 0 0 8px 0; color: #666;">内存配置</h5>
                <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 8px 16px;">
                    <div><strong>内存大小：</strong>${formatBytesToGB(memLimitBytes)}</div>
                    <div><strong>内存使用率：</strong>${formatPercent(memUsage)}</div>
                    <div><strong>已用内存：</strong>${formatBytesToGB(memUsageBytes)}</div>
                    <div><strong>剩余内存：</strong>${formatBytesToGB(memLimitBytes - memUsageBytes)}</div>
                </div>
            </div>
            
            <div style="background: #f6f8fa; padding: 12px; border-radius: 4px; margin-bottom: 16px;">
                <h5 style="margin: 0 0 8px 0; color: #666;">磁盘配置</h5>
                <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 8px 16px;">
                    <div><strong>系统盘大小：</strong>${formatBytesToGB(record.root_fs_total_size)}</div>
                    <div><strong>系统盘使用率：</strong>${formatPercent(record.root_fs_used_rate)}</div>
                    <div><strong>系统盘已用：</strong>${formatBytesToGB(record.root_fs_used_size)}</div>
                    <div><strong>系统盘剩余：</strong>${formatBytesToGB(record.root_fs_total_size - record.root_fs_used_size)}</div>
                    ${record.usage_info?.data_disk_total_size ? `
                        <div><strong>数据盘大小：</strong>${formatBytesToGB(record.usage_info.data_disk_total_size)}</div>
                        <div><strong>数据盘使用率：</strong>${formatPercent(record.root_fs_used_rate)}</div>
                        <div><strong>数据盘已用：</strong>${formatBytesToGB(record.usage_info.data_disk_used_size)}</div>
                        <div><strong>数据盘剩余：</strong>${formatBytesToGB(record.usage_info.data_disk_total_size - record.usage_info.data_disk_used_size)}</div>
                    ` : ''}
                </div>
            </div>
            
            <div style="background: #f6f8fa; padding: 12px; border-radius: 4px;">
                <h5 style="margin: 0 0 8px 0; color: #666;">其他信息</h5>
                <div style="display: grid; grid-template-columns: 1fr 1fr; gap: 8px 16px;">
                    <div><strong>镜像：</strong>${record.image || '--'}</div>
                    <div><strong>启动模式：</strong>${record.start_mode || '--'}</div>
                    <div><strong>共享内存：</strong>${formatBytesToGB(record.shm_size)}</div>
                    <div><strong>启动时间：</strong>${record.started_at?.Valid ? formatDateTime(record.started_at.Time) : '--'}</div>
                    ${record.machine_name ? `<div><strong>所在主机：</strong>${record.machine_name}</div>` : ''}
                    ${record.machine_id ? `<div><strong>主机ID：</strong>${record.machine_id}</div>` : ''}
                    ${record.ssh_command ? `<div style="grid-column: 1 / -1;"><strong>SSH命令：</strong><br><code style="background: #f0f0f0; padding: 4px 8px; border-radius: 3px; font-family: monospace; word-break: break-all;">${record.ssh_command}</code></div>` : ''}
                </div>
            </div>
        </div>
    `
}

// 初始化加载数据
getPageList()

/**
 * 获取实例列表
 */
async function getPageList() {
    try {
        showLoading()
        const { pageSize, current } = paginationState
        const { success, data, total } = await apis.resource
            .getInstancesList({
                pageSize,
                current: current,
                ...searchFormData.value,
            })
            .catch(() => {
                throw new Error()
            })
        hideLoading()
        if (config('http.code.success') === success) {
            listData.value = data
            paginationState.total = total
        }
    } catch (error) {
        hideLoading()
        console.error('获取实例列表失败:', error)
        message.error('获取实例列表失败')
    }
}

/**
 * 查看规格详情
 */
function handleViewSpecDetail(record) {
    currentRecord.value = record
    specModalVisible.value = true
}

/**
 * 打开JupyterLab
 */
function handleOpenJupyterLab(record) {
    if (record.jupyter_port && record.jupyter_token) {
        const jupyterUrl = `http://${record.proxy_host}:${record.jupyter_port}/?token=${record.jupyter_token}`
        window.open(jupyterUrl, '_blank')
        message.success('正在打开JupyterLab...')
    } else {
        message.warning('JupyterLab未启用或配置不完整')
    }
}

/**
 * 打开AutoPanel
 */
function handleOpenAutoPanel(record) {
    if (record.proxy_host) {
        const autoPanelUrl = `http://${record.proxy_host}/autopanel/${record.instance_uuid}`
        window.open(autoPanelUrl, '_blank')
        message.success('正在打开AutoPanel...')
    } else {
        message.warning('AutoPanel未配置')
    }
}

/**
 * 打开实例监控
 */
function handleOpenInstanceMonitor(record) {
    if (record.instance_uuid) {
        const monitorUrl = `/monitor/instance/${record.instance_uuid}`
        window.open(monitorUrl, '_blank')
        message.success('正在打开实例监控...')
    } else {
        message.warning('实例ID不存在')
    }
}

/**
 * 关机实例
 */
function handleShutdownInstance(record) {
    Modal.confirm({
        title: '确认关机',
        content: `确定要关机实例 ${record.instance_uuid || record.machine_name} 吗？关机后实例将停止运行。`,
        okText: '确认关机',
        cancelText: '取消',
        okType: 'danger',
        onOk: () => {
            return new Promise((resolve, reject) => {
                ; (async () => {
                    try {
                        const { success, message: msg } = await apis.instance.shutdownInstance(record.id).catch(() => {
                            throw new Error('API调用失败')
                        })
                        if (config('http.code.success') === success) {
                            resolve()
                            message.success(msg || '关机命令已发送')
                            setTimeout(() => {
                                getPageList()
                            }, 2000)
                        } else {
                            reject(new Error(msg || '关机失败'))
                        }
                    } catch (error) {
                        reject(error)
                        message.error(error.message || '关机失败')
                    }
                })()
            })
        },
    })
}

/**
 * 启动实例
 */
function handleStartInstance(record) {
    Modal.confirm({
        title: '确认启动',
        content: `确定要启动实例 ${record.instance_uuid || record.machine_name} 吗？`,
        okText: '确认启动',
        cancelText: '取消',
        onOk: () => {
            return new Promise((resolve, reject) => {
                ; (async () => {
                    try {
                        const { success, message: msg } = await apis.instance.startInstance(record.id).catch(() => {
                            throw new Error('API调用失败')
                        })
                        if (config('http.code.success') === success) {
                            resolve()
                            message.success(msg || '启动命令已发送')
                            setTimeout(() => {
                                getPageList()
                            }, 2000)
                        } else {
                            reject(new Error(msg || '启动失败'))
                        }
                    } catch (error) {
                        reject(error)
                        message.error(error.message || '启动失败')
                    }
                })()
            })
        },
    })
}

/**
 * 重启实例
 */
function handleRestartInstance(record) {
    Modal.confirm({
        title: '确认重启',
        content: `确定要重启实例 ${record.instance_uuid || record.machine_name} 吗？重启期间实例将暂时不可用。`,
        okText: '确认重启',
        cancelText: '取消',
        onOk: () => {
            return new Promise((resolve, reject) => {
                ; (async () => {
                    try {
                        const { success, message: msg } = await apis.instance.restartInstance(record.id).catch(() => {
                            throw new Error('API调用失败')
                        })
                        if (config('http.code.success') === success) {
                            resolve()
                            message.success(msg || '重启命令已发送')
                            setTimeout(() => {
                                getPageList()
                            }, 2000)
                        } else {
                            reject(new Error(msg || '重启失败'))
                        }
                    } catch (error) {
                        reject(error)
                        message.error(error.message || '重启失败')
                    }
                })()
            })
        },
    })
}

/**
 * 停止实例
 */
function handleStopInstance(record) {
    Modal.confirm({
        title: '确认停止',
        content: `确定要停止实例 ${record.instance_uuid || record.machine_name} 吗？停止后实例将立即终止运行。`,
        okText: '确认停止',
        cancelText: '取消',
        okType: 'danger',
        onOk: () => {
            return new Promise((resolve, reject) => {
                ; (async () => {
                    try {
                        const { success, message: msg } = await apis.instance.stopInstance(record.id).catch(() => {
                            throw new Error('API调用失败')
                        })
                        if (config('http.code.success') === success) {
                            resolve()
                            message.success(msg || '停止命令已发送')
                            setTimeout(() => {
                                getPageList()
                            }, 2000)
                        } else {
                            reject(new Error(msg || '停止失败'))
                        }
                    } catch (error) {
                        reject(error)
                        message.error(error.message || '停止失败')
                    }
                })()
            })
        },
    })
}

/**
 * 删除实例
 */
function handleDeleteInstance(record) {
    Modal.confirm({
        title: '确认删除',
        content: `确定要删除实例 ${record.instance_uuid || record.machine_name} 吗？此操作将永久删除实例及相关数据，不可恢复！`,
        okText: '确认删除',
        cancelText: '取消',
        okType: 'danger',
        onOk: () => {
            return new Promise((resolve, reject) => {
                ; (async () => {
                    try {
                        const { success, message: msg } = await apis.instance.deleteInstance(record.id).catch(() => {
                            throw new Error('API调用失败')
                        })
                        if (config('http.code.success') === success) {
                            resolve()
                            message.success(msg || '删除成功')
                            await getPageList()
                        } else {
                            reject(new Error(msg || '删除失败'))
                        }
                    } catch (error) {
                        reject(error)
                        message.error(error.message || '删除失败')
                    }
                })()
            })
        },
    })
}

/**
 * 查看日志
 */
function handleViewLogs(record) {
    if (record.instance_uuid) {
        const logsUrl = `/logs/instance/${record.instance_uuid}`
        window.open(logsUrl, '_blank')
        message.success('正在打开日志页面...')
    } else {
        message.warning('实例ID不存在')
    }
}

/**
 * 终端连接
 */
function handleTerminal(record) {
    if (record.ssh_command) {
        navigator.clipboard.writeText(record.ssh_command).then(() => {
            message.success('SSH命令已复制到剪贴板')
        }).catch(() => {
            Modal.info({
                title: 'SSH连接命令',
                content: `
                    <div style="margin: 16px 0;">
                        <p>请复制以下命令到终端中使用：</p>
                        <code style="background: #f0f0f0; padding: 8px; border-radius: 4px; display: block; font-family: monospace; word-break: break-all;">
                            ${record.ssh_command}
                        </code>
                    </div>
                `,
                okText: '关闭',
            })
        })
    } else {
        message.warning('SSH连接信息不存在')
    }
}

/**
 * 导出实例列表
 */
function handleExportInstances() {
    Modal.confirm({
        title: '导出实例列表',
        content: '确定要导出当前实例列表吗？导出的文件将包含所有实例的详细信息。',
        okText: '确认导出',
        cancelText: '取消',
        onOk: () => {
            message.loading('正在准备导出数据...', 0)

            setTimeout(() => {
                message.destroy()
                message.success('导出成功！文件已开始下载')
            }, 1500)
        },
    })
}

/**
 * 分页变化
 */
function onTableChange({ current, pageSize }) {
    paginationState.current = current
    paginationState.pageSize = pageSize
    getPageList()
}

/**
 * 重置搜索
 */
function handleResetSearch() {
    searchFormData.value = {}
    resetPagination()
    getPageList()
}

/**
 * 搜索
 */
function handleSearch() {
    resetForm()
    resetPagination()
    getPageList()
}
</script>

<style lang="less" scoped>
.align-right {
    text-align: right;
}

.mb-8-2 {
    margin-bottom: 8px;
}

.text-secondary {
    color: rgba(0, 0, 0, 0.45);
    font-size: 12px;
}

.user-info-cell,
.instance-info-cell,
.spec-detail-cell,
.disk-usage-cell,
.ssh-login-cell,
.quick-tools-cell,
.action-cell {
    display: flex;
    flex-direction: column;
    gap: 4px;
}

.spec-detail-cell {
    .ant-btn-link {
        padding: 0;
        height: auto;
        font-size: 12px;
    }
}

:deep(.ant-table-cell) {
    .ant-btn-link {
        padding: 0;
        height: auto;
    }

    .ant-dropdown-trigger {
        padding: 0;
        height: auto;
    }
}

:deep(.ant-tag) {
    border-radius: 12px;
    padding: 2px 8px;
    font-size: 12px;
    line-height: 1.5;
}

// 弹窗样式
:deep(.ant-modal-body) {
    max-height: 70vh;
    overflow-y: auto;
}
</style>