src/components/bg-task/FYBgTaskCard.vue
@@ -1,67 +1,197 @@
<template>
  <el-card class="bg-task-card" shadow="hover" :body-style="{ padding: '8px' }">
    <!-- <template #header> -->
    <el-row style="background-color: aliceblue">
      <!-- <el-space> -->
      <el-tag>{{ nameToLabel(model.type) }}</el-tag>
      <el-text style="width: 80%" tag="b" size="large" truncated>{{ model.name }}</el-text>
      <!-- <div>{{ model.name }}asdasdasdasdasdasdaasdasdasdasdasdasdaasdasdasdasdasdasdaasdasdasdasdasdasda</div> -->
      <!-- </el-space> -->
    </el-row>
    <!-- <div>
      <el-text truncated>{{ model.name }}asdasdasdasdasdasdaasdasdasdasdasdasdaasdasdasdasdasdasdaasdasdasdasdasdasda</el-text>
        </div> -->
    <!-- </template> -->
    <div>
      <el-text type="info" size="small">ID:{{ model.id }}</el-text>
    </div>
    <div>
      <el-text type="info" size="small">状态:{{ nameToLabel(model.status) }}</el-text>
    </div>
    <div>
      <el-text type="info" size="small">开始:{{ model.startTime }}</el-text>
    </div>
    <div>
      <el-text type="info" size="small">结束:{{ model.endTime }}</el-text>
    </div>
    <!-- <template #footer> -->
    <el-row justify="end">
      <el-button type="primary" size="small" :loading="false" @click="$emit('start', model)"
        >开始任务</el-button
      >
      <el-button type="danger" size="small" :loading="false" @click="$emit('shutDown', model)"
        >强制结束</el-button
      >
      <el-button type="danger" size="small" :loading="false" @click="$emit('remove', model)"
        >移除任务</el-button
      >
      <el-button type="danger" size="small" :loading="false" @click="$emit('gotoResult', model)"
        >查看结果</el-button
      >
    </el-row>
    <!-- </template> -->
  <el-card shadow="never" :body-style="{ padding: 0 }">
    <template #header>
      <el-row justify="space-between">
        <div>
          <div><el-text tag="b" size="large">后台任务</el-text></div>
          <el-text size="small" type="info">显示当前正在进行的后台耗时任务状态</el-text>
        </div>
        <el-button
          icon="Refresh"
          type="primary"
          size="default"
          :loading="loading"
          @click="fetchTask"
          >刷新任务</el-button
        >
      </el-row>
      <!-- <el-row>
        <el-button type="default" size="default" @click="newTestTask">新增测试任务</el-button>
        <el-button type="default" size="default" @click="startNewTestTask"
          >新建并运行一个测试任务</el-button
        >
        <el-button type="default" size="default" @click="shutDownTask"
          >强制关闭所有测试任务</el-button
        >
      </el-row> -->
    </template>
    <el-scrollbar height="70vh" class="scrollbar">
      <template v-for="(v, i) in taskList" :key="i">
        <FYBgTaskItem
          :model="v"
          :index="i"
          @start="startTask"
          @shutDown="shutDownTask"
          @remove="removeTask"
          @gotoResult="gotoResult"
        ></FYBgTaskItem>
      </template>
    </el-scrollbar>
  </el-card>
</template>
<script>
import { nTlBgTask } from '@/enum/bgTask';
/**
 * 自动评估任务管理
 */
import { useFetchData } from '@/composables/fetchData';
import bgtaskApi from '@/api/fysp/bgtaskApi';
import { enumBgTask, BG_TASK_TYPE, BG_TASK_STATUS } from '@/enum/bgTask';
import { SOCKET_MESSAGE_TYPE } from '@/enum/socketMessage';
import MessageManager from '@/socket/MessageManager.js';
export default {
  props: {
    model: Object
  setup() {
    const { loading, fetchData } = useFetchData();
    return { loading, fetchData };
  },
  emits: ['start', 'shutDown', 'remove', 'gotoResult'],
  methods: {
    nameToLabel(name) {
      const t = nTlBgTask(name);
      return t.label;
  props: {
    modelValue: Number
  },
  emits: ['update:modelValue'],
  data() {
    return {
      taskList: [],
      taskIndex: 0
    };
  },
  watch: {
    taskList: {
      handler(nV) {
        let count = 0;
        for (const e of nV) {
          if (e.status == BG_TASK_STATUS.RUNNING.name) {
            count++;
          }
        }
        this.$emit('update:modelValue', count);
      },
      deep: true
    }
  },
  created() {
    this.registerBgTaskMessage()
  },
  methods: {
    registerBgTaskMessage() {
      MessageManager.register(SOCKET_MESSAGE_TYPE.BACKGROUND_TASK.name, (data) => {
        this.refreshTaskById(data)
      })
    },
    /**
     * 刷新一个任务通过id,如果是新的任务则添加到任务列表taskList中
     * @param data
     */
    refreshTaskById(data) {
      if (!data || data == {}) {
        return;
      }
      let isNewTask = true
      for (let index = 0; index < this.taskList.length; index++) {
          const task = this.taskList[index];
          if (task.id == data.id) {
            this.taskList[index] = data
            isNewTask = false
            break
          }
        }
        if (isNewTask) {
          this.taskList.push(data)
        }
    },
    addTask() {},
    newTestTask() {
      this.fetchData((page, pageSize) => {
        return bgtaskApi.newTestTask(`Test-Task-${++this.taskIndex}`).then((res) => {
          this.taskList.push(res.data);
        });
      });
    },
    startNewTestTask() {
      this.fetchData((page, pageSize) => {
        return bgtaskApi.startNewTestTask(`Test-Task-${++this.taskIndex}`).then((res) => {
          this.taskList.push(res.data);
        });
      });
    },
    _getParam(taskStatus) {
      return {
        type: taskStatus.type,
        id: taskStatus.id
      };
    },
    fetchTask() {
      this.fetchData((page, pageSize) => {
        return bgtaskApi
          .fetchTaskStatus({
            // type: BG_TASK_TYPE.AUTO_SCORE.name
          })
          .then((res) => {
            this.taskList = res.data;
          });
      });
    },
    startTask(index, callback) {
      this.fetchData((page, pageSize) => {
        const param = this._getParam(this.taskList[index]);
        return bgtaskApi.startTask(param).then((res) => {
          this.taskList[index] = res.data;
          callback(true);
        });
      });
    },
    shutDownTask(index, callback) {
      this.fetchData((page, pageSize) => {
        const param = this._getParam(this.taskList[index]);
        return bgtaskApi.shutDownTask(param).then((res) => {
          if (index && res.data && res.data.length == 1) {
            this.taskList[index] = res.data[0];
          } else {
            res.data.forEach((e) => {
              let v = this.taskList.find((value) => {
                return value.id == e.id;
              });
              const i = this.taskList.indexOf(v);
              this.taskList[i] = e;
            });
          }
          callback(true);
        });
      });
    },
    removeTask(index, callback) {
      this.fetchData((page, pageSize) => {
        const param = this._getParam(this.taskList[index]);
        return bgtaskApi.removeTask(param).then((res) => {
          if (res.data) {
            this.taskList.splice(index, 1);
            callback(true);
          }
        });
      });
    },
    gotoResult(index) {}
  },
  mounted() {
    this.fetchTask();
    // setInterval(() => {
    //   this.fetchTask();
    // }, 10000);
  }
};
</script>
<style scoped>
.bg-task-card {
  margin-bottom: 8px;
.scrollbar {
  padding: 8px;
}
</style>