yys 6 дней назад
Родитель
Сommit
dea0dc120a
61 измененных файлов с 2653 добавлено и 237 удалено
  1. 633 0
      public/chat-aggregate.html
  2. 18 0
      src/api/admin/commissionRecord.js
  3. 18 0
      src/api/admin/consumeRecord.js
  4. 18 0
      src/api/admin/dailyStatistics.js
  5. 10 0
      src/api/admin/liveVideo.js
  6. 19 19
      src/api/admin/lobster.js
  7. 18 0
      src/api/admin/rechargeRecord.js
  8. 19 0
      src/api/admin/serviceCost.js
  9. 10 0
      src/api/admin/videoResource.js
  10. 43 0
      src/api/admin/withdrawalManage.js
  11. 4 4
      src/api/callRecord/callRecord.js
  12. 6 6
      src/api/complaint/category.js
  13. 7 7
      src/api/complaint/complaint.js
  14. 6 6
      src/api/course/push.js
  15. 5 5
      src/api/courseFinishTemp/course.js
  16. 2 2
      src/api/crm/customer.js
  17. 6 6
      src/api/fastGpt/readPackage.js
  18. 5 5
      src/api/food/record.js
  19. 8 8
      src/api/his/redPacketConfig.js
  20. 2 2
      src/api/hisStore/answer.js
  21. 7 7
      src/api/hisStore/chineseMedicine.js
  22. 8 8
      src/api/hisStore/collection.js
  23. 6 6
      src/api/hisStore/department.js
  24. 7 7
      src/api/hisStore/disease.js
  25. 7 7
      src/api/hisStore/doctorArticle.js
  26. 7 7
      src/api/hisStore/famousPrescribe.js
  27. 7 7
      src/api/hisStore/illnessLibrary.js
  28. 10 10
      src/api/hisStore/integralOrder.js
  29. 7 7
      src/api/hisStore/medicatedFood.js
  30. 9 9
      src/api/hisStore/store.js
  31. 6 6
      src/api/hisStore/storeInstanDiscountIssue.js
  32. 6 6
      src/api/hisStore/storeInstantDiscount.js
  33. 6 6
      src/api/hisStore/storeInstantDiscountUser.js
  34. 6 6
      src/api/hisStore/testReport.js
  35. 8 8
      src/api/hisStore/testTemp.js
  36. 6 6
      src/api/hisStore/testTempItem.js
  37. 8 8
      src/api/hisStore/vessel.js
  38. 2 2
      src/api/login.js
  39. 1 1
      src/api/menu.js
  40. 4 4
      src/api/moduleUsage/moduleUsage.js
  41. 6 6
      src/api/recharge/template.js
  42. 5 5
      src/api/saler/productInfo.js
  43. 1 1
      src/api/store/collectionSchedule.js
  44. 5 5
      src/api/storeOrderOfflineItem/store.js
  45. 4 4
      src/api/sysUser/sysUser.js
  46. 9 9
      src/api/todo/todoItems.js
  47. 6 6
      src/api/wx/sopUserLogsWx.js
  48. 53 0
      src/components/InlineTenantSelector/index.vue
  49. 82 0
      src/components/TenantSelect/index.vue
  50. 8 3
      src/settings.js
  51. 163 0
      src/views/admin/commissionRecord/index.vue
  52. 181 0
      src/views/admin/consumeRecord/index.vue
  53. 270 0
      src/views/admin/dailyStatistics/index.vue
  54. 86 0
      src/views/admin/liveVideo/index.vue
  55. 103 0
      src/views/admin/proxy/feeConfig.vue
  56. 160 0
      src/views/admin/rechargeRecord/index.vue
  57. 106 0
      src/views/admin/serviceCost/index.vue
  58. 86 0
      src/views/admin/videoResource/index.vue
  59. 220 0
      src/views/admin/withdrawalManage/index.vue
  60. 57 0
      src/views/customer/customerList.vue
  61. 57 0
      src/views/operation/operationList.vue

+ 633 - 0
public/chat-aggregate.html

@@ -0,0 +1,633 @@
+<!DOCTYPE html>
+<html lang="zh">
+<head>
+<meta charset="UTF-8">
+<meta name="viewport" content="width=device-width, initial-scale=1.0">
+<title>龙虾引擎 - 聚合聊天</title>
+<script src="https://unpkg.com/vue@3/dist/vue.global.prod.js"></script>
+<style>
+*{margin:0;padding:0;box-sizing:border-box}
+body{font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;background:#0a0a1a;color:#e0e0e0;height:100vh;overflow:hidden}
+.main{display:flex;height:100vh}
+
+/* 左侧账户列表 */
+.account-panel{width:80px;background:#0d0d1f;border-right:1px solid #1a1a3e;display:flex;flex-direction:column;padding:12px 0}
+.account-item{width:56px;height:56px;border-radius:50%;margin:0 auto 8px;cursor:pointer;position:relative;border:2px solid transparent;transition:.2s;display:flex;align-items:center;justify-content:center;font-size:24px}
+.account-item:hover{border-color:#e94560;transform:scale(1.05)}
+.account-item.active{border-color:#e94560;background:#e9456022}
+.account-item .badge{position:absolute;top:-2px;right:-2px;background:#e94560;color:#fff;border-radius:10px;padding:1px 5px;font-size:10px}
+.account-item.disabled{opacity:.4;cursor:not-allowed}
+
+/* 会话列表 */
+.session-panel{width:280px;background:#1a1a2e;border-right:1px solid #2a2a4a;display:flex;flex-direction:column}
+.session-header{padding:12px 16px;border-bottom:1px solid #2a2a4a}
+.session-header h3{font-size:14px;color:#e94560}
+.session-header .search{margin-top:8px}
+.session-header input{width:100%;padding:6px 10px;background:#0a0a1a;border:1px solid #2a2a4a;border-radius:4px;color:#e0e0e0;font-size:12px}
+.session-list{flex:1;overflow-y:auto;padding:8px}
+.session-item{display:flex;padding:10px;cursor:pointer;border-radius:6px;margin-bottom:4px;transition:.2s}
+.session-item:hover{background:#2a2a4a}
+.session-item.active{background:#0f3460}
+.session-avatar{width:40px;height:40px;border-radius:50%;background:linear-gradient(135deg,#e94560,#f59e0b);display:flex;align-items:center;justify-content:center;font-size:16px;flex-shrink:0}
+.session-info{flex:1;min-width:0;margin-left:10px}
+.session-info .name{font-size:13px;color:#e0e0e0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
+.session-info .msg{font-size:12px;color:#888;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;margin-top:2px}
+.session-time{font-size:11px;color:#666;text-align:right}
+.session-item.unread .name{font-weight:600;color:#fff}
+.session-item.unread .badge{background:#e94560;color:#fff;border-radius:10px;padding:1px 5px;font-size:10px}
+
+/* 聊天区域 */
+.chat-panel{flex:1;display:flex;flex-direction:column;background:#0a0a1a}
+.chat-header{padding:12px 20px;background:#1a1a2e;border-bottom:1px solid #2a2a4a;display:flex;align-items:center;justify-content:space-between}
+.chat-title .name{font-size:15px;color:#e0e0e0}
+.chat-title .type{font-size:11px;color:#888;margin-left:8px}
+.chat-actions{display:flex;gap:8px}
+.chat-actions button{padding:6px 12px;background:#0f3460;border:none;border-radius:4px;color:#e0e0e0;font-size:12px;cursor:pointer}
+.chat-actions button:hover{background:#1a4a80}
+
+/* 消息列表 */
+.message-list{flex:1;overflow-y:auto;padding:16px;display:flex;flex-direction:column}
+.message-item{display:flex;margin-bottom:12px;max-width:80%}
+.message-item.sent{align-self:flex-end}
+.message-item.sent .msg-bubble{background:#e94560;color:#fff;border-radius:12px 12px 0 12px}
+.message-item.received{align-self:flex-start}
+.message-item.received .msg-bubble{background:#1a1a2e;color:#e0e0e0;border-radius:12px 12px 12px 0;border:1px solid #2a2a4a}
+.msg-avatar{width:32px;height:32px;border-radius:50%;background:linear-gradient(135deg,#3b82f6,#22c55e);display:flex;align-items:center;justify-content:center;font-size:12px;flex-shrink:0}
+.message-item.sent .msg-avatar{order:2;margin-left:8px}
+.message-item.received .msg-avatar{order:1;margin-right:8px}
+.msg-content{display:flex;flex-direction:column}
+.message-item.sent .msg-content{order:1}
+.message-item.received .msg-content{order:2}
+.msg-bubble{padding:10px 14px;max-width:max-content}
+.msg-text{font-size:13px;line-height:1.5}
+.msg-time{font-size:10px;color:#666;margin-top:4px;text-align:right}
+.message-item.sent .msg-time{color:#fff8}
+
+/* 输入区域 */
+.chat-input{padding:12px 20px;background:#1a1a2e;border-top:1px solid #2a2a4a}
+.input-row{display:flex;gap:10px}
+.input-row textarea{flex:1;padding:10px 14px;background:#0a0a1a;border:1px solid #2a2a4a;border-radius:8px;color:#e0e0e0;font-size:13px;resize:none;min-height:44px;max-height:120px;font-family:inherit}
+.input-row textarea:focus{outline:none;border-color:#e94560}
+.input-row button{padding:10px 24px;background:#e94560;color:#fff;border:none;border-radius:8px;cursor:pointer;font-size:13px;font-weight:500;flex-shrink:0}
+.input-row button:hover{background:#d63850}
+.input-row button:disabled{opacity:.5;cursor:not-allowed}
+
+/* 客户信息面板 */
+.customer-panel{width:280px;background:#1a1a2e;border-left:1px solid #2a2a4a;display:flex;flex-direction:column}
+.customer-header{padding:16px;border-bottom:1px solid #2a2a4a;text-align:center}
+.customer-avatar{width:64px;height:64px;border-radius:50%;background:linear-gradient(135deg,#e94560,#f59e0b);display:flex;align-items:center;justify-content:center;font-size:24px;margin:0 auto}
+.customer-name{font-size:15px;color:#e0e0e0;margin-top:8px}
+.customer-id{font-size:11px;color:#666}
+.customer-tabs{display:flex;border-bottom:1px solid #2a2a4a}
+.customer-tabs .tab{flex:1;padding:8px;text-align:center;font-size:12px;color:#888;cursor:pointer;border-bottom:2px solid transparent}
+.customer-tabs .tab.active{border-color:#e94560;color:#e94560}
+.customer-detail{flex:1;overflow-y:auto;padding:12px}
+.detail-section{margin-bottom:16px}
+.detail-section h4{font-size:12px;color:#888;margin-bottom:8px}
+.detail-row{display:flex;justify-content:space-between;padding:4px 0;font-size:12px}
+.detail-row .label{color:#888}
+.detail-row .value{color:#e0e0e0}
+.tag-list{display:flex;flex-wrap:gap;gap:4px}
+.tag{display:inline-block;padding:3px 8px;background:#0f3460;color:#ccc;border-radius:4px;font-size:11px}
+.record-item{padding:8px;border-bottom:1px solid #1a1a3e}
+.record-item .time{font-size:11px;color:#666}
+.record-item .desc{font-size:12px;color:#e0e0e0;margin-top:2px}
+
+/* 渠道图标 */
+.channel-qw{background:linear-gradient(135deg,#1890ff,#096dd9)}
+.channel-wx{background:linear-gradient(135deg,#07c160,#10b981)}
+.channel-im{background:linear-gradient(135deg,#6366f1,#8b5cf6)}
+.channel-whatsapp{background:linear-gradient(135deg,#25d366,#10b981)}
+.channel-other{background:linear-gradient(135deg,#6b7280,#9ca3af)}
+
+/* 滚动条 */
+::-webkit-scrollbar{width:6px}
+::-webkit-scrollbar-track{background:#0a0a1a}
+::-webkit-scrollbar-thumb{background:#2a2a4a;border-radius:3px}
+::-webkit-scrollbar-thumb:hover{background:#3a3a5a}
+</style>
+</head>
+<body>
+<div id="app" class="main">
+  <!-- 左侧账户列表 -->
+  <div class="account-panel">
+    <div v-for="acc in accounts" :key="acc.id" 
+         :class="['account-item', acc.active ? 'active' : '', acc.connected ? '' : 'disabled']"
+         @click="selectAccount(acc)" :title="acc.name">
+      <span>{{acc.icon}}</span>
+      <span v-if="acc.unread>0" class="badge">{{acc.unread}}</span>
+    </div>
+  </div>
+
+  <!-- 会话列表 -->
+  <div class="session-panel">
+    <div class="session-header">
+      <h3>🗨️ 聊天列表</h3>
+      <div class="search">
+        <input v-model="searchKey" placeholder="搜索联系人..." @keyup="filterSessions">
+      </div>
+    </div>
+    <div class="session-list">
+      <div v-for="sess in filteredSessions" :key="sess.sessionId" 
+           :class="['session-item', sess.sessionId === currentSession?.sessionId ? 'active' : '', sess.unread > 0 ? 'unread' : '']"
+           @click="selectSession(sess)">
+        <div class="session-avatar">{{sess.avatar||'?'}}</div>
+        <div class="session-info">
+          <div class="name">{{sess.name}}</div>
+          <div class="msg">{{sess.lastMsg||'暂无消息'}}</div>
+        </div>
+        <div style="text-align:right;margin-left:8px">
+          <div class="session-time">{{sess.lastTime||''}}</div>
+          <span v-if="sess.unread>0" class="badge">{{sess.unread}}</span>
+        </div>
+      </div>
+      <div v-if="filteredSessions.length===0" style="text-align:center;padding:40px;color:#666;font-size:13px">
+        暂无会话记录
+      </div>
+    </div>
+  </div>
+
+  <!-- 聊天区域 -->
+  <div class="chat-panel">
+    <div v-if="currentSession" class="chat-header">
+      <div class="chat-title">
+        <span class="name">{{currentSession.name}}</span>
+        <span class="type">{{channelName(currentSession.channelType)}}</span>
+      </div>
+      <div class="chat-actions">
+        <button @click="toggleControlMode">{{currentSession.controlMode === 'ai' ? '🤖 AI接管中' : '👤 人工接管'}}</button>
+        <button @click="showCustomerInfo=true">👤 客户信息</button>
+      </div>
+    </div>
+    <div v-else class="chat-header">
+      <div class="chat-title">
+        <span class="name">请选择一个会话</span>
+      </div>
+    </div>
+
+    <div class="message-list" ref="messageList">
+      <div v-for="(msg, idx) in messages" :key="idx" :class="['message-item', msg.sendType === 1 ? 'received' : 'sent']">
+        <div class="msg-avatar">{{msg.sendType === 1 ? '👤' : '🤖'}}</div>
+        <div class="msg-content">
+          <div class="msg-bubble">
+            <div class="msg-text">{{msg.content}}</div>
+          </div>
+          <div class="msg-time">{{msg.time}}</div>
+        </div>
+      </div>
+      <div v-if="messages.length===0" style="text-align:center;padding:60px;color:#666">
+        <div style="font-size:48px;margin-bottom:12px">💬</div>
+        <p>开始与客户聊天</p>
+      </div>
+    </div>
+
+    <div class="chat-input">
+      <div class="input-row">
+        <textarea v-model="inputMsg" placeholder="输入消息..." @keyup.enter="sendMessage"></textarea>
+        <button @click="sendMessage" :disabled="!inputMsg.trim()">发送</button>
+      </div>
+    </div>
+  </div>
+
+  <!-- 客户信息面板 -->
+  <div class="customer-panel" v-if="showCustomerInfo">
+    <div class="customer-header">
+      <div class="customer-avatar">{{currentSession?.avatar||'?'}}</div>
+      <div class="customer-name">{{currentSession?.name||'-'}}</div>
+      <div class="customer-id">{{currentSession?.channelSourceId||'-'}}</div>
+    </div>
+    <div class="customer-tabs">
+      <div :class="['tab', customerTab==='basic'?'active':'']" @click="customerTab='basic'">基本信息</div>
+      <div :class="['tab', customerTab==='tags'?'active':'']" @click="customerTab='tags'">标签</div>
+      <div :class="['tab', customerTab==='records'?'active':'']" @click="customerTab='records'">访问记录</div>
+    </div>
+    <div class="customer-detail">
+      <div v-if="customerTab==='basic'" class="detail-section">
+        <h4>📋 基本信息</h4>
+        <div class="detail-row"><span class="label">渠道</span><span class="value">{{channelName(currentSession?.channelType)}}</span></div>
+        <div class="detail-row"><span class="label">来源ID</span><span class="value">{{currentSession?.channelSourceId||'-'}}</span></div>
+        <div class="detail-row"><span class="label">联系人ID</span><span class="value">{{currentSession?.contactId||'-'}}</span></div>
+        <div class="detail-row"><span class="label">会话ID</span><span class="value">{{currentSession?.sessionId||'-'}}</span></div>
+        <div class="detail-row"><span class="label">创建时间</span><span class="value">{{currentSession?.createTime||'-'}}</span></div>
+      </div>
+      <div v-if="customerTab==='tags'" class="detail-section">
+        <h4>🏷️ 客户标签</h4>
+        <div class="tag-list">
+          <span v-for="tag in customerTags" :key="tag" class="tag">{{tag}}</span>
+        </div>
+        <div v-if="customerTags.length===0" style="color:#666;font-size:12px">暂无标签</div>
+      </div>
+      <div v-if="customerTab==='records'" class="detail-section">
+        <h4>📊 访问记录</h4>
+        <div v-for="record in visitRecords" :key="record.time" class="record-item">
+          <div class="time">{{record.time}}</div>
+          <div class="desc">{{record.desc}}</div>
+        </div>
+        <div v-if="visitRecords.length===0" style="color:#666;font-size:12px">暂无访问记录</div>
+      </div>
+    </div>
+  </div>
+</div>
+
+<script>
+const {createApp, ref, computed, watch, nextTick, onMounted} = Vue;
+    createApp({
+        setup(){
+            const searchKey = ref('');
+            const inputMsg = ref('');
+            const showCustomerInfo = ref(true);
+            const customerTab = ref('basic');
+            const messageList = ref(null);
+            const loading = ref(false);
+            
+            // ====== API配置 ======
+            // 从URL参数获取配置(iframe嵌入时由父窗口传递)
+            const getUrlParam = (name) => {
+                const params = new URLSearchParams(window.location.search);
+                return params.get(name) || '';
+            };
+            
+            // 获取API基路径:URL参数 > 父窗口webpack环境变量 > 默认值
+            const getBaseApi = () => {
+                const fromUrl = getUrlParam('baseApi');
+                if (fromUrl) return fromUrl;
+                try {
+                    if (window.parent && window.parent.process && window.parent.process.env) {
+                        return window.parent.process.env.VUE_APP_BASE_API || '/dev-api';
+                    }
+                } catch(e) {}
+                return '/dev-api';
+            };
+            const BASE_API = getBaseApi();
+            
+            // 获取前端类型:URL参数 > 默认值
+            const getFrontendType = () => {
+                return getUrlParam('frontendType') || 'company';
+            };
+            const FRONTEND_TYPE = getFrontendType();
+            
+            // 从Cookie获取Token
+            const getToken = () => {
+                const match = document.cookie.match(/(?:^|;\s*)Web-Token=([^;]*)/);
+                return match ? match[1] : null;
+            };
+            
+            // 获取租户编码:URL参数 > localStorage
+            const getTenantCode = () => {
+                const fromUrl = getUrlParam('tenantCode');
+                if (fromUrl) return fromUrl;
+                try {
+                    return localStorage.getItem('tenantCode') || '';
+                } catch(e) { return ''; }
+            };
+            
+            // 认证请求工具
+            const request = async (url, options = {}) => {
+                const token = getToken();
+                const tenantCode = getTenantCode();
+                const headers = {
+                    'Content-Type': 'application/json',
+                    'X-Frontend-Type': FRONTEND_TYPE,
+                };
+                if (token) {
+                    headers['Authorization'] = 'Bearer ' + token;
+                }
+                if (tenantCode) {
+                    headers['tenant-code'] = tenantCode;
+                }
+                // 合并自定义headers
+                if (options.headers) {
+                    Object.assign(headers, options.headers);
+                }
+                
+                const fullUrl = url.startsWith('http') ? url : (BASE_API + url);
+                const response = await fetch(fullUrl, {
+                    ...options,
+                    headers,
+                    credentials: 'include',
+                });
+                if (!response.ok) {
+                    const text = await response.text().catch(() => '');
+                    throw new Error(`HTTP ${response.status}: ${text || response.statusText}`);
+                }
+                const data = await response.json();
+                if (data.code === 401) {
+                    // Token过期,显示提示而非强制刷新父窗口(避免死循环)
+                    console.warn('[ChatAggregate] 登录已过期');
+                    throw new Error('登录已过期');
+                }
+                return data;
+            };
+
+            // 账户列表
+            const accounts = ref([]);
+
+            // 会话列表
+            const sessions = ref([]);
+
+            // 当前会话
+            const currentSession = ref(null);
+
+            // 消息列表
+            const messages = ref([]);
+
+            // 客户标签
+            const customerTags = ref([]);
+
+            // 访问记录
+            const visitRecords = ref([]);
+
+            // 当前登录用户的企微账户
+            const currentAccount = ref(null);
+
+            // 过滤后的会话
+            const filteredSessions = computed(()=>{
+                if(!searchKey.value) return sessions.value;
+                const key = searchKey.value.toLowerCase();
+                return sessions.value.filter(s=>{
+                    const name = s.nickName || s.name || '';
+                    return name.toLowerCase().includes(key);
+                });
+            });
+
+            // 加载账户列表
+            const loadAccounts = async () => {
+                try {
+                    // 先获取当前登录用户绑定的企微账户
+                    const res = await request('/qw/user/getMyQwUserList');
+                    if (res.code === 200 || res.code === 0) {
+                        const qwAccounts = (res.data || []).map((acc, idx) => ({
+                            id: acc.id || `qw_${idx}`,
+                            name: acc.qwUserName || '企微账户',
+                            icon: '💼',
+                            active: idx === 0,
+                            connected: true,
+                            unread: 0,
+                            type: 'QW',
+                            corpId: acc.corpId,
+                            qwUserId: acc.qwUserId
+                        }));
+                        
+                        // 添加个微账户占位(后续扩展)
+                        const wxAccounts = []; // 暂时为空,后续实现个微账户绑定
+                        
+                        accounts.value = [...qwAccounts, ...wxAccounts];
+                        
+                        if (accounts.value.length > 0) {
+                            currentAccount.value = accounts.value[0];
+                        }
+                    }
+                } catch (error) {
+                    console.error('加载账户失败:', error);
+                    // 降级显示模拟账户
+                    accounts.value = [
+                        {id:'qw', name:'企业微信', icon:'💼', active:true, connected:true, unread:0, type:'QW'},
+                        {id:'wx', name:'个人微信', icon:'💬', active:false, connected:false, unread:0, type:'WX'},
+                    ];
+                    currentAccount.value = accounts.value[0];
+                }
+            };
+
+            // 加载会话列表
+            const loadSessions = async () => {
+                try {
+                    // 先尝试加载chat会话
+                    const chatRes = await request('/chat/chatSession/list?pageNum=1&pageSize=100');
+                    if (chatRes.code === 200 || chatRes.rows) {
+                        const chatSessions = (chatRes.rows || []).map(s => ({
+                            sessionId: s.sessionId,
+                            name: s.nickName || s.userName || '客户',
+                            avatar: (s.nickName || s.userName || '客').charAt(0),
+                            channelType: 'CHAT',
+                            channelSourceId: s.userId,
+                            contactId: s.userId,
+                            lastMsg: '',
+                            lastTime: s.createTime || '',
+                            unread: 0,
+                            createTime: s.createTime,
+                            status: s.status
+                        }));
+                        
+                        // 再尝试加载企微外部联系人作为会话
+                        const qwRes = await request('/qw/externalContact/list?pageNum=1&pageSize=100');
+                        if (qwRes.code === 200 || qwRes.rows) {
+                            const qwSessions = (qwRes.rows || []).map(c => ({
+                                sessionId: `qw_${c.id}`,
+                                name: c.name || c.remark || '企微客户',
+                                avatar: (c.name || c.remark || '客').charAt(0),
+                                channelType: 'QW',
+                                channelSourceId: c.externalUserId,
+                                contactId: c.id,
+                                lastMsg: '',
+                                lastTime: c.createTime || '',
+                                unread: 0,
+                                createTime: c.createTime,
+                                tagIds: c.tagIds,
+                                customerId: c.customerId,
+                                remarkMobiles: c.remarkMobiles
+                            }));
+                            sessions.value = [...qwSessions, ...chatSessions];
+                        } else {
+                            sessions.value = chatSessions;
+                        }
+                    }
+                } catch (error) {
+                    console.error('加载会话失败:', error);
+                    sessions.value = [];
+                }
+                
+                if (sessions.value.length > 0 && !currentSession.value) {
+                    selectSession(sessions.value[0]);
+                }
+            };
+
+            // 选择账户
+            const selectAccount = (acc)=>{
+                if(!acc.connected) return;
+                accounts.value.forEach(a=>a.active = false);
+                acc.active = true;
+                currentAccount.value = acc;
+                loadSessions();
+            };
+
+            // 选择会话
+            const selectSession = async (sess)=>{
+                currentSession.value = sess;
+                // 清除未读
+                sess.unread = 0;
+                // 加载消息
+                await loadMessages(sess);
+                // 加载客户标签和信息
+                await loadCustomerInfo(sess);
+            };
+
+            // 加载消息
+            const loadMessages = async (session) => {
+                messages.value = [];
+                try {
+                    if (session.channelType === 'CHAT') {
+                        // 加载chat会话消息
+                        const chatDetailRes = await request(`/chat/chatSession/${session.sessionId}`);
+                        if (chatDetailRes.code === 200 || chatDetailRes.data) {
+                            const msgRes = await request(`/chat/chatMsg/list?sessionId=${session.sessionId}&pageNum=1&pageSize=100`);
+                            if (msgRes.rows) {
+                                messages.value = msgRes.rows.map(m => ({
+                                    content: m.content,
+                                    sendType: m.sendType,
+                                    time: m.createTime || new Date().toLocaleTimeString('zh-CN',{hour:'2-digit',minute:'2-digit'})
+                                }));
+                            }
+                        }
+                    } else if (session.channelType === 'QW') {
+                        // TODO: 加载企微聊天记录
+                        messages.value = [];
+                    }
+                } catch (error) {
+                    console.error('加载消息失败:', error);
+                    messages.value = [];
+                }
+                
+                nextTick(()=>{
+                    if(messageList.value){
+                        messageList.value.scrollTop = messageList.value.scrollHeight;
+                    }
+                });
+            };
+
+            // 加载客户信息
+            const loadCustomerInfo = async (session) => {
+                customerTags.value = [];
+                visitRecords.value = [];
+                
+                try {
+                    if (session.tagIds && session.tagIds !== '[]') {
+                        // 解析标签ID并加载标签名称
+                        const tagIds = JSON.parse(session.tagIds);
+                        if (tagIds.length > 0) {
+                            const tagRes = await request(`/qw/tag/list?tagIds=${tagIds.join(',')}`);
+                            if (tagRes.rows) {
+                                customerTags.value = tagRes.rows.map(t => t.tagName || t.name);
+                            }
+                        }
+                    }
+                    
+                    // 加载CRM客户信息
+                    if (session.customerId) {
+                        const crmRes = await request(`/crm/customer/${session.customerId}`);
+                        if (crmRes.data) {
+                            // 补充客户基本信息
+                            if (crmRes.data.phone) {
+                                visitRecords.value.push({
+                                    time: new Date().toLocaleDateString('zh-CN'),
+                                    desc: `手机号: ${crmRes.data.phone}`
+                                });
+                            }
+                            if (crmRes.data.email) {
+                                visitRecords.value.push({
+                                    time: new Date().toLocaleDateString('zh-CN'),
+                                    desc: `邮箱: ${crmRes.data.email}`
+                                });
+                            }
+                        }
+                    }
+                    
+                    // 加载fastGpt聊天摘要
+                    try {
+                        const chatRes = await request('/fastGpt/fastGptChatSession/list?pageNum=1&pageSize=10');
+                        if (chatRes.rows) {
+                            const relatedChat = chatRes.rows.find(c => 
+                                c.externalUserId === session.channelSourceId || 
+                                c.userId === session.contactId
+                            );
+                            if (relatedChat) {
+                                visitRecords.value.push({
+                                    time: relatedChat.createTime || new Date().toLocaleDateString('zh-CN'),
+                                    desc: `最近聊天: ${relatedChat.lastMsg || '暂无消息'}`
+                                });
+                            }
+                        }
+                    } catch (err) {
+                        console.error('加载聊天摘要失败:', err);
+                    }
+                } catch (error) {
+                    console.error('加载客户信息失败:', error);
+                }
+            };
+
+            // 发送消息
+            const sendMessage = async ()=>{
+                if(!inputMsg.value.trim() || !currentSession.value) return;
+                
+                const msg = {
+                    content: inputMsg.value, 
+                    sendType: 2, 
+                    time: new Date().toLocaleTimeString('zh-CN',{hour:'2-digit',minute:'2-digit'})
+                };
+                messages.value.push(msg);
+                const contentToSend = inputMsg.value;
+                inputMsg.value = '';
+                
+                nextTick(()=>{
+                    if(messageList.value){
+                        messageList.value.scrollTop = messageList.value.scrollHeight;
+                    }
+                });
+                
+                // 调用发送消息接口
+                try {
+                    if (currentSession.value.channelType === 'QW') {
+                        // 企微发送消息
+                        await request('/qw/msg/send', {
+                            method: 'POST',
+                            body: JSON.stringify({
+                                externalUserId: currentSession.value.channelSourceId,
+                                content: contentToSend,
+                                qwUserId: currentAccount.value?.qwUserId
+                            })
+                        });
+                    } else if (currentSession.value.channelType === 'CHAT') {
+                        // Chat会话发送消息
+                        await request('/chat/chatMsg', {
+                            method: 'POST',
+                            body: JSON.stringify({
+                                sessionId: currentSession.value.sessionId,
+                                content: contentToSend,
+                                sendType: 2
+                            })
+                        });
+                    }
+                } catch (error) {
+                    console.error('发送消息失败:', error);
+                }
+            };
+
+            // 切换控制模式
+            const toggleControlMode = ()=>{
+                if(currentSession.value){
+                    currentSession.value.controlMode = currentSession.value.controlMode === 'ai' ? 'human' : 'ai';
+                }
+            };
+
+            // 渠道名称
+            const channelName = (type)=>{
+                const names = {QW:'企业微信', WX:'个人微信', IM:'系统IM', WHATSAPP:'WhatsApp', OTHER:'其他渠道', CHAT:'在线咨询'};
+                return names[type] || type;
+            };
+
+            // 初始化
+            onMounted(async () => {
+                await loadAccounts();
+                await loadSessions();
+            });
+
+            return {
+                searchKey, inputMsg, showCustomerInfo, customerTab, messageList, loading,
+                accounts, sessions, currentSession, messages, customerTags, visitRecords,
+                filteredSessions,
+                selectAccount, selectSession, sendMessage, toggleControlMode, channelName
+            };
+        }
+    }).mount('#app');
+</script>
+</body>
+</html>

+ 18 - 0
src/api/admin/commissionRecord.js

@@ -0,0 +1,18 @@
+import request from '@/utils/request'
+
+// 查询代理返佣记录列表
+export function listCommissionRecords(query) {
+  return request({
+    url: '/admin/commission-record/list',
+    method: 'get',
+    params: query
+  })
+}
+
+// 获取返佣记录详情
+export function getCommissionRecord(id) {
+  return request({
+    url: '/admin/commission-record/' + id,
+    method: 'get'
+  })
+}

+ 18 - 0
src/api/admin/consumeRecord.js

@@ -0,0 +1,18 @@
+import request from '@/utils/request'
+
+// 查询租户消费扣款记录列表
+export function listConsumeRecords(query) {
+  return request({
+    url: '/admin/consume-record/list',
+    method: 'get',
+    params: query
+  })
+}
+
+// 获取消费记录详情
+export function getConsumeRecord(id) {
+  return request({
+    url: '/admin/consume-record/' + id,
+    method: 'get'
+  })
+}

+ 18 - 0
src/api/admin/dailyStatistics.js

@@ -0,0 +1,18 @@
+import request from '@/utils/request'
+
+// ======== 每日统计 ========
+
+// 代理下租户每日消费明细
+export function getDailyAgentTenants(params) {
+  return request({ url: '/admin/statistics/daily/agentTenants', method: 'get', params })
+}
+
+// 各服务类型每日利润
+export function getDailyServiceTypeProfit(params) {
+  return request({ url: '/admin/statistics/daily/serviceTypeProfit', method: 'get', params })
+}
+
+// 所有代理每日汇总
+export function getDailyAgentSummary(params) {
+  return request({ url: '/admin/statistics/daily/agentSummary', method: 'get', params })
+}

+ 10 - 0
src/api/admin/liveVideo.js

@@ -0,0 +1,10 @@
+import request from '@/utils/request'
+
+// 查询所有租户直播视频列表
+export function listAllLiveVideos(query) {
+  return request({
+    url: '/admin/liveVideo/list',
+    method: 'get',
+    params: query
+  })
+}

+ 19 - 19
src/api/admin/lobster.js

@@ -4,89 +4,89 @@ import request from '@/utils/request'
 
 // 查看所有租户的工作流实例列表
 export function listAllInstances(params) {
-  return request({ url: '/admin/lobster/instance/list', method: 'get', params })
+  return request({ url: '/workflow/lobster/instance/list', method: 'get', params })
 }
 
 // 查看指定实例详情(跨租户)
 export function getInstanceDetail(instanceId) {
-  return request({ url: `/admin/lobster/instance/${instanceId}`, method: 'get' })
+  return request({ url: `/workflow/lobster/instance/${instanceId}`, method: 'get' })
 }
 
 // 查看指定实例的节点执行日志
 export function getInstanceNodeLogs(instanceId) {
-  return request({ url: `/admin/lobster/instance/node-logs/${instanceId}`, method: 'get' })
+  return request({ url: `/workflow/lobster/instance/node-logs/${instanceId}`, method: 'get' })
 }
 
 // 强制终止指定实例(管理级操作)
 export function forceTerminateInstance(instanceId, reason) {
-  return request({ url: `/admin/lobster/instance/terminate/${instanceId}`, method: 'post', params: { reason } })
+  return request({ url: `/workflow/lobster/instance/terminate/${instanceId}`, method: 'post', params: { reason } })
 }
 
 // 全局工作流运行统计
 export function getInstanceStats() {
-  return request({ url: '/admin/lobster/instance/stats', method: 'get' })
+  return request({ url: '/workflow/lobster/instance/stats', method: 'get' })
 }
 
 // ======== 全局死信队列管理 ========
 
 export function listAllDeadLetters(params) {
-  return request({ url: '/admin/lobster/dead-letter/list', method: 'get', params })
+  return request({ url: '/workflow/lobster/dead-letter/list', method: 'get', params })
 }
 
 export function retryAllDeadLetters() {
-  return request({ url: '/admin/lobster/dead-letter/retry-all', method: 'post' })
+  return request({ url: '/workflow/lobster/dead-letter/retry-all', method: 'post' })
 }
 
 export function getDeadLetterStats() {
-  return request({ url: '/admin/lobster/dead-letter/stats', method: 'get' })
+  return request({ url: '/workflow/lobster/dead-letter/stats', method: 'get' })
 }
 
 // ======== 全局节点审核 ========
 
 export function listAllEventAudits(params) {
-  return request({ url: '/admin/lobster/event-audit/list', method: 'get', params })
+  return request({ url: '/workflow/lobster/event-audit/list', method: 'get', params })
 }
 
 export function approveEventAudit(id) {
-  return request({ url: `/admin/lobster/event-audit/approve/${id}`, method: 'post' })
+  return request({ url: `/workflow/lobster/event-audit/approve/${id}`, method: 'post' })
 }
 
 export function rejectEventAudit(id, data) {
-  return request({ url: `/admin/lobster/event-audit/reject/${id}`, method: 'post', data })
+  return request({ url: `/workflow/lobster/event-audit/reject/${id}`, method: 'post', data })
 }
 
 export function getEventAuditDetail(id) {
-  return request({ url: `/admin/lobster/event-audit/${id}`, method: 'get' })
+  return request({ url: `/workflow/lobster/event-audit/${id}`, method: 'get' })
 }
 
 // ======== 全局优化建议 ========
 
 export function listAllOptimization(params) {
-  return request({ url: '/admin/lobster/optimization/list', method: 'get', params })
+  return request({ url: '/workflow/lobster/optimization/list', method: 'get', params })
 }
 
 export function batchAuditOptimization(data) {
-  return request({ url: '/admin/lobster/optimization/batch-audit', method: 'post', data })
+  return request({ url: '/workflow/lobster/optimization/batch-audit', method: 'post', data })
 }
 
 export function getOptimizationStats() {
-  return request({ url: '/admin/lobster/optimization/stats', method: 'get' })
+  return request({ url: '/workflow/lobster/optimization/stats', method: 'get' })
 }
 
 // ======== 全局Token计费统计 ========
 
 export function listAllBillingRecords(params) {
-  return request({ url: '/admin/lobster/billing/records', method: 'get', params })
+  return request({ url: '/workflow/lobster/billing/records', method: 'get', params })
 }
 
 export function getBillingStats() {
-  return request({ url: '/admin/lobster/billing/stats', method: 'get' })
+  return request({ url: '/workflow/lobster/billing/stats', method: 'get' })
 }
 
 export function getTokenCoefficient() {
-  return request({ url: '/admin/lobster/billing/token-coefficient', method: 'get' })
+  return request({ url: '/workflow/lobster/billing/token-coefficient', method: 'get' })
 }
 
 export function updateTokenCoefficient(data) {
-  return request({ url: '/admin/lobster/billing/token-coefficient', method: 'put', data })
+  return request({ url: '/workflow/lobster/billing/token-coefficient', method: 'put', data })
 }

+ 18 - 0
src/api/admin/rechargeRecord.js

@@ -0,0 +1,18 @@
+import request from '@/utils/request'
+
+// 查询租户充值记录列表
+export function listRechargeRecords(query) {
+  return request({
+    url: '/admin/recharge-record/list',
+    method: 'get',
+    params: query
+  })
+}
+
+// 获取充值记录详情
+export function getRechargeRecord(id) {
+  return request({
+    url: '/admin/recharge-record/' + id,
+    method: 'get'
+  })
+}

+ 19 - 0
src/api/admin/serviceCost.js

@@ -0,0 +1,19 @@
+import request from '@/utils/request'
+
+// ======== 服务成本配置 ========
+
+export function listServiceCost() {
+  return request({ url: '/admin/serviceCost/list', method: 'get' })
+}
+
+export function getServiceCostByType(serviceType) {
+  return request({ url: `/admin/serviceCost/${serviceType}`, method: 'get' })
+}
+
+export function updateServiceCost(data) {
+  return request({ url: '/admin/serviceCost', method: 'put', data })
+}
+
+export function getEnabledServiceTypes() {
+  return request({ url: '/admin/serviceCost/enabled', method: 'get' })
+}

+ 10 - 0
src/api/admin/videoResource.js

@@ -0,0 +1,10 @@
+import request from '@/utils/request'
+
+// 查询所有租户视频资源列表
+export function listAllVideoResources(query) {
+  return request({
+    url: '/admin/videoResource/list',
+    method: 'get',
+    params: query
+  })
+}

+ 43 - 0
src/api/admin/withdrawalManage.js

@@ -0,0 +1,43 @@
+import request from '@/utils/request'
+
+// 查询提现申请列表
+export function listWithdrawals(query) {
+  return request({
+    url: '/admin/withdrawal/list',
+    method: 'get',
+    params: query
+  })
+}
+
+// 获取提现申请详情
+export function getWithdrawal(id) {
+  return request({
+    url: '/admin/withdrawal/' + id,
+    method: 'get'
+  })
+}
+
+// 审核通过
+export function approveWithdrawal(id) {
+  return request({
+    url: '/admin/withdrawal/' + id + '/approve',
+    method: 'put'
+  })
+}
+
+// 审核拒绝
+export function rejectWithdrawal(id, reason) {
+  return request({
+    url: '/admin/withdrawal/' + id + '/reject',
+    method: 'put',
+    params: { reason }
+  })
+}
+
+// 确认打款
+export function confirmPaid(id) {
+  return request({
+    url: '/admin/withdrawal/' + id + '/paid',
+    method: 'put'
+  })
+}

+ 4 - 4
src/api/callRecord/callRecord.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询外呼记录质检列表
 export function listApi(query) {
   return request({
-    url: '/callRecord/list',
+    url: '/company/callRecord/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listApi(query) {
 // 查询外呼记录质检详细
 export function getApi(id) {
   return request({
-    url: '/callRecord/' + id,
+    url: '/company/callRecord/' + id,
     method: 'get'
   })
 }
@@ -38,7 +38,7 @@ export function updateApi(data) {
 // 删除外呼记录质检
 export function delApi(id) {
   return request({
-    url: '/callRecord/' + id,
+    url: '/company/callRecord/' + id,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delApi(id) {
 // 导出外呼记录质检
 export function exportApi(query) {
   return request({
-    url: '/callRecord/export',
+    url: '/company/callRecord/export',
     method: 'post',
     params: query
   })

+ 6 - 6
src/api/complaint/category.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询投诉分类列表
 export function listCategory(query) {
   return request({
-    url: '/complaint/category/list',
+    url: '/store/complaint/category/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listCategory(query) {
 // 查询投诉分类详细
 export function getCategory(id) {
   return request({
-    url: '/complaint/category/' + id,
+    url: '/store/complaint/category/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getCategory(id) {
 // 新增投诉分类
 export function addCategory(data) {
   return request({
-    url: '/complaint/category',
+    url: '/store/complaint/category',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addCategory(data) {
 // 修改投诉分类
 export function updateCategory(data) {
   return request({
-    url: '/complaint/category',
+    url: '/store/complaint/category',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateCategory(data) {
 // 删除投诉分类
 export function delCategory(ids) {
   return request({
-    url: '/complaint/category/' + ids,
+    url: '/store/complaint/category/' + ids,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delCategory(ids) {
 // 修改投诉分类状态
 export function changeStatus(data) {
   return request({
-    url: '/complaint/category/status',
+    url: '/store/complaint/category/status',
     method: 'put',
     data: data
   })

+ 7 - 7
src/api/complaint/complaint.js

@@ -12,7 +12,7 @@ export function submitComplaint(data) {
 // 根据ID查询投诉详情
 export function getComplaintById(id) {
   return request({
-    url: `/complaint/${id}`,
+    url: `/store/complaint/${id}`,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getComplaintById(id) {
 // 根据投诉单号查询投诉详情
 export function getComplaintByNo(complaintNo) {
   return request({
-    url: `/complaint/no/${complaintNo}`,
+    url: `/store/complaint/no/${complaintNo}`,
     method: 'get'
   })
 }
@@ -28,7 +28,7 @@ export function getComplaintByNo(complaintNo) {
 // 分页查询投诉列表
 export function getComplaintPage(data) {
   return request({
-    url: '/complaint/list',
+    url: '/store/complaint/list',
     method: 'post',
     data: data
   })
@@ -37,7 +37,7 @@ export function getComplaintPage(data) {
 // 更新投诉信息
 export function updateComplaint(id, data) {
   return request({
-    url: `/complaint/${id}`,
+    url: `/store/complaint/${id}`,
     method: 'put',
     data: {
       ...data,
@@ -49,7 +49,7 @@ export function updateComplaint(id, data) {
 // 删除投诉
 export function deleteComplaint(id) {
   return request({
-    url: `/complaint/${id}`,
+    url: `/store/complaint/${id}`,
     method: 'delete'
   })
 }
@@ -57,7 +57,7 @@ export function deleteComplaint(id) {
 // 处理投诉(快捷更新状态为已处理)
 export function handleComplaint(id) {
   return request({
-    url: `/complaint/${id}`,
+    url: `/store/complaint/${id}`,
     method: 'put',
     data: {
       status: '1' // 假设1表示已处理状态
@@ -67,7 +67,7 @@ export function handleComplaint(id) {
 // 新增:获取所有投诉分类
 export function getAllCategory() {
   return request({
-    url: '/complaint/queryAllCategory',
+    url: '/store/complaint/queryAllCategory',
     method: 'post'
   })
 }

+ 6 - 6
src/api/course/push.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询营销活动推送列表
 export function listPush(query) {
   return request({
-    url: '/push/push/list',
+    url: '/qw/push/push/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listPush(query) {
 // 查询营销活动推送详细
 export function getPush(id) {
   return request({
-    url: '/push/push/' + id,
+    url: '/qw/push/push/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getPush(id) {
 // 新增营销活动推送
 export function addPush(data) {
   return request({
-    url: '/push/push',
+    url: '/qw/push/push',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addPush(data) {
 // 修改营销活动推送
 export function updatePush(data) {
   return request({
-    url: '/push/push',
+    url: '/qw/push/push',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updatePush(data) {
 // 删除营销活动推送
 export function delPush(id) {
   return request({
-    url: '/push/push/' + id,
+    url: '/qw/push/push/' + id,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delPush(id) {
 // 导出营销活动推送
 export function exportPush(query) {
   return request({
-    url: '/push/push/export',
+    url: '/qw/push/push/export',
     method: 'get',
     params: query
   })

+ 5 - 5
src/api/courseFinishTemp/course.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询列表
 export function listApi(query) {
   return request({
-    url: '/courseFinishTemp/course/list',
+    url: '/course/courseFinishTemp/course/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listApi(query) {
 // 查询详细
 export function getApi(id) {
   return request({
-    url: '/courseFinishTemp/course/' + id,
+    url: '/course/courseFinishTemp/course/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getApi(id) {
 // 新增
 export function addApi(data) {
   return request({
-    url: '/courseFinishTemp/course',
+    url: '/course/courseFinishTemp/course',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addApi(data) {
 // 修改
 export function updateApi(data) {
   return request({
-    url: '/courseFinishTemp/course',
+    url: '/course/courseFinishTemp/course',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateApi(data) {
 // 删除
 export function delApi(id) {
   return request({
-    url: '/courseFinishTemp/course/' + id,
+    url: '/course/courseFinishTemp/course/' + id,
     method: 'delete'
   })
 }

+ 2 - 2
src/api/crm/customer.js

@@ -129,7 +129,7 @@ export function getCustomer(customerId) {
 
 export function addCustomer(data) {
   return request({
-    url: '/crm/customer',
+    url: '/crm/customer/addCrm',
     method: 'post',
     data: data
   })
@@ -138,7 +138,7 @@ export function addCustomer(data) {
 // 修改客户
 export function updateCustomer(data) {
   return request({
-    url: '/crm/customer',
+    url: '/crm/customer/editCrm',
     method: 'put',
     data: data
   })

+ 6 - 6
src/api/fastGpt/readPackage.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询红包消耗统计列表
 export function listFastgptReadpackage(query) {
   return request({
-    url: '/fast_gpt/read_package/list',
+    url: '/fastGpt/read_package/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listFastgptReadpackage(query) {
 // 查询红包消耗统计详细
 export function getFastgptReadpackage(id) {
   return request({
-    url: '/fast_gpt/read_package/' + id,
+    url: '/fastGpt/read_package/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getFastgptReadpackage(id) {
 // 新增红包消耗统计
 export function addFastgptReadpackage(data) {
   return request({
-    url: '/fast_gpt/read_package',
+    url: '/fastGpt/read_package',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addFastgptReadpackage(data) {
 // 修改红包消耗统计
 export function updateFastgptReadpackage(data) {
   return request({
-    url: '/fast_gpt/read_package',
+    url: '/fastGpt/read_package',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateFastgptReadpackage(data) {
 // 删除红包消耗统计
 export function delFastgptReadpackage(id) {
   return request({
-    url: '/fast_gpt/read_package/' + id,
+    url: '/fastGpt/read_package/' + id,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delFastgptReadpackage(id) {
 // 导出红包消耗统计
 export function exportFastgptReadpackage(query) {
   return request({
-    url: '/fast_gpt/read_package/export',
+    url: '/fastGpt/read_package/export',
     method: 'post',
     params: query
   })

+ 5 - 5
src/api/food/record.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询饮食记录列表
 export function listFoodRecord(query) {
   return request({
-    url: '/food-record/admin/list',
+    url: '/his/food-record/admin/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listFoodRecord(query) {
 // 查询饮食记录详细
 export function getFoodRecord(id) {
   return request({
-    url: '/food-record/getRecordInfo/' + id,
+    url: '/his/food-record/getRecordInfo/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getFoodRecord(id) {
 // 新增饮食记录
 export function addFoodRecord(data) {
   return request({
-    url: '/food-record/addRecord',
+    url: '/his/food-record/addRecord',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addFoodRecord(data) {
 // 修改饮食记录
 export function updateFoodRecord(data) {
   return request({
-    url: '/food-record/editRecord',
+    url: '/his/food-record/editRecord',
     method: 'post',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateFoodRecord(data) {
 // 删除饮食记录
 export function delFoodRecord(id) {
   return request({
-    url: '/food-record/deleteRecord/' + id,
+    url: '/his/food-record/deleteRecord/' + id,
     method: 'post'
   })
 }

+ 8 - 8
src/api/his/redPacketConfig.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询多商户配置列表
 export function listMore(query) {
   return request({
-    url: '/redPacket/more/list',
+    url: '/store/redPacket/more/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listMore(query) {
 
 export function getRedPacketMchId(query) {
   return request({
-    url: '/redPacket/more/getRedPacketConfig',
+    url: '/store/redPacket/more/getRedPacketConfig',
     method: 'get',
     params: query
   })
@@ -22,7 +22,7 @@ export function getRedPacketMchId(query) {
 // 查询多商户配置详细
 export function getMore(id) {
   return request({
-    url: '/redPacket/more/' + id,
+    url: '/store/redPacket/more/' + id,
     method: 'get'
   })
 }
@@ -30,7 +30,7 @@ export function getMore(id) {
 // 新增多商户配置
 export function addMore(data) {
   return request({
-    url: '/redPacket/more',
+    url: '/store/redPacket/more',
     method: 'post',
     data: data
   })
@@ -39,7 +39,7 @@ export function addMore(data) {
 // 修改多商户配置
 export function updateMore(data) {
   return request({
-    url: '/redPacket/more',
+    url: '/store/redPacket/more',
     method: 'put',
     data: data
   })
@@ -47,7 +47,7 @@ export function updateMore(data) {
 
 export function updateChangeMchId(data) {
   return request({
-    url: '/redPacket/more/updateChangeMchId',
+    url: '/store/redPacket/more/updateChangeMchId',
     method: 'post',
     data: data
   })
@@ -56,7 +56,7 @@ export function updateChangeMchId(data) {
 // 删除多商户配置
 export function delMore(id) {
   return request({
-    url: '/redPacket/more/' + id,
+    url: '/store/redPacket/more/' + id,
     method: 'delete'
   })
 }
@@ -64,7 +64,7 @@ export function delMore(id) {
 // 导出多商户配置
 export function exportMore(query) {
   return request({
-    url: '/redPacket/more/export',
+    url: '/store/redPacket/more/export',
     method: 'get',
     params: query
   })

+ 2 - 2
src/api/hisStore/answer.js

@@ -5,7 +5,7 @@ import request from '@/utils/request'
 // 查询问答详细
 export function getAnswer(id) {
   return request({
-    url: '/store/answer/' + id,
+    url: '/his/answer/' + id,
     method: 'get'
   })
 }
@@ -13,7 +13,7 @@ export function getAnswer(id) {
 // 问答列表选项
 export function questionOptions() {
   return request({
-    url: '/store/answer/allList',
+    url: '/his/answer/allList',
     method: 'get',
   })
 }

+ 7 - 7
src/api/hisStore/chineseMedicine.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询中药科普管理列表
 export function listChineseMedicine(query) {
   return request({
-    url: '/store/his/chineseMedicine/list',
+    url: '/his/chineseMedicine/list',
     method: 'get',
     params: query
   })
@@ -12,21 +12,21 @@ export function listChineseMedicine(query) {
 // 查询中药科普管理详细
 export function getChineseMedicine(id) {
   return request({
-    url: '/store/his/chineseMedicine/' + id,
+    url: '/his/chineseMedicine/' + id,
     method: 'get'
   })
 }
 // 下载导入模板
 export function importTemplate() {
   return request({
-    url: '/store/his/chineseMedicine/importTemplate',
+    url: '/his/chineseMedicine/importTemplate',
     method: 'get'
   })
 }
 // 新增中药科普管理
 export function addChineseMedicine(data) {
   return request({
-    url: '/store/his/chineseMedicine',
+    url: '/his/chineseMedicine',
     method: 'post',
     data: data
   })
@@ -35,7 +35,7 @@ export function addChineseMedicine(data) {
 // 修改中药科普管理
 export function updateChineseMedicine(data) {
   return request({
-    url: '/store/his/chineseMedicine',
+    url: '/his/chineseMedicine',
     method: 'put',
     data: data
   })
@@ -44,7 +44,7 @@ export function updateChineseMedicine(data) {
 // 删除中药科普管理
 export function delChineseMedicine(id) {
   return request({
-    url: '/store/his/chineseMedicine/' + id,
+    url: '/his/chineseMedicine/' + id,
     method: 'delete'
   })
 }
@@ -52,7 +52,7 @@ export function delChineseMedicine(id) {
 // 导出中药科普管理
 export function exportChineseMedicine(query) {
   return request({
-    url: '/store/his/chineseMedicine/export',
+    url: '/his/chineseMedicine/export',
     method: 'get',
     params: query
   })

+ 8 - 8
src/api/hisStore/collection.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询用户信息采集列表
 export function listCollection(query) {
   return request({
-    url: '/hisStore/collection/list',
+    url: '/store/store/collection/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listCollection(query) {
 // 查询用户信息采集详细
 export function getCollection(id) {
   return request({
-    url: '/hisStore/collection/' + id,
+    url: '/store/store/collection/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getCollection(id) {
 // 查询用户信息采集详细
 export function getInfo(query) {
   return request({
-    url: '/hisStore/collection/getInfo',
+    url: '/store/store/collection/getInfo',
     method: 'get',
     params: query
   })
@@ -29,7 +29,7 @@ export function getInfo(query) {
 // 新增用户信息采集
 export function addCollection(data) {
   return request({
-    url: '/hisStore/collection',
+    url: '/store/store/collection',
     method: 'post',
     data: data
   })
@@ -38,7 +38,7 @@ export function addCollection(data) {
 // 修改用户信息采集
 export function updateCollection(data) {
   return request({
-    url: '/hisStore/collection',
+    url: '/store/store/collection',
     method: 'put',
     data: data
   })
@@ -47,7 +47,7 @@ export function updateCollection(data) {
 // 删除用户信息采集
 export function delCollection(id) {
   return request({
-    url: '/hisStore/collection/' + id,
+    url: '/store/store/collection/' + id,
     method: 'delete'
   })
 }
@@ -55,7 +55,7 @@ export function delCollection(id) {
 // 导出用户信息采集
 export function exportCollection(query) {
   return request({
-    url: '/hisStore/collection/export',
+    url: '/store/store/collection/export',
     method: 'get',
     params: query
   })
@@ -64,7 +64,7 @@ export function exportCollection(query) {
 
 export function getWxaCodeCollectionUnLimit(collectionId) {
   return request({
-    url: '/hisStore/collection/getWxaCodeCollectionUnLimit/'+collectionId,
+    url: '/store/store/collection/getWxaCodeCollectionUnLimit/'+collectionId,
     method: 'get',
   })
 }

+ 6 - 6
src/api/hisStore/department.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询科室列表
 export function listDepartment(query) {
   return request({
-    url: '/store/his/department/list',
+    url: '/his/department/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listDepartment(query) {
 // 查询科室详细
 export function getDepartment(deptId) {
   return request({
-    url: '/store/his/department/' + deptId,
+    url: '/his/department/' + deptId,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getDepartment(deptId) {
 // 新增科室
 export function addDepartment(data) {
   return request({
-    url: '/store/his/department',
+    url: '/his/department',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addDepartment(data) {
 // 修改科室
 export function updateDepartment(data) {
   return request({
-    url: '/store/his/department',
+    url: '/his/department',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateDepartment(data) {
 // 删除科室
 export function delDepartment(deptId) {
   return request({
-    url: '/store/his/department/' + deptId,
+    url: '/his/department/' + deptId,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delDepartment(deptId) {
 // 导出科室
 export function exportDepartment(query) {
   return request({
-    url: '/store/his/department/export',
+    url: '/his/department/export',
     method: 'get',
     params: query
   })

+ 7 - 7
src/api/hisStore/disease.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询疾病列表
 export function listDisease(query) {
   return request({
-    url: '/store/his/disease/list',
+    url: '/his/disease/list',
     method: 'get',
     params: query
   })
@@ -12,14 +12,14 @@ export function listDisease(query) {
 // 查询疾病详细
 export function getDisease(diseaseId) {
   return request({
-    url: '/store/his/disease/' + diseaseId,
+    url: '/his/disease/' + diseaseId,
     method: 'get'
   })
 }
 // 查询科室列表
 export function listDepartment(query) {
   return request({
-    url: '/store/his/department/listOptions',
+    url: '/his/department/listOptions',
     method: 'get',
     params: query
   })
@@ -27,7 +27,7 @@ export function listDepartment(query) {
 // 新增疾病
 export function addDisease(data) {
   return request({
-    url: '/store/his/disease',
+    url: '/his/disease',
     method: 'post',
     data: data
   })
@@ -36,7 +36,7 @@ export function addDisease(data) {
 // 修改疾病
 export function updateDisease(data) {
   return request({
-    url: '/store/his/disease',
+    url: '/his/disease',
     method: 'put',
     data: data
   })
@@ -45,7 +45,7 @@ export function updateDisease(data) {
 // 删除疾病
 export function delDisease(diseaseId) {
   return request({
-    url: '/store/his/disease/' + diseaseId,
+    url: '/his/disease/' + diseaseId,
     method: 'delete'
   })
 }
@@ -53,7 +53,7 @@ export function delDisease(diseaseId) {
 // 导出疾病
 export function exportDisease(query) {
   return request({
-    url: '/store/his/disease/export',
+    url: '/his/disease/export',
     method: 'get',
     params: query
   })

+ 7 - 7
src/api/hisStore/doctorArticle.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询医生文章列表
 export function listArticle(query) {
   return request({
-    url: '/store/his/doctorArticle/list',
+    url: '/his/doctorArticle/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listArticle(query) {
 // 查询医生名称列表
 export function listdocuser(query) {
   return request({
-    url: '/store/his/doctor/userdoc/list',
+    url: '/his/doctor/userdoc/list',
     method: 'get',
     params: query
   })
@@ -21,7 +21,7 @@ export function listdocuser(query) {
 // 查询医生文章详细
 export function getArticle(articleId) {
   return request({
-    url: '/store/his/doctorArticle/' + articleId,
+    url: '/his/doctorArticle/' + articleId,
     method: 'get'
   })
 }
@@ -29,7 +29,7 @@ export function getArticle(articleId) {
 // 新增医生文章
 export function addArticle(data) {
   return request({
-    url: '/store/his/doctorArticle',
+    url: '/his/doctorArticle',
     method: 'post',
     data: data
   })
@@ -38,7 +38,7 @@ export function addArticle(data) {
 // 修改医生文章
 export function updateArticle(data) {
   return request({
-    url: '/store/his/doctorArticle',
+    url: '/his/doctorArticle',
     method: 'put',
     data: data
   })
@@ -47,7 +47,7 @@ export function updateArticle(data) {
 // 删除医生文章
 export function delArticle(articleId) {
   return request({
-    url: '/store/his/doctorArticle/' + articleId,
+    url: '/his/doctorArticle/' + articleId,
     method: 'delete'
   })
 }
@@ -55,7 +55,7 @@ export function delArticle(articleId) {
 // 导出医生文章
 export function exportArticle(query) {
   return request({
-    url: '/store/his/doctorArticle/export',
+    url: '/his/doctorArticle/export',
     method: 'get',
     params: query
   })

+ 7 - 7
src/api/hisStore/famousPrescribe.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询经典名方列表
 export function listFamousPrescribe(query) {
   return request({
-    url: '/store/his/famousPrescribe/list',
+    url: '/his/famousPrescribe/list',
     method: 'get',
     params: query
   })
@@ -12,21 +12,21 @@ export function listFamousPrescribe(query) {
 // 查询经典名方详细
 export function getFamousPrescribe(id) {
   return request({
-    url: '/store/his/famousPrescribe/' + id,
+    url: '/his/famousPrescribe/' + id,
     method: 'get'
   })
 }
 // 下载导入模板
 export function importTemplate() {
   return request({
-    url: '/store/his/chineseMedicine/importTemplate',
+    url: '/his/chineseMedicine/importTemplate',
     method: 'get'
   })
 }
 // 新增经典名方
 export function addFamousPrescribe(data) {
   return request({
-    url: '/store/his/famousPrescribe',
+    url: '/his/famousPrescribe',
     method: 'post',
     data: data
   })
@@ -35,7 +35,7 @@ export function addFamousPrescribe(data) {
 // 修改经典名方
 export function updateFamousPrescribe(data) {
   return request({
-    url: '/store/his/famousPrescribe',
+    url: '/his/famousPrescribe',
     method: 'put',
     data: data
   })
@@ -44,7 +44,7 @@ export function updateFamousPrescribe(data) {
 // 删除经典名方
 export function delFamousPrescribe(id) {
   return request({
-    url: '/store/his/famousPrescribe/' + id,
+    url: '/his/famousPrescribe/' + id,
     method: 'delete'
   })
 }
@@ -52,7 +52,7 @@ export function delFamousPrescribe(id) {
 // 导出经典名方
 export function exportFamousPrescribe(query) {
   return request({
-    url: '/store/his/famousPrescribe/export',
+    url: '/his/famousPrescribe/export',
     method: 'get',
     params: query
   })

+ 7 - 7
src/api/hisStore/illnessLibrary.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询中医疾病列表
 export function listillnessLibrary(query) {
   return request({
-    url: '/store/his/illnessLibrary/list',
+    url: '/his/illnessLibrary/list',
     method: 'get',
     params: query
   })
@@ -12,13 +12,13 @@ export function listillnessLibrary(query) {
 // 查询中医疾病详细
 export function getillnessLibrary(illnessId) {
   return request({
-    url: '/store/his/illnessLibrary/' + illnessId,
+    url: '/his/illnessLibrary/' + illnessId,
     method: 'get'
   })
 }
 export function getIllness(query) {
   return request({
-    url: '/store/his/illnessLibrary/getIllness/',
+    url: '/his/illnessLibrary/getIllness/',
     method: 'get',
     params: query
   })
@@ -27,7 +27,7 @@ export function getIllness(query) {
 // 新增中医疾病
 export function addillnessLibrary(data) {
   return request({
-    url: '/store/his/illnessLibrary',
+    url: '/his/illnessLibrary',
     method: 'post',
     data: data
   })
@@ -36,7 +36,7 @@ export function addillnessLibrary(data) {
 // 修改中医疾病
 export function updateillnessLibrary(data) {
   return request({
-    url: '/store/his/illnessLibrary',
+    url: '/his/illnessLibrary',
     method: 'put',
     data: data
   })
@@ -45,7 +45,7 @@ export function updateillnessLibrary(data) {
 // 删除中医疾病
 export function delillnessLibrary(illnessId) {
   return request({
-    url: '/store/his/illnessLibrary/' + illnessId,
+    url: '/his/illnessLibrary/' + illnessId,
     method: 'delete'
   })
 }
@@ -53,7 +53,7 @@ export function delillnessLibrary(illnessId) {
 // 导出中医疾病
 export function exportillnessLibrary(query) {
   return request({
-    url: '/store/his/illnessLibrary/export',
+    url: '/his/illnessLibrary/export',
     method: 'get',
     params: query
   })

+ 10 - 10
src/api/hisStore/integralOrder.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询积分商品订单列表
 export function listIntegralOrder(query) {
   return request({
-    url: '/store/his/integralOrder/list',
+    url: '/his/integralOrder/list',
     method: 'get',
     params: query
   })
@@ -12,25 +12,25 @@ export function listIntegralOrder(query) {
 // 查询积分商品订单详细
 export function getIntegralOrder(orderId) {
   return request({
-    url: '/store/his/integralOrder/' + orderId,
+    url: '/his/integralOrder/' + orderId,
     method: 'get'
   })
 }
 export function getExpress(orderId) {
   return request({
-    url: '/store/his/integralOrder/getExpress/' + orderId,
+    url: '/his/integralOrder/getExpress/' + orderId,
     method: 'get'
   })
 }
 export function importTemplate() {
   return request({
-    url: '/store/his/integralOrder/importTemplate',
+    url: '/his/integralOrder/importTemplate',
     method: 'get'
   })
 }
 export function sendgoods(data) {
   return request({
-    url: '/store/his/integralOrder/sendGoods',
+    url: '/his/integralOrder/sendGoods',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function sendgoods(data) {
 // 新增积分商品订单
 export function addIntegralOrder(data) {
   return request({
-    url: '/store/his/integralOrder',
+    url: '/his/integralOrder',
     method: 'post',
     data: data
   })
@@ -47,7 +47,7 @@ export function addIntegralOrder(data) {
 // 修改积分商品订单
 export function updateIntegralOrder(data) {
   return request({
-    url: '/store/his/integralOrder',
+    url: '/his/integralOrder',
     method: 'put',
     data: data
   })
@@ -56,7 +56,7 @@ export function updateIntegralOrder(data) {
 // 删除积分商品订单
 export function delIntegralOrder(orderId) {
   return request({
-    url: '/store/his/integralOrder/' + orderId,
+    url: '/his/integralOrder/' + orderId,
     method: 'delete'
   })
 }
@@ -64,7 +64,7 @@ export function delIntegralOrder(orderId) {
 // 导出积分商品订单
 export function exportIntegralOrder(query) {
   return request({
-    url: '/store/his/integralOrder/export',
+    url: '/his/integralOrder/export',
     method: 'get',
     params: query
   })
@@ -74,7 +74,7 @@ export function exportIntegralOrder(query) {
 // 查询收货人电话
 export function getOrderUserPhone(orderId) {
   return request({
-    url: '/store/his/integralOrder/queryPhone/' + orderId,
+    url: '/his/integralOrder/queryPhone/' + orderId,
     method: 'get'
   })
 }

+ 7 - 7
src/api/hisStore/medicatedFood.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询药膳食疗列表
 export function listMedicatedFood(query) {
   return request({
-    url: '/store/his/medicatedFood/list',
+    url: '/his/medicatedFood/list',
     method: 'get',
     params: query
   })
@@ -12,14 +12,14 @@ export function listMedicatedFood(query) {
 // 下载导入模板
 export function importTemplate() {
   return request({
-    url: '/store/his/medicatedFood/importTemplate',
+    url: '/his/medicatedFood/importTemplate',
     method: 'get'
   })
 }
 // 查询药膳食疗详细
 export function getMedicatedFood(id) {
   return request({
-    url: '/store/his/medicatedFood/' + id,
+    url: '/his/medicatedFood/' + id,
     method: 'get'
   })
 }
@@ -27,7 +27,7 @@ export function getMedicatedFood(id) {
 // 新增药膳食疗
 export function addMedicatedFood(data) {
   return request({
-    url: '/store/his/medicatedFood',
+    url: '/his/medicatedFood',
     method: 'post',
     data: data
   })
@@ -36,7 +36,7 @@ export function addMedicatedFood(data) {
 // 修改药膳食疗
 export function updateMedicatedFood(data) {
   return request({
-    url: '/store/his/medicatedFood',
+    url: '/his/medicatedFood',
     method: 'put',
     data: data
   })
@@ -45,7 +45,7 @@ export function updateMedicatedFood(data) {
 // 删除药膳食疗
 export function delMedicatedFood(id) {
   return request({
-    url: '/store/his/medicatedFood/' + id,
+    url: '/his/medicatedFood/' + id,
     method: 'delete'
   })
 }
@@ -53,7 +53,7 @@ export function delMedicatedFood(id) {
 // 导出药膳食疗
 export function exportMedicatedFood(query) {
   return request({
-    url: '/store/his/medicatedFood/export',
+    url: '/his/medicatedFood/export',
     method: 'get',
     params: query
   })

+ 9 - 9
src/api/hisStore/store.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询店铺管理列表
 export function listStore(query) {
   return request({
-    url: '/store/his/store/list',
+    url: '/his/store/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listStore(query) {
 // 查询店铺管理详细
 export function getStore(storeId) {
   return request({
-    url: '/store/his/store/' + storeId,
+    url: '/his/store/' + storeId,
     method: 'get'
   })
 }
@@ -21,7 +21,7 @@ export function getStore(storeId) {
 // 新增店铺管理
 export function addStore(data) {
   return request({
-    url: '/store/his/store',
+    url: '/his/store',
     method: 'post',
     data: data
   })
@@ -30,7 +30,7 @@ export function addStore(data) {
 // 修改店铺管理
 export function updateStore(data) {
   return request({
-    url: '/store/his/store',
+    url: '/his/store',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateStore(data) {
 // 修改店铺管理
 export function audit(data) {
   return request({
-    url: '/store/his/store/audit',
+    url: '/his/store/audit',
     method: 'put',
     data: data
   })
@@ -46,14 +46,14 @@ export function audit(data) {
 // 删除店铺管理
 export function delStore(storeId) {
   return request({
-    url: '/store/his/store/' + storeId,
+    url: '/his/store/' + storeId,
     method: 'delete'
   })
 }
 
 export function refreshPasWod(storeId) {
   return request({
-    url: '/store/his/store/refresh/'+ storeId,
+    url: '/his/store/refresh/'+ storeId,
     method: 'put'
   })
 }
@@ -61,7 +61,7 @@ export function refreshPasWod(storeId) {
 // 导出店铺管理
 export function exportStore(query) {
   return request({
-    url: '/store/his/store/export',
+    url: '/his/store/export',
     method: 'get',
     params: query
   })
@@ -70,7 +70,7 @@ export function exportStore(query) {
 //getStoreAuditLog
 export function getStoreAuditLog(storeId) {
   return request({
-    url: '/store/his/store/auditLog/'+ storeId,
+    url: '/his/store/auditLog/'+ storeId,
     method: 'get'
   })
 }

+ 6 - 6
src/api/hisStore/storeInstanDiscountIssue.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询已发布立减金券列表
 export function listHisstoreStoreinstandiscountissue(query) {
   return request({
-    url: '/his_store/store_instan_discount_issue/list',
+    url: '/store/store_instan_discount_issue/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listHisstoreStoreinstandiscountissue(query) {
 // 查询已发布立减金券详细
 export function getHisstoreStoreinstandiscountissue(id) {
   return request({
-    url: '/his_store/store_instan_discount_issue/' + id,
+    url: '/store/store_instan_discount_issue/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getHisstoreStoreinstandiscountissue(id) {
 // 新增已发布立减金券
 export function addHisstoreStoreinstandiscountissue(data) {
   return request({
-    url: '/his_store/store_instan_discount_issue',
+    url: '/store/store_instan_discount_issue',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addHisstoreStoreinstandiscountissue(data) {
 // 修改已发布立减金券
 export function updateHisstoreStoreinstandiscountissue(data) {
   return request({
-    url: '/his_store/store_instan_discount_issue',
+    url: '/store/store_instan_discount_issue',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateHisstoreStoreinstandiscountissue(data) {
 // 删除已发布立减金券
 export function delHisstoreStoreinstandiscountissue(id) {
   return request({
-    url: '/his_store/store_instan_discount_issue/' + id,
+    url: '/store/store_instan_discount_issue/' + id,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delHisstoreStoreinstandiscountissue(id) {
 // 导出已发布立减金券
 export function exportHisstoreStoreinstandiscountissue(query) {
   return request({
-    url: '/his_store/store_instan_discount_issue/export',
+    url: '/store/store_instan_discount_issue/export',
     method: 'post',
     params: query
   })

+ 6 - 6
src/api/hisStore/storeInstantDiscount.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询立减金劵制作列表
 export function listHisstoreStoreinstantdiscount(query) {
   return request({
-    url: '/his_store/store_instant_discount/list',
+    url: '/store/store_instant_discount/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listHisstoreStoreinstantdiscount(query) {
 // 查询立减金劵制作详细
 export function getHisstoreStoreinstantdiscount(id) {
   return request({
-    url: '/his_store/store_instant_discount/' + id,
+    url: '/store/store_instant_discount/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getHisstoreStoreinstantdiscount(id) {
 // 新增立减金劵制作
 export function addHisstoreStoreinstantdiscount(data) {
   return request({
-    url: '/his_store/store_instant_discount',
+    url: '/store/store_instant_discount',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addHisstoreStoreinstantdiscount(data) {
 // 修改立减金劵制作
 export function updateHisstoreStoreinstantdiscount(data) {
   return request({
-    url: '/his_store/store_instant_discount',
+    url: '/store/store_instant_discount',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateHisstoreStoreinstantdiscount(data) {
 // 删除立减金劵制作
 export function delHisstoreStoreinstantdiscount(id) {
   return request({
-    url: '/his_store/store_instant_discount/' + id,
+    url: '/store/store_instant_discount/' + id,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delHisstoreStoreinstantdiscount(id) {
 // 导出立减金劵制作
 export function exportHisstoreStoreinstantdiscount(query) {
   return request({
-    url: '/his_store/store_instant_discount/export',
+    url: '/store/store_instant_discount/export',
     method: 'post',
     params: query
   })

+ 6 - 6
src/api/hisStore/storeInstantDiscountUser.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询立减金购买记录列表
 export function listHisstoreStoreinstantdiscountuser(query) {
   return request({
-    url: '/his_store/store_instant_discount_user/list',
+    url: '/store/store_instant_discount_user/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listHisstoreStoreinstantdiscountuser(query) {
 // 查询立减金购买记录详细
 export function getHisstoreStoreinstantdiscountuser(id) {
   return request({
-    url: '/his_store/store_instant_discount_user/' + id,
+    url: '/store/store_instant_discount_user/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getHisstoreStoreinstantdiscountuser(id) {
 // 新增立减金购买记录
 export function addHisstoreStoreinstantdiscountuser(data) {
   return request({
-    url: '/his_store/store_instant_discount_user',
+    url: '/store/store_instant_discount_user',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addHisstoreStoreinstantdiscountuser(data) {
 // 修改立减金购买记录
 export function updateHisstoreStoreinstantdiscountuser(data) {
   return request({
-    url: '/his_store/store_instant_discount_user',
+    url: '/store/store_instant_discount_user',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateHisstoreStoreinstantdiscountuser(data) {
 // 删除立减金购买记录
 export function delHisstoreStoreinstantdiscountuser(id) {
   return request({
-    url: '/his_store/store_instant_discount_user/' + id,
+    url: '/store/store_instant_discount_user/' + id,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delHisstoreStoreinstantdiscountuser(id) {
 // 导出立减金购买记录
 export function exportHisstoreStoreinstantdiscountuser(query) {
   return request({
-    url: '/his_store/store_instant_discount_user/export',
+    url: '/store/store_instant_discount_user/export',
     method: 'post',
     params: query
   })

+ 6 - 6
src/api/hisStore/testReport.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询测试报告列表
 export function listTestReport(query) {
   return request({
-    url: '/store/his/testReport/list',
+    url: '/his/testReport/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listTestReport(query) {
 // 查询测试报告详细
 export function getTestReport(reportId) {
   return request({
-    url: '/store/his/testReport/' + reportId,
+    url: '/his/testReport/' + reportId,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getTestReport(reportId) {
 // 新增测试报告
 export function addTestReport(data) {
   return request({
-    url: '/store/his/testReport',
+    url: '/his/testReport',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addTestReport(data) {
 // 修改测试报告
 export function updateTestReport(data) {
   return request({
-    url: '/store/his/testReport',
+    url: '/his/testReport',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateTestReport(data) {
 // 删除测试报告
 export function delTestReport(reportId) {
   return request({
-    url: '/store/his/testReport/' + reportId,
+    url: '/his/testReport/' + reportId,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delTestReport(reportId) {
 // 导出测试报告
 export function exportTestReport(query) {
   return request({
-    url: '/store/his/testReport/export',
+    url: '/his/testReport/export',
     method: 'get',
     params: query
   })

+ 8 - 8
src/api/hisStore/testTemp.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询测一测模板列表
 export function listTestTemp(query) {
   return request({
-    url: '/store/his/testTemp/list',
+    url: '/his/testTemp/list',
     method: 'get',
     params: query
   })
@@ -12,19 +12,19 @@ export function listTestTemp(query) {
 // 查询测一测模板详细
 export function getTempType(tempId) {
   return request({
-    url: '/store/his/testTemp/getTempType/' + tempId,
+    url: '/his/testTemp/getTempType/' + tempId,
     method: 'get'
   })
 }
 export function getTestTemp(tempId) {
   return request({
-    url: '/store/his/testTemp/' + tempId,
+    url: '/his/testTemp/' + tempId,
     method: 'get'
   })
 }
 export function getAllTestTemp() {
   return request({
-    url: '/store/his/testTemp/allList',
+    url: '/his/testTemp/allList',
     method: 'get'
   })
 }
@@ -32,7 +32,7 @@ export function getAllTestTemp() {
 // 新增测一测模板
 export function addTestTemp(data) {
   return request({
-    url: '/store/his/testTemp',
+    url: '/his/testTemp',
     method: 'post',
     data: data
   })
@@ -41,7 +41,7 @@ export function addTestTemp(data) {
 // 修改测一测模板
 export function updateTestTemp(data) {
   return request({
-    url: '/store/his/testTemp',
+    url: '/his/testTemp',
     method: 'put',
     data: data
   })
@@ -50,7 +50,7 @@ export function updateTestTemp(data) {
 // 删除测一测模板
 export function delTestTemp(tempId) {
   return request({
-    url: '/store/his/testTemp/' + tempId,
+    url: '/his/testTemp/' + tempId,
     method: 'delete'
   })
 }
@@ -58,7 +58,7 @@ export function delTestTemp(tempId) {
 // 导出测一测模板
 export function exportTestTemp(query) {
   return request({
-    url: '/store/his/testTemp/export',
+    url: '/his/testTemp/export',
     method: 'get',
     params: query
   })

+ 6 - 6
src/api/hisStore/testTempItem.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询模板项目列表
 export function listTestTempItem(query) {
   return request({
-    url: '/store/his/testTempItem/list',
+    url: '/his/testTempItem/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listTestTempItem(query) {
 // 查询模板项目详细
 export function getTestTempItem(itemId) {
   return request({
-    url: '/store/his/testTempItem/' + itemId,
+    url: '/his/testTempItem/' + itemId,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getTestTempItem(itemId) {
 // 新增模板项目
 export function addTestTempItem(data) {
   return request({
-    url: '/store/his/testTempItem',
+    url: '/his/testTempItem',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addTestTempItem(data) {
 // 修改模板项目
 export function updateTestTempItem(data) {
   return request({
-    url: '/store/his/testTempItem',
+    url: '/his/testTempItem',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateTestTempItem(data) {
 // 删除模板项目
 export function delTestTempItem(itemId) {
   return request({
-    url: '/store/his/testTempItem/' + itemId,
+    url: '/his/testTempItem/' + itemId,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delTestTempItem(itemId) {
 // 导出模板项目
 export function exportTestTempItem(query) {
   return request({
-    url: '/store/his/testTempItem/export',
+    url: '/his/testTempItem/export',
     method: 'get',
     params: query
   })

+ 8 - 8
src/api/hisStore/vessel.js

@@ -3,14 +3,14 @@ import request from '@/utils/request'
 // 查询经络管理列表
 export function listVessel(query) {
   return request({
-    url: '/store/his/vessel/list',
+    url: '/his/vessel/list',
     method: 'get',
     params: query
   })
 }
 export function getAllList() {
   return request({
-    url: '/store/his/vessel/allList',
+    url: '/his/vessel/allList',
     method: 'get'
   })
 }
@@ -18,21 +18,21 @@ export function getAllList() {
 // 查询经络管理详细
 export function getVessel(id) {
   return request({
-    url: '/store/his/vessel/' + id,
+    url: '/his/vessel/' + id,
     method: 'get'
   })
 }
 // 下载导入模板
 export function importTemplate() {
   return request({
-    url: '/store/his/questions/importTemplate',
+    url: '/his/questions/importTemplate',
     method: 'get'
   })
 }
 // 新增经络管理
 export function addVessel(data) {
   return request({
-    url: '/store/his/vessel',
+    url: '/his/vessel',
     method: 'post',
     data: data
   })
@@ -41,7 +41,7 @@ export function addVessel(data) {
 // 修改经络管理
 export function updateVessel(data) {
   return request({
-    url: '/store/his/vessel',
+    url: '/his/vessel',
     method: 'put',
     data: data
   })
@@ -50,7 +50,7 @@ export function updateVessel(data) {
 // 删除经络管理
 export function delVessel(id) {
   return request({
-    url: '/store/his/vessel/' + id,
+    url: '/his/vessel/' + id,
     method: 'delete'
   })
 }
@@ -58,7 +58,7 @@ export function delVessel(id) {
 // 导出经络管理
 export function exportVessel(query) {
   return request({
-    url: '/store/his/vessel/export',
+    url: '/his/vessel/export',
     method: 'get',
     params: query
   })

+ 2 - 2
src/api/login.js

@@ -10,7 +10,7 @@ export function login(username, password, code, uuid,tenantCode) {
     tenantCode
   }
   return request({
-    url: '/login',
+    url: '/admin/login',
     method: 'post',
     data: data
   })
@@ -31,7 +31,7 @@ export function register(data) {
 // 获取用户详细信息
 export function getInfo() {
   return request({
-    url: '/getInfo',
+    url: '/admin/getInfo',
     method: 'get'
   })
 }

+ 1 - 1
src/api/menu.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 获取路由
 export const getRouters = () => {
   return request({
-    url: '/getRouters',
+    url: '/admin/getRouters',
     method: 'get'
   })
 }

+ 4 - 4
src/api/moduleUsage/moduleUsage.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询模块用量统计列表
 export function listApi(query) {
   return request({
-    url: '/moduleUsage/list',
+    url: '/stats/moduleUsage/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listApi(query) {
 // 查询模块用量统计详细
 export function getApi(id) {
   return request({
-    url: '/moduleUsage/' + id,
+    url: '/stats/moduleUsage/' + id,
     method: 'get'
   })
 }
@@ -38,7 +38,7 @@ export function updateApi(data) {
 // 删除模块用量统计
 export function delApi(id) {
   return request({
-    url: '/moduleUsage/' + id,
+    url: '/stats/moduleUsage/' + id,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delApi(id) {
 // 导出模块用量统计
 export function exportApi(query) {
   return request({
-    url: '/moduleUsage/export',
+    url: '/stats/moduleUsage/export',
     method: 'post',
     params: query
   })

+ 6 - 6
src/api/recharge/template.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询充值模板列表
 export function listRechargeTemplate(query) {
   return request({
-    url: '/recharge-templates/list',
+    url: '/store/recharge-templates/list',
     method: 'post',
     data: query
   })
@@ -12,7 +12,7 @@ export function listRechargeTemplate(query) {
 // 查询充值模板详细
 export function getRechargeTemplate(id) {
   return request({
-    url: '/recharge-templates/' + id,
+    url: '/store/recharge-templates/' + id,
     method: 'get'
   })
 }
@@ -29,7 +29,7 @@ export function addRechargeTemplate(data) {
 // 修改充值模板
 export function updateRechargeTemplate(data) {
   return request({
-    url: '/recharge-templates/' + data.id,
+    url: '/store/recharge-templates/' + data.id,
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateRechargeTemplate(data) {
 // 删除充值模板
 export function delRechargeTemplate(id) {
   return request({
-    url: '/recharge-templates/' + id,
+    url: '/store/recharge-templates/' + id,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delRechargeTemplate(id) {
 // 修改充值模板状态
 export function updateRechargeTemplateStatus(id, status) {
   return request({
-    url: '/recharge-templates/' + id + '/status',
+    url: '/store/recharge-templates/' + id + '/status',
     method: 'put',
     params: {
       status: status
@@ -62,7 +62,7 @@ export function updateRechargeTemplateStatus(id, status) {
  */
 export function getCouponList(query) {
   return request({
-    url: '/recharge-templates/getCouponList',
+    url: '/store/recharge-templates/getCouponList',
     method: 'get',
     params: query
   })

+ 5 - 5
src/api/saler/productInfo.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询商品列表
 export function listProductInfo(query) {
   return request({
-    url: '/saler/serviceGoods/listPage',
+    url: '/crm/saler/serviceGoods/listPage',
     method: 'post',
     data: query
   })
@@ -12,7 +12,7 @@ export function listProductInfo(query) {
 // 查询商品详细
 export function getProductInfo(id) {
   return request({
-    url: '/saler/serviceGoods/findById',
+    url: '/crm/saler/serviceGoods/findById',
     method: 'post',
     data: { id }
   })
@@ -21,7 +21,7 @@ export function getProductInfo(id) {
 // 新增商品
 export function addProductInfo(data) {
   return request({
-    url: '/saler/serviceGoods/save',
+    url: '/crm/saler/serviceGoods/save',
     method: 'post',
     data: data
   })
@@ -30,7 +30,7 @@ export function addProductInfo(data) {
 // 修改商品
 export function updateProductInfo(data) {
   return request({
-    url: '/saler/serviceGoods/updateById',
+    url: '/crm/saler/serviceGoods/updateById',
     method: 'post',
     data: data
   })
@@ -39,7 +39,7 @@ export function updateProductInfo(data) {
 // 删除商品
 export function delProductInfo(id) {
   return request({
-    url: '/saler/serviceGoods/deleteById',
+    url: '/crm/saler/serviceGoods/deleteById',
     method: 'post',
     data: { id }
   })

+ 1 - 1
src/api/store/collectionSchedule.js

@@ -44,7 +44,7 @@ export function endProcess(data) {
 }  // 终止用户信息采集进度
 export function stop(data) {
   return request({
-    url: '/hisStore/collection/stop',
+    url: '/store/store/collection/stop',
     method: 'put',
     data: data
   })

+ 5 - 5
src/api/storeOrderOfflineItem/store.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询列表
 export function listApi(query) {
   return request({
-    url: '/storeOrderOfflineItem/store/list',
+    url: '/store/storeOrderOfflineItem/store/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listApi(query) {
 // 查询详细
 export function getApi(id) {
   return request({
-    url: '/storeOrderOfflineItem/store/' + id,
+    url: '/store/storeOrderOfflineItem/store/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getApi(id) {
 // 新增
 export function addApi(data) {
   return request({
-    url: '/storeOrderOfflineItem/store',
+    url: '/store/storeOrderOfflineItem/store',
     method: 'post',
     data: data
   })
@@ -29,7 +29,7 @@ export function addApi(data) {
 // 修改
 export function updateApi(data) {
   return request({
-    url: '/storeOrderOfflineItem/store',
+    url: '/store/storeOrderOfflineItem/store',
     method: 'put',
     data: data
   })
@@ -38,7 +38,7 @@ export function updateApi(data) {
 // 删除
 export function delApi(id) {
   return request({
-    url: '/storeOrderOfflineItem/store/' + id,
+    url: '/store/storeOrderOfflineItem/store/' + id,
     method: 'delete'
   })
 }

+ 4 - 4
src/api/sysUser/sysUser.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询员工管理列表
 export function listApi(query) {
   return request({
-    url: '/sysUser/list',
+    url: '/system/sysUser/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listApi(query) {
 // 查询员工管理详细
 export function getApi(id) {
   return request({
-    url: '/sysUser/' + id,
+    url: '/system/sysUser/' + id,
     method: 'get'
   })
 }
@@ -38,7 +38,7 @@ export function updateApi(data) {
 // 删除员工管理
 export function delApi(id) {
   return request({
-    url: '/sysUser/' + id,
+    url: '/system/sysUser/' + id,
     method: 'delete'
   })
 }
@@ -46,7 +46,7 @@ export function delApi(id) {
 // 导出员工管理
 export function exportApi(query) {
   return request({
-    url: '/sysUser/export',
+    url: '/system/sysUser/export',
     method: 'post',
     params: query
   })

+ 9 - 9
src/api/todo/todoItems.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询待办事项列表
 export function listTodoItems(query) {
   return request({
-    url: '/todoItems/listPage',
+    url: '/system/todoItems/listPage',
     method: 'post',
     data: query
   })
@@ -12,7 +12,7 @@ export function listTodoItems(query) {
 // 查询待办事项详细
 export function getTodoItems(id) {
   return request({
-    url: '/todoItems/findById',
+    url: '/system/todoItems/findById',
     method: 'post',
     data: { id: id }
   })
@@ -21,7 +21,7 @@ export function getTodoItems(id) {
 // 新增待办事项
 export function addTodoItems(data) {
   return request({
-    url: '/todoItems/add',
+    url: '/system/todoItems/add',
     method: 'post',
     data: data
   })
@@ -30,7 +30,7 @@ export function addTodoItems(data) {
 // 修改待办事项
 export function updateTodoItems(data) {
   return request({
-    url: '/todoItems/updateById',
+    url: '/system/todoItems/updateById',
     method: 'post',
     data: data
   })
@@ -39,7 +39,7 @@ export function updateTodoItems(data) {
 // 更新待办事项状态
 export function updateTodoItemsStatus(id, status) {
   return request({
-    url: '/todoItems/updateStatusById',
+    url: '/system/todoItems/updateStatusById',
     method: 'post',
     data: { id: id, status: status }
   })
@@ -48,7 +48,7 @@ export function updateTodoItemsStatus(id, status) {
 // 删除待办事项
 export function delTodoItems(id) {
   return request({
-    url: '/todoItems/removeById',
+    url: '/system/todoItems/removeById',
     method: 'post',
     data: { id: id }
   })
@@ -57,7 +57,7 @@ export function delTodoItems(id) {
 // 分配执行者
 export function assignExecutor(data) {
   return request({
-    url: '/todoItems/assignExecutor',
+    url: '/system/todoItems/assignExecutor',
     method: 'post',
     data: data
   })
@@ -66,7 +66,7 @@ export function assignExecutor(data) {
 // 获取可分配的执行者列表
 export function getExecutorList() {
   return request({
-    url: '/todoItems/getExecutorList',
+    url: '/system/todoItems/getExecutorList',
     method: 'get'
   })
 }
@@ -74,7 +74,7 @@ export function getExecutorList() {
 // 获取执行人员列表(支持分页和公司名称搜索)
 export function getUserList(param) {
   return request({
-    url: '/todoItems/getUserList',
+    url: '/system/todoItems/getUserList',
     method: 'post',
     data: param
   })

+ 6 - 6
src/api/wx/sopUserLogsWx.js

@@ -3,7 +3,7 @@ import request from '@/utils/request'
 // 查询个微SOP营期列表
 export function listSopUserLogsWx(query) {
   return request({
-    url: '/wxSop/sopUserLogsWx/list',
+    url: '/qw/wxSop/sopUserLogsWx/list',
     method: 'get',
     params: query
   })
@@ -12,7 +12,7 @@ export function listSopUserLogsWx(query) {
 // 查询个微SOP营期详细
 export function getSopUserLogsWx(id) {
   return request({
-    url: '/wxSop/sopUserLogsWx/' + id,
+    url: '/qw/wxSop/sopUserLogsWx/' + id,
     method: 'get'
   })
 }
@@ -20,7 +20,7 @@ export function getSopUserLogsWx(id) {
 // 删除个微SOP营期
 export function delSopUserLogsWx(ids) {
   return request({
-    url: '/wxSop/sopUserLogsWx/' + ids,
+    url: '/qw/wxSop/sopUserLogsWx/' + ids,
     method: 'delete'
   })
 }
@@ -28,7 +28,7 @@ export function delSopUserLogsWx(ids) {
 // 导出个微SOP营期
 export function exportSopUserLogsWx(query) {
   return request({
-    url: '/wxSop/sopUserLogsWx/export',
+    url: '/qw/wxSop/sopUserLogsWx/export',
     method: 'get',
     params: query
   })
@@ -37,7 +37,7 @@ export function exportSopUserLogsWx(query) {
 // 批量修改个微SOP营期时间
 export function updateLogDate(data) {
   return request({
-    url: '/wxSop/sopUserLogsWx/updateLogDate',
+    url: '/qw/wxSop/sopUserLogsWx/updateLogDate',
     method: 'post',
     data: data
   })
@@ -46,7 +46,7 @@ export function updateLogDate(data) {
 // 查询个微SOP营期详情(客户列表)
 export function getSopUserLogsDetail(sopUserId, query) {
   return request({
-    url: '/wxSop/sopUserLogsWx/detail/' + sopUserId,
+    url: '/qw/wxSop/sopUserLogsWx/detail/' + sopUserId,
     method: 'get',
     params: query
   })

+ 53 - 0
src/components/InlineTenantSelector/index.vue

@@ -0,0 +1,53 @@
+<template>
+  <el-select
+    v-model="selectedId"
+    placeholder="选择租户"
+    clearable
+    filterable
+    size="small"
+    style="width: 160px"
+    @change="handleChange"
+  >
+    <el-option
+      v-for="item in tenantList"
+      :key="item.id"
+      :label="item.tenantName"
+      :value="item.id"
+    />
+  </el-select>
+</template>
+
+<script>
+import { tenantList } from '@/api/tenant/tenant'
+
+export default {
+  name: 'InlineTenantSelector',
+  data() {
+    return {
+      tenantList: [],
+      selectedId: null
+    }
+  },
+  created() {
+    // 从Vuex恢复上次选择
+    const saved = this.$store.getters.selectedCompanyId
+    if (saved) {
+      this.selectedId = saved
+    }
+    this.loadTenants()
+  },
+  methods: {
+    loadTenants() {
+      tenantList().then(response => {
+        this.tenantList = response.rows || response.data || []
+      }).catch(() => {
+        this.tenantList = []
+      })
+    },
+    handleChange(val) {
+      this.$store.dispatch('tenant/setCompanyId', val)
+      this.$emit('change', val)
+    }
+  }
+}
+</script>

+ 82 - 0
src/components/TenantSelect/index.vue

@@ -0,0 +1,82 @@
+<template>
+  <el-select
+    v-model="selectedId"
+    placeholder="请选择租户"
+    clearable
+    filterable
+    remote
+    reserve-keyword
+    :remote-method="remoteSearch"
+    :loading="loading"
+    size="small"
+    style="width: 220px"
+    @change="handleChange"
+  >
+    <el-option
+      v-for="item in tenantOptions"
+      :key="item.id"
+      :label="`[${item.tenantCode}] ${item.tenantName}`"
+      :value="item.id"
+    />
+  </el-select>
+</template>
+
+<script>
+import { tenantList } from '@/api/tenant/tenant'
+
+export default {
+  name: 'TenantSelect',
+  props: {
+    value: {
+      type: [Number, String],
+      default: null
+    }
+  },
+  data() {
+    return {
+      selectedId: this.value,
+      tenantOptions: [],
+      loading: false,
+      searchTimer: null
+    }
+  },
+  watch: {
+    value(val) {
+      this.selectedId = val
+    }
+  },
+  mounted() {
+    this.fetchList()
+  },
+  methods: {
+    handleChange(val) {
+      this.$emit('input', val)
+      this.$emit('change', val)
+    },
+    remoteSearch(query) {
+      if (this.searchTimer) clearTimeout(this.searchTimer)
+      this.searchTimer = setTimeout(() => {
+        this.fetchList(query)
+      }, 300)
+    },
+    fetchList(query) {
+      this.loading = true
+      const params = {}
+      if (query) {
+        params.tenantCode = query
+        params.tenantName = query
+      }
+      tenantList(params)
+        .then(res => {
+          this.tenantOptions = res.data || res.rows || []
+        })
+        .catch(() => {
+          this.tenantOptions = []
+        })
+        .finally(() => {
+          this.loading = false
+        })
+    }
+  }
+}
+</script>

+ 8 - 3
src/settings.js

@@ -2,7 +2,7 @@ module.exports = {
   /**
    * 侧边栏主题 深色主题theme-dark,浅色主题theme-light
    */
-  sideTheme: 'theme-dark',
+  sideTheme: 'theme-light',
 
   /**
    * 是否系统布局配置
@@ -22,18 +22,23 @@ module.exports = {
   /**
    * 是否固定头部
    */
-  fixedHeader: false,
+  fixedHeader: true,
 
   /**
    * 是否显示logo
    */
-  sidebarLogo: true,
+  sidebarLogo: false,
 
   /**
    * 是否显示动态标题
    */
   dynamicTitle: false,
 
+  /**
+   * 主题色(Indigo-600,参考 Token 管理端配色)
+   */
+  theme: '#4F46E5',
+
   /**
    * @type {string | array} 'production' | ['production', 'development']
    * @description Need show err logs component.

+ 163 - 0
src/views/admin/commissionRecord/index.vue

@@ -0,0 +1,163 @@
+<template>
+  <div class="app-container">
+    <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch" label-width="100px">
+      <el-form-item label="代理名称" prop="proxyName">
+        <el-input v-model="queryParams.proxyName" placeholder="请输入代理名称" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item label="租户名称" prop="tenantName">
+        <el-input v-model="queryParams.tenantName" placeholder="请输入租户名称" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item label="消费时间">
+        <el-date-picker
+          v-model="dateRange"
+          type="daterange"
+          range-separator="至"
+          start-placeholder="开始日期"
+          end-placeholder="结束日期"
+          value-format="yyyy-MM-dd"
+          size="small"
+          style="width:240px"
+        />
+      </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">导出</el-button>
+      </el-col>
+      <right-toolbar :showSearch.sync="showSearch" @queryTable="getList" />
+    </el-row>
+
+    <el-table border v-loading="loading" :data="recordList">
+      <el-table-column type="index" label="序号" width="55" align="center" />
+      <el-table-column label="代理ID" align="center" prop="proxyId" width="70" />
+      <el-table-column label="代理名称" align="center" prop="proxyName" width="120" />
+      <el-table-column label="租户ID" align="center" prop="tenantId" width="70" />
+      <el-table-column label="租户名称" align="center" prop="tenantName" min-width="120" />
+      <el-table-column label="消费金额" align="center" prop="amount" width="110">
+        <template slot-scope="scope">¥{{ scope.row.amount || '0.00' }}</template>
+      </el-table-column>
+      <el-table-column label="平台成本" align="center" prop="platformCost" width="100">
+        <template slot-scope="scope">
+          <span style="color:#909399">¥{{ scope.row.platformCost || '0.00' }}</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="租户售价" align="center" prop="tenantPrice" width="100">
+        <template slot-scope="scope">¥{{ scope.row.tenantPrice || '0.00' }}</template>
+      </el-table-column>
+      <el-table-column label="分佣比例" align="center" prop="proxyRatio" width="90">
+        <template slot-scope="scope">{{ scope.row.proxyRatio || 0 }}%</template>
+      </el-table-column>
+      <el-table-column label="分佣金额" align="center" prop="proxyProfit" width="110">
+        <template slot-scope="scope">
+          <span style="color:#E6A23C;font-weight:bold">¥{{ scope.row.proxyProfit || '0.00' }}</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="消费时间" align="center" prop="consumeTime" width="160" />
+      <el-table-column label="操作" align="center" width="80" fixed="right">
+        <template slot-scope="scope">
+          <el-button size="mini" type="text" icon="el-icon-view" @click="handleDetail(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="返佣记录详情" :visible.sync="detailVisible" width="550px" append-to-body>
+      <el-descriptions :column="2" border>
+        <el-descriptions-item label="代理ID">{{ detail.proxyId }}</el-descriptions-item>
+        <el-descriptions-item label="代理名称">{{ detail.proxyName }}</el-descriptions-item>
+        <el-descriptions-item label="租户ID">{{ detail.tenantId }}</el-descriptions-item>
+        <el-descriptions-item label="租户名称">{{ detail.tenantName }}</el-descriptions-item>
+        <el-descriptions-item label="消费金额">¥{{ detail.amount || '0.00' }}</el-descriptions-item>
+        <el-descriptions-item label="平台成本">¥{{ detail.platformCost || '0.00' }}</el-descriptions-item>
+        <el-descriptions-item label="租户售价">¥{{ detail.tenantPrice || '0.00' }}</el-descriptions-item>
+        <el-descriptions-item label="分佣比例">{{ detail.proxyRatio || 0 }}%</el-descriptions-item>
+        <el-descriptions-item label="分佣金额">
+          <span style="color:#E6A23C;font-weight:bold">¥{{ detail.proxyProfit || '0.00' }}</span>
+        </el-descriptions-item>
+        <el-descriptions-item label="计费模式">
+          <el-tag v-if="detail.billingMode === 'USAGE'" type="primary" size="small">按量</el-tag>
+          <el-tag v-else-if="detail.billingMode === 'SUBSCRIPTION'" type="success" size="small">套餐</el-tag>
+          <span v-else>{{ detail.billingMode || '-' }}</span>
+        </el-descriptions-item>
+        <el-descriptions-item label="消费时间">{{ detail.consumeTime }}</el-descriptions-item>
+        <el-descriptions-item label="消费类型" :span="2">{{ detail.eventType || '-' }}</el-descriptions-item>
+        <el-descriptions-item label="关联业务ID" :span="2">{{ detail.bizId || '-' }}</el-descriptions-item>
+      </el-descriptions>
+    </el-dialog>
+  </div>
+</template>
+
+<script>
+import { listCommissionRecords, getCommissionRecord } from '@/api/admin/commissionRecord'
+
+export default {
+  name: 'AdminCommissionRecord',
+  data() {
+    return {
+      loading: false,
+      exportLoading: false,
+      showSearch: true,
+      total: 0,
+      recordList: [],
+      dateRange: [],
+      queryParams: {
+        pageNum: 1,
+        pageSize: 10,
+        proxyName: null,
+        tenantName: null,
+        beginTime: null,
+        endTime: null
+      },
+      detailVisible: false,
+      detail: {}
+    }
+  },
+  created() {
+    this.getList()
+  },
+  methods: {
+    getList() {
+      this.loading = true
+      if (this.dateRange && this.dateRange.length === 2) {
+        this.queryParams.beginTime = this.dateRange[0]
+        this.queryParams.endTime = this.dateRange[1]
+      } else {
+        this.queryParams.beginTime = null
+        this.queryParams.endTime = null
+      }
+      listCommissionRecords(this.queryParams).then(res => {
+        this.recordList = res.rows || []
+        this.total = res.total || 0
+        this.loading = false
+      }).catch(() => { this.loading = false })
+    },
+    handleQuery() {
+      this.queryParams.pageNum = 1
+      this.getList()
+    },
+    resetQuery() {
+      this.dateRange = []
+      this.resetForm('queryForm')
+      this.handleQuery()
+    },
+    handleDetail(row) {
+      getCommissionRecord(row.id).then(res => {
+        this.detail = res.data || {}
+        this.detailVisible = true
+      })
+    },
+    handleExport() {
+      this.exportLoading = true
+      this.$message.info('导出功能开发中')
+      this.exportLoading = false
+    }
+  }
+}
+</script>

+ 181 - 0
src/views/admin/consumeRecord/index.vue

@@ -0,0 +1,181 @@
+<template>
+  <div class="app-container">
+    <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch" label-width="100px">
+      <el-form-item label="租户名称" prop="tenantName">
+        <el-input v-model="queryParams.tenantName" placeholder="请输入租户名称" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item label="消费类型" prop="eventType">
+        <el-select v-model="queryParams.eventType" placeholder="请选择消费类型" clearable size="small">
+          <el-option label="外呼通话" value="CALL" />
+          <el-option label="短信" value="SMS" />
+          <el-option label="AI模型" value="AI_MODEL" />
+          <el-option label="龙虾引擎" value="LOBSTER" />
+          <el-option label="企微服务" value="QW_SERVICE" />
+          <el-option label="个微服务" value="WX_SERVICE" />
+          <el-option label="直播" value="LIVE" />
+          <el-option label="课程" value="COURSE" />
+          <el-option label="商品" value="PRODUCT" />
+          <el-option label="其他" value="OTHER" />
+        </el-select>
+      </el-form-item>
+      <el-form-item label="消费时间">
+        <el-date-picker
+          v-model="dateRange"
+          type="daterange"
+          range-separator="至"
+          start-placeholder="开始日期"
+          end-placeholder="结束日期"
+          value-format="yyyy-MM-dd"
+          size="small"
+          style="width:240px"
+        />
+      </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">导出</el-button>
+      </el-col>
+      <right-toolbar :showSearch.sync="showSearch" @queryTable="getList" />
+    </el-row>
+
+    <el-table border v-loading="loading" :data="recordList">
+      <el-table-column type="index" label="序号" width="55" align="center" />
+      <el-table-column label="租户ID" align="center" prop="tenantId" width="80" />
+      <el-table-column label="租户名称" align="center" prop="tenantName" min-width="140" />
+      <el-table-column label="消费类型" align="center" prop="eventType" width="100">
+        <template slot-scope="scope">
+          <el-tag v-if="scope.row.eventType === 'CALL'" type="warning">外呼通话</el-tag>
+          <el-tag v-else-if="scope.row.eventType === 'SMS'" type="info">短信</el-tag>
+          <el-tag v-else-if="scope.row.eventType === 'AI_MODEL'">AI模型</el-tag>
+          <el-tag v-else-if="scope.row.eventType === 'LOBSTER'" type="success">龙虾引擎</el-tag>
+          <el-tag v-else-if="scope.row.eventType === 'QW_SERVICE'" type="danger">企微服务</el-tag>
+          <el-tag v-else-if="scope.row.eventType === 'WX_SERVICE'" type="danger">个微服务</el-tag>
+          <el-tag v-else-if="scope.row.eventType === 'LIVE'" type="warning">直播</el-tag>
+          <el-tag v-else-if="scope.row.eventType === 'COURSE'">课程</el-tag>
+          <el-tag v-else-if="scope.row.eventType === 'PRODUCT'">商品</el-tag>
+          <el-tag v-else>{{ scope.row.eventType || '其他' }}</el-tag>
+        </template>
+      </el-table-column>
+      <el-table-column label="消费金额" align="center" prop="amount" width="120">
+        <template slot-scope="scope">¥{{ scope.row.amount || '0.00' }}</template>
+      </el-table-column>
+      <el-table-column label="扣款后余额" align="center" prop="balanceAfter" width="120">
+        <template slot-scope="scope">¥{{ scope.row.balanceAfter || '0.00' }}</template>
+      </el-table-column>
+      <el-table-column label="计费模式" align="center" prop="billingMode" width="90">
+        <template slot-scope="scope">
+          <el-tag v-if="scope.row.billingMode === 'USAGE'" type="primary" size="small">按量</el-tag>
+          <el-tag v-else-if="scope.row.billingMode === 'SUBSCRIPTION'" type="success" size="small">套餐</el-tag>
+          <span v-else>{{ scope.row.billingMode || '-' }}</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="关联业务ID" align="center" prop="bizId" width="120" show-overflow-tooltip />
+      <el-table-column label="消费时间" align="center" prop="occurredAt" width="160" />
+      <el-table-column label="操作" align="center" width="80" fixed="right">
+        <template slot-scope="scope">
+          <el-button size="mini" type="text" icon="el-icon-view" @click="handleDetail(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="消费扣款详情" :visible.sync="detailVisible" width="550px" append-to-body>
+      <el-descriptions :column="2" border>
+        <el-descriptions-item label="租户ID">{{ detail.tenantId }}</el-descriptions-item>
+        <el-descriptions-item label="租户名称">{{ detail.tenantName }}</el-descriptions-item>
+        <el-descriptions-item label="消费类型">
+          <el-tag v-if="detail.eventType === 'CALL'" type="warning">外呼通话</el-tag>
+          <el-tag v-else-if="detail.eventType === 'SMS'" type="info">短信</el-tag>
+          <el-tag v-else-if="detail.eventType === 'AI_MODEL'">AI模型</el-tag>
+          <el-tag v-else-if="detail.eventType === 'LOBSTER'" type="success">龙虾引擎</el-tag>
+          <el-tag v-else>{{ detail.eventType || '-' }}</el-tag>
+        </el-descriptions-item>
+        <el-descriptions-item label="消费金额">¥{{ detail.amount || '0.00' }}</el-descriptions-item>
+        <el-descriptions-item label="扣款后余额">¥{{ detail.balanceAfter || '0.00' }}</el-descriptions-item>
+        <el-descriptions-item label="计费模式">
+          <el-tag v-if="detail.billingMode === 'USAGE'" type="primary" size="small">按量</el-tag>
+          <el-tag v-else-if="detail.billingMode === 'SUBSCRIPTION'" type="success" size="small">套餐</el-tag>
+          <span v-else>{{ detail.billingMode || '-' }}</span>
+        </el-descriptions-item>
+        <el-descriptions-item label="关联业务ID">{{ detail.bizId || '-' }}</el-descriptions-item>
+        <el-descriptions-item label="消费时间" :span="2">{{ detail.occurredAt }}</el-descriptions-item>
+        <el-descriptions-item label="备注" :span="2">{{ detail.remark || '-' }}</el-descriptions-item>
+      </el-descriptions>
+    </el-dialog>
+  </div>
+</template>
+
+<script>
+import { listConsumeRecords, getConsumeRecord } from '@/api/admin/consumeRecord'
+
+export default {
+  name: 'AdminConsumeRecord',
+  data() {
+    return {
+      loading: false,
+      exportLoading: false,
+      showSearch: true,
+      total: 0,
+      recordList: [],
+      dateRange: [],
+      queryParams: {
+        pageNum: 1,
+        pageSize: 10,
+        tenantName: null,
+        eventType: null,
+        beginTime: null,
+        endTime: null
+      },
+      detailVisible: false,
+      detail: {}
+    }
+  },
+  created() {
+    this.getList()
+  },
+  methods: {
+    getList() {
+      this.loading = true
+      if (this.dateRange && this.dateRange.length === 2) {
+        this.queryParams.beginTime = this.dateRange[0]
+        this.queryParams.endTime = this.dateRange[1]
+      } else {
+        this.queryParams.beginTime = null
+        this.queryParams.endTime = null
+      }
+      listConsumeRecords(this.queryParams).then(res => {
+        this.recordList = res.rows || []
+        this.total = res.total || 0
+        this.loading = false
+      }).catch(() => { this.loading = false })
+    },
+    handleQuery() {
+      this.queryParams.pageNum = 1
+      this.getList()
+    },
+    resetQuery() {
+      this.dateRange = []
+      this.resetForm('queryForm')
+      this.handleQuery()
+    },
+    handleDetail(row) {
+      getConsumeRecord(row.id).then(res => {
+        this.detail = res.data || {}
+        this.detailVisible = true
+      })
+    },
+    handleExport() {
+      this.exportLoading = true
+      this.$message.info('导出功能开发中')
+      this.exportLoading = false
+    }
+  }
+}
+</script>

+ 270 - 0
src/views/admin/dailyStatistics/index.vue

@@ -0,0 +1,270 @@
+<template>
+  <div class="app-container">
+    <el-card shadow="never" class="mb16 filter-card">
+      <el-form :inline="true" size="small">
+        <el-form-item label="选择代理">
+          <el-select v-model="selectedProxyId" placeholder="全部代理" clearable filterable @change="refreshAll" style="width:200px">
+            <el-option v-for="p in enabledProxyList" :key="p.proxyId" :label="p.proxyName" :value="p.proxyId" />
+          </el-select>
+        </el-form-item>
+        <el-form-item label="日期">
+          <el-date-picker v-model="statDate" type="date" value-format="yyyy-MM-dd" placeholder="请选择日期" @change="refreshAll" style="width:160px" />
+        </el-form-item>
+        <el-form-item>
+          <el-button type="primary" icon="el-icon-search" size="mini" @click="refreshAll">查询</el-button>
+          <el-button icon="el-icon-refresh" size="mini" @click="resetQuery">重置</el-button>
+        </el-form-item>
+      </el-form>
+    </el-card>
+
+    <!-- 概览卡片 -->
+    <el-row :gutter="16" class="mb16">
+      <el-col :span="6" v-for="card in overviewCards" :key="card.label">
+        <el-card shadow="hover" class="overview-card">
+          <div class="card-inner">
+            <div class="card-icon" :style="{ background: card.bg }"><i :class="card.icon"></i></div>
+            <div class="card-info">
+              <span class="card-value">{{ card.value }}</span>
+              <span class="card-label">{{ card.label }}</span>
+            </div>
+          </div>
+        </el-card>
+      </el-col>
+    </el-row>
+
+    <el-tabs v-model="activeTab" type="card" @tab-click="handleTabClick">
+      <!-- Tab 1:代理下租户消费 -->
+      <el-tab-pane label="租户消费明细" name="tenantConsume">
+        <el-table border v-loading="loading" :data="tenantStats" size="small" style="width:100%">
+          <el-table-column label="租户ID" prop="tenantId" width="80" align="center" />
+          <el-table-column label="租户名称" min-width="140">
+            <template slot-scope="s">{{ tenantNames[s.row.tenantId] || s.row.remark || '-' }}</template>
+          </el-table-column>
+          <el-table-column label="消费金额" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#1890ff;font-weight:bold">{{ fmt(s.row.consumeAmount) }}</span>
+            </template>
+          </el-table-column>
+          <el-table-column label="平台成本" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#fa8c16">{{ fmt(s.row.platformCost) }}</span>
+            </template>
+          </el-table-column>
+          <el-table-column label="租户售价" align="center" width="140">
+            <template slot-scope="s">{{ fmt(s.row.tenantPrice) }}</template>
+          </el-table-column>
+          <el-table-column label="利润(售价-成本)" align="center" width="150">
+            <template slot-scope="s">
+              <span style="color:#52c41a;font-weight:bold">
+                {{ fmt((s.row.tenantPrice || 0) - (s.row.platformCost || 0)) }}
+              </span>
+            </template>
+          </el-table-column>
+          <el-table-column label="代理分佣" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#722ed1;font-weight:bold">{{ fmt(s.row.proxyProfit) }}</span>
+            </template>
+          </el-table-column>
+          <el-table-column label="订单数" prop="orderCount" width="80" align="center" />
+        </el-table>
+        <el-empty v-if="!loading && tenantStats.length === 0" description="暂无数据" :image-size="80" />
+      </el-tab-pane>
+
+      <!-- Tab 2:服务类型利润 -->
+      <el-tab-pane label="服务类型利润" name="typeProfit">
+        <el-table border v-loading="loading" :data="typeStats" size="small" style="width:100%">
+          <el-table-column label="服务类型" min-width="160">
+            <template slot-scope="s">
+              <el-tag :type="typeTag(s.row.consumeType)">{{ typeName(s.row.consumeType) }}</el-tag>
+            </template>
+          </el-table-column>
+          <el-table-column label="消费金额" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#1890ff;font-weight:bold">{{ fmt(s.row.consumeAmount) }}</span>
+            </template>
+          </el-table-column>
+          <el-table-column label="平台成本" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#fa8c16">{{ fmt(s.row.platformCost) }}</span>
+            </template>
+          </el-table-column>
+          <el-table-column label="利润" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#52c41a;font-weight:bold">
+                {{ fmt((s.row.consumeAmount || 0) - (s.row.platformCost || 0)) }}
+              </span>
+            </template>
+          </el-table-column>
+          <el-table-column label="代理分佣" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#722ed1">{{ fmt(s.row.proxyProfit) }}</span>
+            </template>
+          </el-table-column>
+          <el-table-column label="平台收益" align="center" width="140">
+            <template slot-scope="s">
+              <b style="color:#333">
+                {{ fmt((s.row.tenantPrice || 0) - (s.row.platformCost || 0) - (s.row.proxyProfit || 0)) }}
+              </b>
+            </template>
+          </el-table-column>
+          <el-table-column label="订单数" prop="orderCount" width="80" align="center" />
+        </el-table>
+        <el-empty v-if="!loading && typeStats.length === 0" description="暂无数据" :image-size="80" />
+      </el-tab-pane>
+
+      <!-- Tab 3:代理汇总 -->
+      <el-tab-pane label="代理汇总" name="agentSummary">
+        <el-table border v-loading="loading" :data="agentStats" size="small" style="width:100%">
+          <el-table-column label="代理ID" prop="proxyId" width="80" align="center" />
+          <el-table-column label="代理名称" min-width="140">
+            <template slot-scope="s">{{ proxyNames[s.row.proxyId] || '-' }}</template>
+          </el-table-column>
+          <el-table-column label="消费金额" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#1890ff;font-weight:bold">{{ fmt(s.row.consumeAmount) }}</span>
+            </template>
+          </el-table-column>
+          <el-table-column label="平台成本" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#fa8c16">{{ fmt(s.row.platformCost) }}</span>
+            </template>
+          </el-table-column>
+          <el-table-column label="总利润" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#52c41a;font-weight:bold">
+                {{ fmt((s.row.tenantPrice || 0) - (s.row.platformCost || 0)) }}
+              </span>
+            </template>
+          </el-table-column>
+          <el-table-column label="代理分佣" align="center" width="140">
+            <template slot-scope="s">
+              <span style="color:#722ed1;font-weight:bold">{{ fmt(s.row.proxyProfit) }}</span>
+            </template>
+          </el-table-column>
+          <el-table-column label="订单数" prop="orderCount" width="80" align="center" />
+        </el-table>
+        <el-empty v-if="!loading && agentStats.length === 0" description="暂无数据" :image-size="80" />
+      </el-tab-pane>
+    </el-tabs>
+  </div>
+</template>
+
+<script>
+import { allEnabledProxies } from '@/api/admin/proxy'
+import { getDailyAgentTenants, getDailyServiceTypeProfit, getDailyAgentSummary } from '@/api/admin/dailyStatistics'
+
+const TYPE_MAP = {
+  'COURSE': '课程流量费', 'LIVE': '直播流量费', 'AI_TOKEN': 'AI TOKEN',
+  'SMS': '短信发送', 'MANUAL_CALL': '手拨外呼', 'AI_CALL': 'AI智能外呼',
+  'MICRO_ASSISTANT': '微助手', 'ACCOUNT_FEE': '账户费',
+  'AI_MODEL': 'AI模型训练'
+}
+const TYPE_TAGS = {
+  'COURSE': '', 'LIVE': 'warning', 'AI_TOKEN': 'info', 'SMS': 'info',
+  'MANUAL_CALL': 'warning', 'AI_CALL': 'warning', 'MICRO_ASSISTANT': 'success',
+  'ACCOUNT_FEE': 'danger', 'AI_MODEL': ''
+}
+
+export default {
+  name: 'AdminDailyStatistics',
+  data() {
+    return {
+      activeTab: 'tenantConsume',
+      selectedProxyId: null,
+      statDate: new Date().toISOString().slice(0, 10),
+      loading: false,
+      enabledProxyList: [],
+      // Cards
+      overviewCards: [
+        { label: '总消费', value: '¥0.00', icon: 'el-icon-wallet', bg: '#e6f7ff' },
+        { label: '平台成本', value: '¥0.00', icon: 'el-icon-coins', bg: '#fff7e6' },
+        { label: '总利润', value: '¥0.00', icon: 'el-icon-data-line', bg: '#f6ffed' },
+        { label: '代理分佣', value: '¥0.00', icon: 'el-icon-user-solid', bg: '#f9f0ff' }
+      ],
+      // Tab data
+      tenantStats: [],
+      tenantNames: {},
+      typeStats: [],
+      agentStats: [],
+      proxyNames: {}
+    }
+  },
+  created() {
+    this.loadProxies()
+    this.refreshAll()
+  },
+  methods: {
+    fmt(val) {
+      if (val === null || val === undefined) return '¥0.00'
+      return '¥' + Number(val).toFixed(2)
+    },
+    typeName(t) { return TYPE_MAP[t] || t || '-' },
+    typeTag(t) { return TYPE_TAGS[t] || '' },
+
+    loadProxies() {
+      allEnabledProxies().then(r => { this.enabledProxyList = r.data || [] })
+    },
+
+    resetQuery() {
+      this.selectedProxyId = null
+      this.statDate = new Date().toISOString().slice(0, 10)
+      this.refreshAll()
+    },
+
+    handleTabClick() { this.refreshAll() },
+
+    refreshAll() {
+      const params = { statDate: this.statDate }
+      if (this.selectedProxyId) params.proxyId = this.selectedProxyId
+
+      this.loadTenantConsume(params)
+      this.loadTypeProfit(params)
+      this.loadAgentSummary()
+    },
+
+    loadTenantConsume(params) {
+      this.tenantStats = []
+      getDailyAgentTenants(params).then(r => {
+        const d = r.data
+        this.tenantStats = d.items || []
+        this.tenantNames = d.tenantNames || {}
+        this.overviewCards[0].value = this.fmt(d.totalConsume)
+        this.overviewCards[1].value = this.fmt(d.totalCost)
+        this.overviewCards[2].value = this.fmt(d.totalProfit)
+        this.overviewCards[3].value = this.fmt(d.totalAgentProfit)
+      }).catch(() => { this.tenantStats = [] })
+    },
+
+    loadTypeProfit(params) {
+      this.typeStats = []
+      getDailyServiceTypeProfit(params).then(r => {
+        this.typeStats = r.data.items || []
+      }).catch(() => { this.typeStats = [] })
+    },
+
+    loadAgentSummary() {
+      this.agentStats = []
+      getDailyAgentSummary({ statDate: this.statDate }).then(r => {
+        const d = r.data
+        this.agentStats = d.items || []
+        this.proxyNames = d.proxyNames || {}
+      }).catch(() => { this.agentStats = [] })
+    }
+  }
+}
+</script>
+
+<style scoped>
+.filter-card { padding-bottom: 0; }
+.mb16 { margin-bottom: 16px; }
+
+.overview-card { cursor: default; }
+.card-inner { display: flex; align-items: center; }
+.card-icon {
+  width: 46px; height: 46px; border-radius: 50%;
+  display: flex; align-items: center; justify-content: center;
+  margin-right: 14px; font-size: 22px; color: #fff;
+}
+.card-value { font-size: 22px; font-weight: bold; color: #333; display: block; }
+.card-label { font-size: 12px; color: #999; }
+</style>

+ 86 - 0
src/views/admin/liveVideo/index.vue

@@ -0,0 +1,86 @@
+<template>
+  <div class="app-container">
+    <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch" label-width="100px">
+      <el-form-item label="租户名称" prop="companyName">
+        <el-input v-model="queryParams.companyName" placeholder="请输入租户名称" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item label="视频标题" prop="videoTitle">
+        <el-input v-model="queryParams.videoTitle" placeholder="请输入视频标题" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item>
+        <inline-tenant-selector @change="onTenantChange" />
+        <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-table v-loading="loading" :data="list">
+      <el-table-column label="租户名称" prop="companyName" width="160" />
+      <el-table-column label="视频标题" prop="title" :show-overflow-tooltip="true" />
+      <el-table-column label="直播ID" prop="liveId" width="120" />
+      <el-table-column label="播放地址" prop="playUrl" :show-overflow-tooltip="true" />
+      <el-table-column label="时长(秒)" prop="duration" width="100" />
+      <el-table-column label="状态" prop="status" width="80" align="center">
+        <template slot-scope="scope">
+          <el-tag :type="scope.row.status === 1 ? 'success' : 'info'" size="mini">
+            {{ scope.row.status === 1 ? '已生成' : '处理中' }}
+          </el-tag>
+        </template>
+      </el-table-column>
+      <el-table-column label="创建时间" prop="createTime" width="160" align="center" />
+    </el-table>
+
+    <pagination v-show="total > 0" :total="total" :page.sync="queryParams.pageNum" :limit.sync="queryParams.pageSize" @pagination="getList" />
+  </div>
+</template>
+
+<script>
+import { listAllLiveVideos } from '@/api/admin/liveVideo'
+import InlineTenantSelector from '@/components/InlineTenantSelector'
+
+export default {
+  name: 'AdminLiveVideo',
+  components: { InlineTenantSelector },
+  data() {
+    return {
+      loading: false,
+      showSearch: true,
+      list: [],
+      total: 0,
+      queryParams: {
+        pageNum: 1,
+        pageSize: 10,
+        companyName: null,
+        videoTitle: null,
+        companyId: null
+      }
+    }
+  },
+  created() {
+    this.getList()
+  },
+  methods: {
+    getList() {
+      this.loading = true
+      listAllLiveVideos(this.queryParams).then(res => {
+        this.list = res.rows
+        this.total = res.total
+        this.loading = false
+      }).catch(() => { this.loading = false })
+    },
+    handleQuery() {
+      this.queryParams.pageNum = 1
+      this.getList()
+    },
+    resetQuery() {
+      this.resetForm('queryForm')
+      this.queryParams.companyId = null
+      this.handleQuery()
+    },
+    onTenantChange(companyId) {
+      this.queryParams.companyId = companyId
+      this.handleQuery()
+    }
+  }
+}
+</script>

+ 103 - 0
src/views/admin/proxy/feeConfig.vue

@@ -0,0 +1,103 @@
+<template>
+  <div class="app-container">
+    <el-alert title="设置代理的分成比例,代理每日分佣 = 该代理下所有租户当日消费总额扣减平台成本后的总利润 × 代理分成比例" type="info" :closable="false" show-icon class="mb16" />
+
+    <el-row :gutter="10" class="mb8">
+      <el-col :span="1.5">
+        <el-button type="primary" icon="el-icon-edit" size="mini" @click="toggleEdit">
+          {{ editing ? '取消编辑' : '批量编辑' }}
+        </el-button>
+      </el-col>
+      <el-col :span="1.5" v-if="editing">
+        <el-button type="success" icon="el-icon-check" size="mini" @click="saveAll">保存全部</el-button>
+      </el-col>
+    </el-row>
+
+    <el-table border v-loading="loading" :data="proxyList" style="width:100%">
+      <el-table-column label="代理ID" prop="proxyId" width="80" align="center" />
+      <el-table-column label="代理名称" prop="proxyName" min-width="140" />
+      <el-table-column label="联系人" prop="contactName" width="100" />
+      <el-table-column label="联系电话" prop="contactMobile" width="130" />
+      <el-table-column label="余额" align="center" width="120">
+        <template slot-scope="s">
+          <span style="color:#1890ff;font-weight:bold">¥{{ (s.row.balance || 0).toFixed(2) }}</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="分成比例(%)" align="center" width="150">
+        <template slot-scope="s">
+          <el-input-number v-if="editing" v-model="s.row.profitShareRatio" :min="0" :max="100" :precision="2" size="small" style="width:100px" />
+          <span v-else style="color:#52c41a;font-weight:bold">{{ s.row.profitShareRatio || 0 }}%</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="发展客户数" align="center" width="100">
+        <template slot-scope="s">{{ s.row.tenantCount || 0 }}</template>
+      </el-table-column>
+      <el-table-column label="到期时间" align="center" prop="expireTime" width="120" />
+      <el-table-column label="状态" align="center" width="80">
+        <template slot-scope="s">
+          <el-tag v-if="s.row.status === 1" type="success" size="small">启用</el-tag>
+          <el-tag v-else type="danger" size="small">禁用</el-tag>
+        </template>
+      </el-table-column>
+      <el-table-column label="操作" width="100" align="center" v-if="editing">
+        <template slot-scope="s">
+          <el-button size="mini" type="text" icon="el-icon-check" @click="saveOne(s.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="loadList" />
+  </div>
+</template>
+
+<script>
+import { listProxy, updateProxy } from '@/api/admin/proxy'
+
+export default {
+  name: 'AdminProxyFeeConfig',
+  data() {
+    return {
+      loading: false,
+      editing: false,
+      proxyList: [],
+      total: 0,
+      queryParams: { pageNum: 1, pageSize: 20 }
+    }
+  },
+  created() {
+    this.loadList()
+  },
+  methods: {
+    toggleEdit() { this.editing = !this.editing },
+    loadList() {
+      this.loading = true
+      listProxy(this.queryParams).then(res => {
+        this.proxyList = res.rows || []
+        this.total = res.total || 0
+        this.loading = false
+      }).catch(() => { this.loading = false })
+    },
+    saveOne(row) {
+      updateProxy({ proxyId: row.proxyId, profitShareRatio: row.profitShareRatio }).then(() => {
+        this.$message.success(`${row.proxyName} 分成比例更新成功`)
+      })
+    },
+    saveAll() {
+      let count = 0
+      const promises = this.proxyList
+        .filter(p => p.proxyId)
+        .map(p => updateProxy({ proxyId: p.proxyId, profitShareRatio: p.profitShareRatio }).then(() => count++))
+      Promise.all(promises).then(() => {
+        this.$message.success(`批量保存成功,共更新 ${count} 个代理`)
+        this.editing = false
+        this.loadList()
+      })
+    }
+  }
+}
+</script>
+
+<style scoped>
+.mb16 { margin-bottom: 16px; }
+.mb8 { margin-bottom: 8px; }
+</style>

+ 160 - 0
src/views/admin/rechargeRecord/index.vue

@@ -0,0 +1,160 @@
+<template>
+  <div class="app-container">
+    <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch" label-width="100px">
+      <el-form-item label="租户名称" prop="tenantName">
+        <el-input v-model="queryParams.tenantName" placeholder="请输入租户名称" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item label="操作人" prop="createBy">
+        <el-input v-model="queryParams.createBy" placeholder="请输入操作人" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item label="充值时间">
+        <el-date-picker
+          v-model="dateRange"
+          type="daterange"
+          range-separator="至"
+          start-placeholder="开始日期"
+          end-placeholder="结束日期"
+          value-format="yyyy-MM-dd"
+          size="small"
+          style="width:240px"
+        />
+      </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">导出</el-button>
+      </el-col>
+      <right-toolbar :showSearch.sync="showSearch" @queryTable="getList" />
+    </el-row>
+
+    <el-table border v-loading="loading" :data="recordList">
+      <el-table-column type="index" label="序号" width="55" align="center" />
+      <el-table-column label="租户ID" align="center" prop="tenantId" width="80" />
+      <el-table-column label="租户名称" align="center" prop="tenantName" min-width="140" />
+      <el-table-column label="充值金额" align="center" prop="amount" width="120">
+        <template slot-scope="scope">
+          <span style="color:#67C23A;font-weight:bold">+¥{{ scope.row.amount || '0.00' }}</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="充值后余额" align="center" prop="balanceAfter" width="130">
+        <template slot-scope="scope">¥{{ scope.row.balanceAfter || '0.00' }}</template>
+      </el-table-column>
+      <el-table-column label="充值方式" align="center" prop="payMethod" width="100">
+        <template slot-scope="scope">
+          <el-tag v-if="scope.row.payMethod === 'ADMIN'" type="warning" size="small">后台充值</el-tag>
+          <el-tag v-else-if="scope.row.payMethod === 'ALIPAY'" type="primary" size="small">支付宝</el-tag>
+          <el-tag v-else-if="scope.row.payMethod === 'WECHAT'" type="success" size="small">微信支付</el-tag>
+          <el-tag v-else-if="scope.row.payMethod === 'BANK'" size="small">银行转账</el-tag>
+          <span v-else>{{ scope.row.payMethod || '-' }}</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="操作人" align="center" prop="createBy" width="120" />
+      <el-table-column label="充值时间" align="center" prop="createTime" width="160" />
+      <el-table-column label="备注" align="center" prop="remark" min-width="150" show-overflow-tooltip />
+      <el-table-column label="操作" align="center" width="80" fixed="right">
+        <template slot-scope="scope">
+          <el-button size="mini" type="text" icon="el-icon-view" @click="handleDetail(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="充值记录详情" :visible.sync="detailVisible" width="500px" append-to-body>
+      <el-descriptions :column="2" border>
+        <el-descriptions-item label="租户ID">{{ detail.tenantId }}</el-descriptions-item>
+        <el-descriptions-item label="租户名称">{{ detail.tenantName }}</el-descriptions-item>
+        <el-descriptions-item label="充值金额">
+          <span style="color:#67C23A;font-weight:bold">+¥{{ detail.amount || '0.00' }}</span>
+        </el-descriptions-item>
+        <el-descriptions-item label="充值后余额">¥{{ detail.balanceAfter || '0.00' }}</el-descriptions-item>
+        <el-descriptions-item label="充值前余额">¥{{ detail.balanceBefore || '0.00' }}</el-descriptions-item>
+        <el-descriptions-item label="充值方式">
+          <el-tag v-if="detail.payMethod === 'ADMIN'" type="warning" size="small">后台充值</el-tag>
+          <el-tag v-else-if="detail.payMethod === 'ALIPAY'" type="primary" size="small">支付宝</el-tag>
+          <el-tag v-else-if="detail.payMethod === 'WECHAT'" type="success" size="small">微信支付</el-tag>
+          <el-tag v-else-if="detail.payMethod === 'BANK'" size="small">银行转账</el-tag>
+          <span v-else>{{ detail.payMethod || '-' }}</span>
+        </el-descriptions-item>
+        <el-descriptions-item label="操作人">{{ detail.createBy || '-' }}</el-descriptions-item>
+        <el-descriptions-item label="充值时间">{{ detail.createTime }}</el-descriptions-item>
+        <el-descriptions-item label="交易流水号" :span="2">{{ detail.txnNo || '-' }}</el-descriptions-item>
+        <el-descriptions-item label="备注" :span="2">{{ detail.remark || '-' }}</el-descriptions-item>
+      </el-descriptions>
+    </el-dialog>
+  </div>
+</template>
+
+<script>
+import { listRechargeRecords, getRechargeRecord } from '@/api/admin/rechargeRecord'
+
+export default {
+  name: 'AdminRechargeRecord',
+  data() {
+    return {
+      loading: false,
+      exportLoading: false,
+      showSearch: true,
+      total: 0,
+      recordList: [],
+      dateRange: [],
+      queryParams: {
+        pageNum: 1,
+        pageSize: 10,
+        tenantName: null,
+        createBy: null,
+        beginTime: null,
+        endTime: null
+      },
+      detailVisible: false,
+      detail: {}
+    }
+  },
+  created() {
+    this.getList()
+  },
+  methods: {
+    getList() {
+      this.loading = true
+      if (this.dateRange && this.dateRange.length === 2) {
+        this.queryParams.beginTime = this.dateRange[0]
+        this.queryParams.endTime = this.dateRange[1]
+      } else {
+        this.queryParams.beginTime = null
+        this.queryParams.endTime = null
+      }
+      listRechargeRecords(this.queryParams).then(res => {
+        this.recordList = res.rows || []
+        this.total = res.total || 0
+        this.loading = false
+      }).catch(() => { this.loading = false })
+    },
+    handleQuery() {
+      this.queryParams.pageNum = 1
+      this.getList()
+    },
+    resetQuery() {
+      this.dateRange = []
+      this.resetForm('queryForm')
+      this.handleQuery()
+    },
+    handleDetail(row) {
+      getRechargeRecord(row.id).then(res => {
+        this.detail = res.data || {}
+        this.detailVisible = true
+      })
+    },
+    handleExport() {
+      this.exportLoading = true
+      this.$message.info('导出功能开发中')
+      this.exportLoading = false
+    }
+  }
+}
+</script>

+ 106 - 0
src/views/admin/serviceCost/index.vue

@@ -0,0 +1,106 @@
+<template>
+  <div class="app-container">
+    <el-alert title="设置各服务类型的平台成本价,代理分佣按每日总利润(租户消费 - 平台成本)× 分成比例计算" type="info" :closable="false" show-icon class="mb16" />
+
+    <el-row :gutter="10" class="mb8">
+      <el-col :span="1.5">
+        <el-button type="primary" icon="el-icon-edit" size="mini" @click="editing = !editing">
+          {{ editing ? '取消编辑' : '编辑模式' }}
+        </el-button>
+      </el-col>
+      <el-col :span="1.5" v-if="editing">
+        <el-button type="success" icon="el-icon-check" size="mini" @click="submitAll">批量保存</el-button>
+      </el-col>
+    </el-row>
+
+    <el-table border v-loading="loading" :data="costList" style="width:100%">
+      <el-table-column label="服务类型ID" prop="serviceType" width="100" align="center" />
+      <el-table-column label="服务类型" prop="configName" min-width="140" />
+      <el-table-column label="收费单位" prop="feeUnit" width="120" align="center" />
+      <el-table-column label="租户售价(元)" align="center" width="160">
+        <template slot-scope="s">
+          <el-input-number v-if="editing" v-model="s.row.feeStandard" :min="0" :precision="4" size="small" controls-position="right" style="width:130px" />
+          <span v-else>¥{{ s.row.feeStandard || '0' }}</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="平台成本价(元)" align="center" width="160">
+        <template slot-scope="s">
+          <el-input-number v-if="editing" v-model="s.row.platformCost" :min="0" :precision="4" size="small" controls-position="right" style="width:130px" />
+          <span v-else style="color:#fa8c16;font-weight:bold">¥{{ s.row.platformCost || '0' }}</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="预计利润(售价-成本)" align="center" width="160">
+        <template slot-scope="s">
+          <span style="color:#52c41a;font-weight:bold">
+            ¥{{ ((s.row.feeStandard || 0) - (s.row.platformCost || 0)).toFixed(4) }}
+          </span>
+        </template>
+      </el-table-column>
+      <el-table-column label="描述" prop="description" min-width="150" show-overflow-tooltip />
+      <el-table-column label="状态" width="80" align="center">
+        <template slot-scope="s">
+          <el-tag v-if="s.row.enabled === 1" type="success" size="small">启用</el-tag>
+          <el-tag v-else type="info" size="small">禁用</el-tag>
+        </template>
+      </el-table-column>
+      <el-table-column label="操作" width="100" align="center" v-if="editing">
+        <template slot-scope="s">
+          <el-button size="mini" type="text" icon="el-icon-check" @click="submitOne(s.row)">保存</el-button>
+          <el-button size="mini" type="text" icon="el-icon-switch-button" @click="toggleEnabled(s.row)">
+            {{ s.row.enabled === 1 ? '禁用' : '启用' }}
+          </el-button>
+        </template>
+      </el-table-column>
+    </el-table>
+  </div>
+</template>
+
+<script>
+import { listServiceCost, updateServiceCost } from '@/api/admin/serviceCost'
+
+export default {
+  name: 'AdminServiceCost',
+  data() {
+    return {
+      loading: false,
+      editing: false,
+      costList: []
+    }
+  },
+  created() {
+    this.loadList()
+  },
+  methods: {
+    loadList() {
+      this.loading = true
+      listServiceCost().then(res => {
+        this.costList = res.data || []
+        this.loading = false
+      }).catch(() => { this.loading = false })
+    },
+    submitOne(row) {
+      updateServiceCost(row).then(() => {
+        this.$message.success(`${row.configName} 更新成功`)
+      })
+    },
+    submitAll() {
+      let count = 0
+      const promises = this.costList.map(row => updateServiceCost(row).then(() => count++))
+      Promise.all(promises).then(() => {
+        this.$message.success(`批量保存成功,共更新 ${count} 条`)
+        this.editing = false
+        this.loadList()
+      })
+    },
+    toggleEnabled(row) {
+      row.enabled = row.enabled === 1 ? 0 : 1
+      this.submitOne(row)
+    }
+  }
+}
+</script>
+
+<style scoped>
+.mb16 { margin-bottom: 16px; }
+.mb8 { margin-bottom: 8px; }
+</style>

+ 86 - 0
src/views/admin/videoResource/index.vue

@@ -0,0 +1,86 @@
+<template>
+  <div class="app-container">
+    <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch" label-width="100px">
+      <el-form-item label="租户名称" prop="companyName">
+        <el-input v-model="queryParams.companyName" placeholder="请输入租户名称" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item label="视频名称" prop="videoName">
+        <el-input v-model="queryParams.videoName" placeholder="请输入视频名称" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item>
+        <inline-tenant-selector @change="onTenantChange" />
+        <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-table v-loading="loading" :data="list">
+      <el-table-column label="租户名称" prop="companyName" width="160" />
+      <el-table-column label="视频名称" prop="videoName" :show-overflow-tooltip="true" />
+      <el-table-column label="视频类型" prop="videoType" width="100" />
+      <el-table-column label="播放地址" prop="playUrl" :show-overflow-tooltip="true" />
+      <el-table-column label="时长(秒)" prop="duration" width="100" />
+      <el-table-column label="状态" prop="status" width="80" align="center">
+        <template slot-scope="scope">
+          <el-tag :type="scope.row.status === 1 ? 'success' : 'info'" size="mini">
+            {{ scope.row.status === 1 ? '正常' : '禁用' }}
+          </el-tag>
+        </template>
+      </el-table-column>
+      <el-table-column label="创建时间" prop="createTime" width="160" align="center" />
+    </el-table>
+
+    <pagination v-show="total > 0" :total="total" :page.sync="queryParams.pageNum" :limit.sync="queryParams.pageSize" @pagination="getList" />
+  </div>
+</template>
+
+<script>
+import { listAllVideoResources } from '@/api/admin/videoResource'
+import InlineTenantSelector from '@/components/InlineTenantSelector'
+
+export default {
+  name: 'AdminVideoResource',
+  components: { InlineTenantSelector },
+  data() {
+    return {
+      loading: false,
+      showSearch: true,
+      list: [],
+      total: 0,
+      queryParams: {
+        pageNum: 1,
+        pageSize: 10,
+        companyName: null,
+        videoName: null,
+        companyId: null
+      }
+    }
+  },
+  created() {
+    this.getList()
+  },
+  methods: {
+    getList() {
+      this.loading = true
+      listAllVideoResources(this.queryParams).then(res => {
+        this.list = res.rows
+        this.total = res.total
+        this.loading = false
+      }).catch(() => { this.loading = false })
+    },
+    handleQuery() {
+      this.queryParams.pageNum = 1
+      this.getList()
+    },
+    resetQuery() {
+      this.resetForm('queryForm')
+      this.queryParams.companyId = null
+      this.handleQuery()
+    },
+    onTenantChange(companyId) {
+      this.queryParams.companyId = companyId
+      this.handleQuery()
+    }
+  }
+}
+</script>

+ 220 - 0
src/views/admin/withdrawalManage/index.vue

@@ -0,0 +1,220 @@
+<template>
+  <div class="app-container">
+    <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch" label-width="100px">
+      <el-form-item label="代理名称" prop="proxyName">
+        <el-input v-model="queryParams.proxyName" placeholder="请输入代理名称" clearable size="small" @keyup.enter.native="handleQuery" />
+      </el-form-item>
+      <el-form-item label="状态" prop="status">
+        <el-select v-model="queryParams.status" placeholder="请选择状态" clearable size="small">
+          <el-option label="待审核" :value="0" />
+          <el-option label="已通过" :value="1" />
+          <el-option label="已拒绝" :value="2" />
+          <el-option label="已打款" :value="3" />
+        </el-select>
+      </el-form-item>
+      <el-form-item label="申请时间">
+        <el-date-picker
+          v-model="dateRange"
+          type="daterange"
+          range-separator="至"
+          start-placeholder="开始日期"
+          end-placeholder="结束日期"
+          value-format="yyyy-MM-dd"
+          size="small"
+          style="width:240px"
+        />
+      </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">导出</el-button>
+      </el-col>
+      <right-toolbar :showSearch.sync="showSearch" @queryTable="getList" />
+    </el-row>
+
+    <el-table border v-loading="loading" :data="recordList">
+      <el-table-column type="index" label="序号" width="55" align="center" />
+      <el-table-column label="代理ID" align="center" prop="proxyId" width="70" />
+      <el-table-column label="代理名称" align="center" prop="proxyName" min-width="120" />
+      <el-table-column label="可提现金额" align="center" prop="availableAmount" width="120">
+        <template slot-scope="scope">¥{{ scope.row.availableAmount || scope.row.balance || '0.00' }}</template>
+      </el-table-column>
+      <el-table-column label="申请金额" align="center" prop="withdrawAmount" width="120">
+        <template slot-scope="scope">
+          <span style="color:#E6A23C;font-weight:bold">¥{{ scope.row.withdrawAmount || '0.00' }}</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="状态" align="center" prop="status" width="90">
+        <template slot-scope="scope">
+          <el-tag v-if="scope.row.status === 0" type="warning">待审核</el-tag>
+          <el-tag v-else-if="scope.row.status === 1" type="success">已通过</el-tag>
+          <el-tag v-else-if="scope.row.status === 2" type="danger">已拒绝</el-tag>
+          <el-tag v-else-if="scope.row.status === 3" type="primary">已打款</el-tag>
+          <el-tag v-else type="info">{{ scope.row.status }}</el-tag>
+        </template>
+      </el-table-column>
+      <el-table-column label="银行名称" align="center" prop="bankName" width="140" show-overflow-tooltip />
+      <el-table-column label="银行账号" align="center" prop="bankAccount" width="160" show-overflow-tooltip />
+      <el-table-column label="申请时间" align="center" prop="createTime" width="160" />
+      <el-table-column label="审核时间" align="center" prop="auditTime" width="160" />
+      <el-table-column label="审核人" align="center" prop="auditorName" width="100" />
+      <el-table-column label="操作" align="center" width="200" fixed="right">
+        <template slot-scope="scope">
+          <el-button v-if="scope.row.status === 0" size="mini" type="success" @click="handleApprove(scope.row)">通过</el-button>
+          <el-button v-if="scope.row.status === 0" size="mini" type="danger" @click="handleReject(scope.row)">拒绝</el-button>
+          <el-button v-if="scope.row.status === 1" size="mini" type="primary" @click="handlePaid(scope.row)">确认打款</el-button>
+          <el-button size="mini" type="text" icon="el-icon-view" @click="handleDetail(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="拒绝提现申请" :visible.sync="rejectVisible" width="450px" append-to-body>
+      <el-form ref="rejectForm" :model="rejectForm" :rules="rejectRules" label-width="100px">
+        <el-form-item label="拒绝原因" prop="reason">
+          <el-input v-model="rejectForm.reason" type="textarea" :rows="3" placeholder="请输入拒绝原因" />
+        </el-form-item>
+      </el-form>
+      <div slot="footer">
+        <el-button @click="rejectVisible = false">取 消</el-button>
+        <el-button type="danger" @click="submitReject">确 定</el-button>
+      </div>
+    </el-dialog>
+
+    <!-- 详情弹窗 -->
+    <el-dialog title="提现申请详情" :visible.sync="detailVisible" width="550px" append-to-body>
+      <el-descriptions :column="2" border>
+        <el-descriptions-item label="代理ID">{{ detail.proxyId }}</el-descriptions-item>
+        <el-descriptions-item label="代理名称">{{ detail.proxyName }}</el-descriptions-item>
+        <el-descriptions-item label="可提现金额">¥{{ detail.availableAmount || detail.balance || '0.00' }}</el-descriptions-item>
+        <el-descriptions-item label="申请金额">¥{{ detail.withdrawAmount || '0.00' }}</el-descriptions-item>
+        <el-descriptions-item label="状态">
+          <el-tag v-if="detail.status === 0" type="warning">待审核</el-tag>
+          <el-tag v-else-if="detail.status === 1" type="success">已通过</el-tag>
+          <el-tag v-else-if="detail.status === 2" type="danger">已拒绝</el-tag>
+          <el-tag v-else-if="detail.status === 3" type="primary">已打款</el-tag>
+        </el-descriptions-item>
+        <el-descriptions-item label="银行名称">{{ detail.bankName || '-' }}</el-descriptions-item>
+        <el-descriptions-item label="银行账号">{{ detail.bankAccount || '-' }}</el-descriptions-item>
+        <el-descriptions-item label="申请时间">{{ detail.createTime }}</el-descriptions-item>
+        <el-descriptions-item label="审核时间">{{ detail.auditTime || '-' }}</el-descriptions-item>
+        <el-descriptions-item label="审核人">{{ detail.auditorName || '-' }}</el-descriptions-item>
+        <el-descriptions-item label="拒绝原因" :span="2">{{ detail.failReason || '-' }}</el-descriptions-item>
+        <el-descriptions-item label="备注" :span="2">{{ detail.remark || '-' }}</el-descriptions-item>
+      </el-descriptions>
+    </el-dialog>
+  </div>
+</template>
+
+<script>
+import { listWithdrawals, getWithdrawal, approveWithdrawal, rejectWithdrawal, confirmPaid } from '@/api/admin/withdrawalManage'
+
+export default {
+  name: 'AdminWithdrawal',
+  data() {
+    return {
+      loading: false,
+      exportLoading: false,
+      showSearch: true,
+      total: 0,
+      recordList: [],
+      dateRange: [],
+      rejectVisible: false,
+      currentRejectId: null,
+      rejectForm: { reason: '' },
+      rejectRules: {
+        reason: [{ required: true, message: '请输入拒绝原因', trigger: 'blur' }]
+      },
+      queryParams: {
+        pageNum: 1,
+        pageSize: 10,
+        proxyName: null,
+        status: null,
+        beginTime: null,
+        endTime: null
+      },
+      detailVisible: false,
+      detail: {}
+    }
+  },
+  created() {
+    this.getList()
+  },
+  methods: {
+    getList() {
+      this.loading = true
+      if (this.dateRange && this.dateRange.length === 2) {
+        this.queryParams.beginTime = this.dateRange[0]
+        this.queryParams.endTime = this.dateRange[1]
+      } else {
+        this.queryParams.beginTime = null
+        this.queryParams.endTime = null
+      }
+      listWithdrawals(this.queryParams).then(res => {
+        this.recordList = res.rows || []
+        this.total = res.total || 0
+        this.loading = false
+      }).catch(() => { this.loading = false })
+    },
+    handleQuery() {
+      this.queryParams.pageNum = 1
+      this.getList()
+    },
+    resetQuery() {
+      this.dateRange = []
+      this.resetForm('queryForm')
+      this.handleQuery()
+    },
+    handleApprove(row) {
+      this.$confirm(`确认通过代理 "${row.proxyName}" 的提现申请 (¥${row.withdrawAmount})?`, '审核通过', { type: 'warning' }).then(() => {
+        approveWithdrawal(row.id).then(() => {
+          this.$message.success('审核通过')
+          this.getList()
+        })
+      })
+    },
+    handleReject(row) {
+      this.currentRejectId = row.id
+      this.rejectForm.reason = ''
+      this.rejectVisible = true
+      this.$nextTick(() => { this.$refs.rejectForm && this.$refs.rejectForm.resetFields() })
+    },
+    submitReject() {
+      this.$refs['rejectForm'].validate(valid => {
+        if (!valid) return
+        rejectWithdrawal(this.currentRejectId, this.rejectForm.reason).then(() => {
+          this.$message.success('已拒绝')
+          this.rejectVisible = false
+          this.getList()
+        })
+      })
+    },
+    handlePaid(row) {
+      this.$confirm(`确认已向代理 "${row.proxyName}" 打款 ¥${row.withdrawAmount}?`, '确认打款', { type: 'warning' }).then(() => {
+        confirmPaid(row.id).then(() => {
+          this.$message.success('已确认打款')
+          this.getList()
+        })
+      })
+    },
+    handleDetail(row) {
+      getWithdrawal(row.id).then(res => {
+        this.detail = res.data || {}
+        this.detailVisible = true
+      })
+    },
+    handleExport() {
+      this.exportLoading = true
+      this.$message.info('导出功能开发中')
+      this.exportLoading = false
+    }
+  }
+}
+</script>

+ 57 - 0
src/views/customer/customerList.vue

@@ -0,0 +1,57 @@
+<template>
+  <div class="app-container">
+    <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch">
+      <el-form-item label="关键字" prop="keyword">
+        <el-input v-model="queryParams.keyword" placeholder="请输入关键字" clearable size="small" @keyup.enter.native="handleQuery"/>
+      </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-table v-loading="loading" :data="list">
+      <el-table-column label="ID" align="center" prop="id" width="80"/>
+      <el-table-column label="名称" align="center" prop="name"/>
+      <el-table-column label="状态" align="center" prop="status"/>
+      <el-table-column label="创建时间" align="center" prop="createTime" width="180"/>
+    </el-table>
+
+    <pagination v-show="total>0" :total="total" :page.sync="queryParams.pageNum" :limit.sync="queryParams.pageSize" @pagination="getList"/>
+  </div>
+</template>
+
+<script>
+export default {
+  name: "CustomerList",
+  data() {
+    return {
+      loading: false,
+      showSearch: true,
+      list: [],
+      total: 0,
+      queryParams: {
+        pageNum: 1,
+        pageSize: 10,
+        keyword: undefined
+      }
+    }
+  },
+  created() {
+    this.getList()
+  },
+  methods: {
+    getList() {
+      this.loading = false
+    },
+    handleQuery() {
+      this.queryParams.pageNum = 1
+      this.getList()
+    },
+    resetQuery() {
+      this.resetForm("queryForm")
+      this.handleQuery()
+    }
+  }
+}
+</script>

+ 57 - 0
src/views/operation/operationList.vue

@@ -0,0 +1,57 @@
+<template>
+  <div class="app-container">
+    <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch">
+      <el-form-item label="关键字" prop="keyword">
+        <el-input v-model="queryParams.keyword" placeholder="请输入关键字" clearable size="small" @keyup.enter.native="handleQuery"/>
+      </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-table v-loading="loading" :data="list">
+      <el-table-column label="ID" align="center" prop="id" width="80"/>
+      <el-table-column label="名称" align="center" prop="name"/>
+      <el-table-column label="状态" align="center" prop="status"/>
+      <el-table-column label="创建时间" align="center" prop="createTime" width="180"/>
+    </el-table>
+
+    <pagination v-show="total>0" :total="total" :page.sync="queryParams.pageNum" :limit.sync="queryParams.pageSize" @pagination="getList"/>
+  </div>
+</template>
+
+<script>
+export default {
+  name: "OperationList",
+  data() {
+    return {
+      loading: false,
+      showSearch: true,
+      list: [],
+      total: 0,
+      queryParams: {
+        pageNum: 1,
+        pageSize: 10,
+        keyword: undefined
+      }
+    }
+  },
+  created() {
+    this.getList()
+  },
+  methods: {
+    getList() {
+      this.loading = false
+    },
+    handleQuery() {
+      this.queryParams.pageNum = 1
+      this.getList()
+    },
+    resetQuery() {
+      this.resetForm("queryForm")
+      this.handleQuery()
+    }
+  }
+}
+</script>