Browse Source

新增汇总统计

lmx 1 week ago
parent
commit
791aa75086
2 changed files with 251 additions and 1 deletions
  1. 17 1
      src/api/course/courseTrafficLog.js
  2. 234 0
      src/views/course/courseTrafficLog/statistics.vue

+ 17 - 1
src/api/course/courseTrafficLog.js

@@ -50,4 +50,20 @@ export function exportCourseTrafficLog(query) {
     method: 'get',
     params: query
   })
-}
+}
+
+export function statisticsSummaryList(query) {
+  return request({
+    url: '/course/courseTrafficLog/statisticsSummaryList',
+    method: 'get',
+    params: query
+  })
+}
+
+export function exportStatisticsSummary(query) {
+  return request({
+    url: '/course/courseTrafficLog/exportStatisticsSummary',
+    method: 'get',
+    params: query
+  })
+}

+ 234 - 0
src/views/course/courseTrafficLog/statistics.vue

@@ -0,0 +1,234 @@
+<template>
+  <div class="app-container">
+    <!-- 查询条件 -->
+    <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch" label-width="68px">
+      <!-- 公司选择 -->
+      <el-form-item label="统计维度">
+        <el-select v-model="queryParams.statisticsType" placeholder="请选择统计维度" filterable clearable size="small">
+          <el-option v-for="(option, index) in dimensionStatistics" :key="index" :value="option.value" :label="option.text"></el-option>
+        </el-select>
+      </el-form-item>
+
+      <!-- 项目选择 -->
+      <el-form-item label="选择公司">
+        <el-select v-model="queryParams.companyId" placeholder="请选择公司" filterable clearable size="small">
+          <el-option v-for="dict in companyList" :key="dict.dictValue" :label="dict.dictLabel" :value="dict.dictValue" />
+        </el-select>
+      </el-form-item>
+
+      <!-- 时间选择 -->
+      <el-form-item label="年月">
+        <el-date-picker
+          v-model="timeRange"
+          type="daterange"
+          placeholder="选择年月"
+          :value-format="'yyyy-MM-dd'"
+          :picker-options="pickerOptions"
+          @change="handleDateData"
+        ></el-date-picker>
+      </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-row :gutter="10" class="mb8">
+      <el-col :span="1.5">
+        <el-button
+          type="warning"
+          plain
+          icon="el-icon-download"
+          size="mini"
+          :loading="exportLoading"
+          @click="handleExport"
+          v-hasPermi="['course:courseRedPacketLog:export']"
+        >导出</el-button>
+      </el-col>
+      <right-toolbar :showSearch.sync="showSearch" @queryTable="getList"></right-toolbar>
+    </el-row>
+    
+
+    <!-- 表格 -->
+    <el-table border v-loading="loading" :data="courseTrafficLogList" @selection-change="handleSelectionChange">
+      <el-table-column type="selection" width="55" align="center" />
+      <el-table-column label="公司" align="center" prop="companyName" />
+      <el-table-column v-if="showDept" label="部门" align="center" prop="deptName" />
+      <el-table-column label="统计范围" align="center" prop="dateRange" />
+      <el-table-column label="使用流量" align="center"  prop="formattedTotalTraffic">
+      </el-table-column>
+      <el-table-column label="金额" align="center" prop="totalAmount">
+      </el-table-column>
+    </el-table>
+
+    <!-- 分页 -->
+    <pagination
+      v-show="total > 0"
+      :total="total"
+      :page.sync="queryParams.pageNum"
+      :limit.sync="queryParams.pageSize"
+      @pagination="getList"
+    />
+  </div>
+</template>
+
+<script>
+import { listCourseTrafficLog, exportCourseTrafficLog,statisticsSummaryList,exportStatisticsSummary } from "@/api/course/courseTrafficLog";
+import { courseList } from "@/api/course/courseRedPacketLog";
+import { allList } from "@/api/company/company";
+
+export default {
+  data() {
+    return {
+      showDept:false,
+      dimensionStatistics:[
+        {text:"按公司",value:1},
+        {text:"按部门",value:2}
+      ],
+      timeRange: null, // 时间范围单独绑定
+      companyList: [],
+      projectOptions: [],
+      pickerOptions: {
+        shortcuts: [
+          {
+            text: '今日',
+            onClick(picker) {
+              const start = new Date();
+              const end = new Date();
+              picker.$emit('pick', [start, end]);
+            }
+          },
+          {
+            text: '昨日',
+            onClick(picker) {
+              const start = new Date();
+              start.setDate(start.getDate() - 1);
+              const end = new Date(start);
+              picker.$emit('pick', [start, end]);
+            }
+          },
+          {
+            text: '本周',
+            onClick(picker) {
+              const now = new Date();
+              const day = now.getDay() || 7;
+              const start = new Date(now);
+              start.setDate(now.getDate() - day + 1);
+              const end = new Date();
+              picker.$emit('pick', [start, end]);
+            }
+          },
+          {
+            text: '本月',
+            onClick(picker) {
+              const start = new Date(new Date().setDate(1));
+              const end = new Date();
+              picker.$emit('pick', [start, end]);
+            }
+          }
+        ]
+      },
+      courseLists: [],
+      loading: false,
+      exportLoading: false,
+      showSearch: true,
+      total: 0,
+      courseTrafficLogList: [],
+      queryParams: {
+        tabType: "", // 当前 tab 类型
+        startDate: null,
+        endDate: null,
+        pageNum: 1,
+        pageSize: 10,
+        statisticsType: null,//统计维度 1、按照公司 2、按照部门
+        companyId:null,
+        project: null,
+        courseId: null
+      }
+    };
+  },
+  created() {
+    courseList().then(res => this.courseLists = res.list);
+    this.getDicts("sys_course_project").then(res => this.projectOptions = res.data);
+    this.getAllCompany();
+    this.getList();
+  },
+  methods: {
+    handleTabClick(tab) {
+      this.queryParams.tabType = tab.name;
+      this.queryParams.pageNum = 1;
+
+      // 清理互斥参数
+      if (tab.name !== "project") this.queryParams.project = null;
+      if (tab.name !== "course") this.queryParams.courseId = null;
+      if (tab.name !== "company") this.queryParams.companyId = null;
+
+      this.getList();
+    },
+
+    handleDateData() {
+      if (this.timeRange) {
+        this.queryParams.startDate = this.timeRange[0];
+        this.queryParams.endDate = this.timeRange[1];
+      } else {
+        this.queryParams.startDate = null;
+        this.queryParams.endDate = null;
+      }
+    },
+    getAllCompany() {
+      allList().then(res => this.companyList = res.rows);
+    },
+    getList() {
+      this.loading = true;
+      if(this.queryParams.statisticsType == 2){
+         this.showDept = true;
+      }else{
+        this.showDept = false;
+      }
+      statisticsSummaryList(this.queryParams).then(res => {
+        this.courseTrafficLogList = res.rows;
+        this.total = res.total;
+      }).finally(() => {
+        this.loading = false;
+      });
+    },
+    handleQuery() {
+      this.queryParams.pageNum = 1;
+      this.getList();
+    },
+    resetQuery() {
+      this.timeRange = null;
+      this.queryParams = {
+        ...this.queryParams,
+        startDate: null,
+        endDate: null,
+        companyId: null,
+        project: null,
+        courseId: null,
+        pageNum: 1,
+      };
+      this.getList();
+    },
+    formatTrafficData(traffic) {
+      if (traffic < 1024) return `${traffic} B`;
+      if (traffic < 1024 ** 2) return `${(traffic / 1024).toFixed(2)} KB`;
+      if (traffic < 1024 ** 3) return `${(traffic / 1024 ** 2).toFixed(2)} MB`;
+      return `${(traffic / 1024 ** 3).toFixed(2)} GB`;
+    },
+    handleSelectionChange(selection) {
+      this.ids = selection.map(item => item.logId);
+    },
+    handleExport() {
+      this.$confirm("确认导出数据?", "提示").then(() => {
+        this.exportLoading = true;
+        return exportStatisticsSummary(this.queryParams);
+      }).then(res => {
+        this.download(res.msg);
+      }).finally(() => {
+        this.exportLoading = false;
+      });
+    }
+  }
+};
+</script>