<template>
  <div class="app-container">
    <el-card shadow="never" class="mb8">
      <div slot="header">
        <span>外部接口管理配置</span>
      </div>

      <el-form :model="queryParams" ref="queryForm" size="small" :inline="true" label-width="70px">
        <el-form-item label="接口类型">
          <el-input v-model="queryParams.apiType" placeholder="请输入" clearable @keyup.enter.native="handleQuery" />
        </el-form-item>
        <el-form-item label="接口名称">
          <el-input v-model="queryParams.apiName" placeholder="请输入" clearable @keyup.enter.native="handleQuery" />
        </el-form-item>
        <el-form-item label="接口编码">
          <el-input v-model="queryParams.apiCode" placeholder="请输入" clearable @keyup.enter.native="handleQuery" />
        </el-form-item>
        <el-form-item label="状态">
          <el-select v-model="queryParams.status" placeholder="请选择" clearable style="width: 120px">
            <el-option label="启用" :value="1" />
            <el-option label="停用" :value="0" />
          </el-select>
        </el-form-item>
        <el-form-item>
          <el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">查询</el-button>
          <el-button icon="el-icon-refresh" size="mini" @click="resetQuery">重置</el-button>
        </el-form-item>
      </el-form>
    </el-card>

    <el-row :gutter="10" class="mb8">
      <el-col :span="1.5">
        <el-button type="primary" plain icon="el-icon-plus" size="mini" @click="handleAdd">新增接口</el-button>
      </el-col>
    </el-row>

    <el-table v-loading="loading" :data="list" border>
      <el-table-column type="index" label="序号" width="60" />
      <el-table-column prop="apiName" label="接口名称" min-width="160" show-overflow-tooltip />
      <el-table-column prop="apiCode" label="接口编码" min-width="160" show-overflow-tooltip />
      <el-table-column prop="apiType" label="接口类型" width="120" />
      <el-table-column prop="apiUrl" label="请求地址" min-width="260" show-overflow-tooltip />
      <el-table-column prop="httpMethod" label="请求方式" width="110" />
      <el-table-column label="限频规则" width="140">
        <template slot-scope="scope">
          <span v-if="scope.row.rateMaxCount && scope.row.rateWindowSeconds">
            {{ scope.row.rateMaxCount }}次/{{ formatWindow(scope.row.rateWindowSeconds) }}
          </span>
          <span v-else>-</span>
        </template>
      </el-table-column>
      <el-table-column prop="priority" label="优先级" width="90" />
      <el-table-column label="状态" width="110">
        <template slot-scope="scope">
          <el-switch
            v-model="scope.row.status"
            :active-value="1"
            :inactive-value="0"
            @change="val => handleStatusChange(scope.row, val)"
          />
        </template>
      </el-table-column>
      <el-table-column label="操作" width="260" fixed="right">
        <template slot-scope="scope">
          <el-button type="text" size="mini" @click="handleTest(scope.row)">测试</el-button>
          <el-button type="text" size="mini" @click="handleEdit(scope.row)">编辑</el-button>
          <el-button type="text" size="mini" @click="handleLogs(scope.row)">日志</el-button>
          <el-button type="text" size="mini" style="color:#F56C6C" @click="handleDelete(scope.row)">删除</el-button>
        </template>
      </el-table-column>
    </el-table>

    <pagination
      v-show="total > 0"
      :total="total"
      :page.sync="queryParams.pageNum"
      :limit.sync="queryParams.pageSize"
      @pagination="getList"
    />

    <!-- 新增/编辑 -->
    <el-dialog :title="form.id ? '编辑接口' : '新增接口'" :visible.sync="openForm" width="720px" append-to-body>
      <el-form ref="formRef" :model="form" :rules="rules" label-width="110px">
        <el-row :gutter="12">
          <el-col :span="12">
            <el-form-item label="接口类型" prop="apiType">
              <el-input v-model="form.apiType" placeholder="例如 WEATHER" />
            </el-form-item>
          </el-col>
          <el-col :span="12">
            <el-form-item label="接口名称" prop="apiName">
              <el-input v-model="form.apiName" />
            </el-form-item>
          </el-col>
          <el-col :span="12">
            <el-form-item label="接口编码" prop="apiCode">
              <el-input v-model="form.apiCode" :disabled="!!form.id" />
            </el-form-item>
          </el-col>
          <el-col :span="12">
            <el-form-item label="请求方式" prop="httpMethod">
              <el-select v-model="form.httpMethod" placeholder="请选择" style="width:100%">
                <el-option label="GET" value="GET" />
                <el-option label="POST" value="POST" />
                <el-option label="PUT" value="PUT" />
                <el-option label="DELETE" value="DELETE" />
              </el-select>
            </el-form-item>
          </el-col>
          <el-col :span="24">
            <el-form-item label="请求地址" prop="apiUrl">
              <el-input v-model="form.apiUrl" placeholder="https://..." />
            </el-form-item>
          </el-col>

          <el-col :span="12">
            <el-form-item label="限频窗口(秒)">
              <el-input-number v-model="form.rateWindowSeconds" :min="1" :step="1" style="width:100%" />
            </el-form-item>
          </el-col>
          <el-col :span="12">
            <el-form-item label="窗口最大次数">
              <el-input-number v-model="form.rateMaxCount" :min="1" :step="1" style="width:100%" />
            </el-form-item>
          </el-col>

          <el-col :span="12">
            <el-form-item label="优先级">
              <el-input-number v-model="form.priority" :min="0" :step="1" style="width:100%" />
            </el-form-item>
          </el-col>
          <el-col :span="12">
            <el-form-item label="状态">
              <el-select v-model="form.status" style="width:100%">
                <el-option label="启用" :value="1" />
                <el-option label="停用" :value="0" />
              </el-select>
            </el-form-item>
          </el-col>

          <el-col :span="12">
            <el-form-item label="超时(ms)">
              <el-input-number v-model="form.timeoutMs" :min="1000" :step="500" style="width:100%" />
            </el-form-item>
          </el-col>

          <el-col :span="24">
            <el-form-item label="默认请求头(JSON)">
              <el-input v-model="form.defaultHeadersJson" type="textarea" :rows="3" placeholder='{"Content-Type":"application/json"}' />
            </el-form-item>
          </el-col>
          <el-col :span="24">
            <el-form-item label="默认请求体(JSON)">
              <el-input v-model="form.defaultBodyJson" type="textarea" :rows="4" placeholder='{"k":"v"}' />
            </el-form-item>
          </el-col>
        </el-row>
      </el-form>
      <div slot="footer" class="dialog-footer">
        <el-button @click="openForm = false">取消</el-button>
        <el-button type="primary" @click="submitForm">确定</el-button>
      </div>
    </el-dialog>

    <!-- 测试 -->
    <el-dialog title="测试接口" :visible.sync="openTest" width="760px" append-to-body>
      <el-form :model="testForm" label-width="130px">
        <el-form-item label="覆盖请求头(JSON)">
          <el-input v-model="testForm.headersJson" type="textarea" :rows="3" />
        </el-form-item>
        <el-form-item label="覆盖请求体(JSON)">
          <el-input v-model="testForm.bodyJson" type="textarea" :rows="4" />
        </el-form-item>
        <el-form-item label="覆盖超时(ms)">
          <el-input-number v-model="testForm.timeoutMs" :min="1000" :step="500" />
        </el-form-item>
      </el-form>

      <el-divider content-position="left">响应</el-divider>
      <el-descriptions :column="2" border size="small">
        <el-descriptions-item label="状态码">{{ testResult.responseStatus || '-' }}</el-descriptions-item>
        <el-descriptions-item label="耗时(ms)">{{ testResult.durationMs || '-' }}</el-descriptions-item>
        <el-descriptions-item label="是否成功">{{ testResult.success === true ? '是' : (testResult.success === false ? '否' : '-') }}</el-descriptions-item>
        <el-descriptions-item label="错误信息">{{ testResult.errorMessage || '-' }}</el-descriptions-item>
      </el-descriptions>
      <el-input v-model="testResult.responseBody" type="textarea" :rows="10" readonly style="margin-top: 10px" />

      <div slot="footer" class="dialog-footer">
        <el-button @click="openTest = false">关闭</el-button>
        <el-button type="primary" :loading="testLoading" @click="doTest">开始测试</el-button>
      </div>
    </el-dialog>

    <!-- 日志 -->
    <el-dialog title="调用日志" :visible.sync="openLogs" width="980px" append-to-body>
      <el-table v-loading="logsLoading" :data="logs" border height="520px">
        <el-table-column type="index" label="序号" width="60" />
        <el-table-column prop="createTime" label="时间" width="170" />
        <el-table-column prop="httpMethod" label="方法" width="90" />
        <el-table-column prop="requestUrl" label="URL" min-width="260" show-overflow-tooltip />
        <el-table-column prop="responseStatus" label="状态码" width="90" />
        <el-table-column prop="durationMs" label="耗时(ms)" width="100" />
        <el-table-column prop="success" label="成功" width="80">
          <template slot-scope="scope">
            <el-tag v-if="scope.row.success === 1" type="success">成功</el-tag>
            <el-tag v-else type="danger">失败</el-tag>
          </template>
        </el-table-column>
        <el-table-column prop="errorMessage" label="错误信息" min-width="160" show-overflow-tooltip />
      </el-table>

      <pagination
        v-show="logsTotal > 0"
        :total="logsTotal"
        :page.sync="logsQuery.pageNum"
        :limit.sync="logsQuery.pageSize"
        @pagination="getLogs"
      />

      <div slot="footer" class="dialog-footer">
        <el-button @click="openLogs = false">关闭</el-button>
      </div>
    </el-dialog>
  </div>
</template>

<script>
import {
  pageExternalApi,
  getExternalApi,
  saveOrUpdateExternalApi,
  changeExternalApiStatus,
  deleteExternalApi,
  testExternalApi,
  pageExternalApiLogs
} from '@/api/company/externalApi'

export default {
  name: 'CompanyWorkflowExternalApi',
  data() {
    return {
      loading: false,
      list: [],
      total: 0,
      queryParams: {
        pageNum: 1,
        pageSize: 10,
        apiType: undefined,
        apiName: undefined,
        apiCode: undefined,
        status: undefined
      },

      openForm: false,
      form: this.emptyForm(),
      rules: {
        apiType: [{ required: true, message: '接口类型不能为空', trigger: 'blur' }],
        apiName: [{ required: true, message: '接口名称不能为空', trigger: 'blur' }],
        apiCode: [{ required: true, message: '接口编码不能为空', trigger: 'blur' }],
        apiUrl: [{ required: true, message: '请求地址不能为空', trigger: 'blur' }],
        httpMethod: [{ required: true, message: '请求方式不能为空', trigger: 'change' }]
      },

      openTest: false,
      testLoading: false,
      currentRow: null,
      testForm: {
        headersJson: '',
        bodyJson: '',
        timeoutMs: 10000
      },
      testResult: {
        responseStatus: null,
        responseBody: '',
        durationMs: null,
        success: null,
        errorMessage: ''
      },

      openLogs: false,
      logsLoading: false,
      logs: [],
      logsTotal: 0,
      logsQuery: {
        pageNum: 1,
        pageSize: 10,
        configId: null
      }
    }
  },
  created() {
    this.getList()
  },
  methods: {
    emptyForm() {
      return {
        id: null,
        apiType: '',
        apiName: '',
        apiCode: '',
        apiUrl: '',
        httpMethod: 'GET',
        rateWindowSeconds: null,
        rateMaxCount: null,
        priority: 0,
        status: 1,
        timeoutMs: 10000,
        defaultHeadersJson: '',
        defaultBodyJson: ''
      }
    },
    formatWindow(seconds) {
      if (!seconds) return '-'
      if (seconds % 86400 === 0) return (seconds / 86400) + '天'
      if (seconds % 3600 === 0) return (seconds / 3600) + '小时'
      if (seconds % 60 === 0) return (seconds / 60) + '分钟'
      return seconds + '秒'
    },
    getList() {
      this.loading = true
      pageExternalApi(this.queryParams).then(res => {
        const page = res.data || {}
        this.list = page.records || []
        this.total = page.total || 0
      }).finally(() => {
        this.loading = false
      })
    },
    handleQuery() {
      this.queryParams.pageNum = 1
      this.getList()
    },
    resetQuery() {
      this.queryParams = {
        pageNum: 1,
        pageSize: 10,
        apiType: undefined,
        apiName: undefined,
        apiCode: undefined,
        status: undefined
      }
      this.getList()
    },
    handleAdd() {
      this.form = this.emptyForm()
      this.openForm = true
      this.$nextTick(() => this.$refs.formRef && this.$refs.formRef.clearValidate())
    },
    handleEdit(row) {
      getExternalApi(row.id).then(res => {
        this.form = Object.assign(this.emptyForm(), res.data || {})
        this.openForm = true
        this.$nextTick(() => this.$refs.formRef && this.$refs.formRef.clearValidate())
      })
    },
    submitForm() {
      this.$refs.formRef.validate(valid => {
        if (!valid) return
        saveOrUpdateExternalApi(this.form).then(() => {
          this.$message.success('保存成功')
          this.openForm = false
          this.getList()
        })
      })
    },
    handleStatusChange(row, val) {
      changeExternalApiStatus(row.id, val).then(() => {
        this.$message.success('状态已更新')
      }).catch(() => {
        row.status = val === 1 ? 0 : 1
      })
    },
    handleDelete(row) {
      this.$confirm(`确认删除接口【${row.apiName}】？`, '提示', { type: 'warning' })
        .then(() => deleteExternalApi(row.id))
        .then(() => {
          this.$message.success('删除成功')
          this.getList()
        })
        .catch(() => {})
    },
    handleTest(row) {
      this.currentRow = row
      this.testForm = { headersJson: '', bodyJson: '', timeoutMs: row.timeoutMs || 10000 }
      this.testResult = { responseStatus: null, responseBody: '', durationMs: null, success: null, errorMessage: '' }
      this.openTest = true
    },
    doTest() {
      if (!this.currentRow) return
      this.testLoading = true
      testExternalApi(this.currentRow.id, this.testForm).then(res => {
        this.testResult = res.data || this.testResult
      }).finally(() => {
        this.testLoading = false
      })
    },
    handleLogs(row) {
      this.logsQuery = { pageNum: 1, pageSize: 10, configId: row.id }
      this.openLogs = true
      this.getLogs()
    },
    getLogs() {
      this.logsLoading = true
      pageExternalApiLogs(this.logsQuery).then(res => {
        const page = res.data || {}
        this.logs = page.records || []
        this.logsTotal = page.total || 0
      }).finally(() => {
        this.logsLoading = false
      })
    }
  }
}
</script>

<style scoped>
.mb8 { margin-bottom: 8px; }
</style>

