修复设备列表过滤筛选的bug
This commit is contained in:
84
Cunkebao/api/device.js
Normal file
84
Cunkebao/api/device.js
Normal file
@@ -0,0 +1,84 @@
|
|||||||
|
import request from '@/utils/request'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取设备列表
|
||||||
|
* @param {Object} params 查询参数
|
||||||
|
* @param {string} params.keyword 关键词搜索(同时搜索IMEI和备注)
|
||||||
|
* @param {number} params.alive 设备在线状态(可选,1:在线 0:离线)
|
||||||
|
* @param {number} params.page 页码
|
||||||
|
* @param {number} params.limit 每页数量
|
||||||
|
* @returns {Promise} 设备列表
|
||||||
|
*
|
||||||
|
* 注意: params 参数会被自动添加到URL查询字符串中,如 /v1/devices?keyword=xxx&alive=1&page=1&limit=20
|
||||||
|
*/
|
||||||
|
export function getDeviceList(params) {
|
||||||
|
return request({
|
||||||
|
url: '/v1/devices',
|
||||||
|
method: 'GET',
|
||||||
|
params
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取设备总数
|
||||||
|
* @param {Object} params 查询参数
|
||||||
|
* @param {number} params.alive 设备在线状态(可选,1:在线 0:离线)
|
||||||
|
* @returns {Promise} 设备总数
|
||||||
|
*/
|
||||||
|
export function getDeviceCount(params) {
|
||||||
|
return request({
|
||||||
|
url: '/v1/devices/count',
|
||||||
|
method: 'GET',
|
||||||
|
params
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取设备详情
|
||||||
|
* @param {number} id 设备ID
|
||||||
|
* @returns {Promise} 设备详情
|
||||||
|
*/
|
||||||
|
export function getDeviceDetail(id) {
|
||||||
|
return request({
|
||||||
|
url: `/v1/devices/${id}`,
|
||||||
|
method: 'GET'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 删除设备
|
||||||
|
* @param {number} id 设备ID
|
||||||
|
* @returns {Promise} 删除结果
|
||||||
|
*/
|
||||||
|
export function deleteDevice(id) {
|
||||||
|
return request({
|
||||||
|
url: `/v1/devices/${id}`,
|
||||||
|
method: 'DELETE'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 刷新设备状态
|
||||||
|
* @returns {Promise} 刷新结果
|
||||||
|
*/
|
||||||
|
export function refreshDevices() {
|
||||||
|
return request({
|
||||||
|
url: '/v1/devices/refresh',
|
||||||
|
method: 'PUT'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 添加设备
|
||||||
|
* @param {Object} data 设备数据
|
||||||
|
* @param {string} data.imei 设备IMEI
|
||||||
|
* @param {string} data.memo 设备备注
|
||||||
|
* @returns {Promise} 添加结果
|
||||||
|
*/
|
||||||
|
export function addDevice(data) {
|
||||||
|
return request({
|
||||||
|
url: '/v1/devices',
|
||||||
|
method: 'POST',
|
||||||
|
data
|
||||||
|
})
|
||||||
|
}
|
||||||
@@ -19,11 +19,11 @@
|
|||||||
<view class="stats-cards">
|
<view class="stats-cards">
|
||||||
<view class="stat-card">
|
<view class="stat-card">
|
||||||
<view class="stat-label">总设备数</view>
|
<view class="stat-label">总设备数</view>
|
||||||
<view class="stat-value blue">42</view>
|
<view class="stat-value blue">{{ totalDeviceCount }}</view>
|
||||||
</view>
|
</view>
|
||||||
<view class="stat-card">
|
<view class="stat-card">
|
||||||
<view class="stat-label">在线设备</view>
|
<view class="stat-label">在线设备</view>
|
||||||
<view class="stat-value green">35</view>
|
<view class="stat-value green">{{ onlineDeviceCount }}</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
@@ -40,6 +40,9 @@
|
|||||||
bgColor="#fff"
|
bgColor="#fff"
|
||||||
searchIconSize="50"
|
searchIconSize="50"
|
||||||
shape="round"
|
shape="round"
|
||||||
|
@search="handleSearch"
|
||||||
|
@clear="handleClearSearch"
|
||||||
|
@input="handleSearchInput"
|
||||||
></u-search>
|
></u-search>
|
||||||
</view>
|
</view>
|
||||||
<view class="filter-btn" @click="showFilter">
|
<view class="filter-btn" @click="showFilter">
|
||||||
@@ -56,8 +59,20 @@
|
|||||||
<text>{{ statusText }}</text>
|
<text>{{ statusText }}</text>
|
||||||
<u-icon name="arrow-down" size="28" color="#333"></u-icon>
|
<u-icon name="arrow-down" size="28" color="#333"></u-icon>
|
||||||
</view>
|
</view>
|
||||||
<view class="select-all">
|
<!-- 添加搜索过滤标签 -->
|
||||||
<u-checkbox v-model="selectAll" size="40" iconSize="35" shape="circle" activeColor="#4080ff"></u-checkbox>
|
<view class="filter-tag" v-if="searchKeyword">
|
||||||
|
<text>{{ searchKeyword }}</text>
|
||||||
|
<text class="close-icon" @click.stop="clearSearch">×</text>
|
||||||
|
</view>
|
||||||
|
<view class="select-all" v-if="deviceList.length > 0">
|
||||||
|
<u-checkbox
|
||||||
|
v-model="selectAll"
|
||||||
|
size="40"
|
||||||
|
iconSize="35"
|
||||||
|
shape="circle"
|
||||||
|
activeColor="#4080ff"
|
||||||
|
@change="handleSelectAllChange"
|
||||||
|
></u-checkbox>
|
||||||
<text class="select-text">全选</text>
|
<text class="select-text">全选</text>
|
||||||
</view>
|
</view>
|
||||||
<view class="delete-btn" @click="deleteDevices" :class="{disabled: !hasSelected}">
|
<view class="delete-btn" @click="deleteDevices" :class="{disabled: !hasSelected}">
|
||||||
@@ -67,83 +82,66 @@
|
|||||||
|
|
||||||
<!-- 设备列表 -->
|
<!-- 设备列表 -->
|
||||||
<view class="device-list">
|
<view class="device-list">
|
||||||
<!-- 设备项 1 -->
|
<!-- 加载中 -->
|
||||||
<view class="device-item" @click="goToDeviceDetail(1)">
|
<view v-if="loading && page === 1" class="loading-container">
|
||||||
<view class="device-checkbox">
|
<u-loading-icon mode="circle" size="36"></u-loading-icon>
|
||||||
<u-checkbox size="40" iconSize="35" v-model="device1Selected" shape="circle" activeColor="#4080ff" @click.stop></u-checkbox>
|
<text class="loading-text">加载中...</text>
|
||||||
</view>
|
|
||||||
<view class="device-info">
|
|
||||||
<view class="device-header">
|
|
||||||
<view class="device-name">设备 1</view>
|
|
||||||
<view class="device-status online">在线</view>
|
|
||||||
</view>
|
|
||||||
<view class="device-imei">IMEI: sd123123</view>
|
|
||||||
<view class="device-wx">微信号: wxid_hxdxdoal</view>
|
|
||||||
<view class="device-likes">
|
|
||||||
<text>好友数: 435</text>
|
|
||||||
<text class="today-stats">今日新增: +20</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<!-- 设备项 2 -->
|
<!-- 空状态 -->
|
||||||
<view class="device-item" @click="goToDeviceDetail(2)">
|
<view v-else-if="deviceList.length === 0" class="empty-container">
|
||||||
<view class="device-checkbox">
|
<u-empty mode="list" text="暂无设备"></u-empty>
|
||||||
<u-checkbox v-model="device2Selected" shape="circle" activeColor="#4080ff"
|
|
||||||
size="40" iconSize="35" @click.stop
|
|
||||||
></u-checkbox>
|
|
||||||
</view>
|
|
||||||
<view class="device-info">
|
|
||||||
<view class="device-header">
|
|
||||||
<view class="device-name">设备 2</view>
|
|
||||||
<view class="device-status online">在线</view>
|
|
||||||
</view>
|
|
||||||
<view class="device-imei">IMEI: sd123124</view>
|
|
||||||
<view class="device-wx">微信号: wxid_2i7sncgq</view>
|
|
||||||
<view class="device-likes">
|
|
||||||
<text>好友数: 143</text>
|
|
||||||
<text class="today-stats">今日新增: +26</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<!-- 设备项 3 -->
|
<!-- 设备列表内容 -->
|
||||||
<view class="device-item" @click="goToDeviceDetail(3)">
|
<template v-else>
|
||||||
<view class="device-checkbox">
|
<!-- 设备项 -->
|
||||||
<u-checkbox size="40" iconSize="35" v-model="device3Selected" shape="circle" activeColor="#4080ff" @click.stop></u-checkbox>
|
<view
|
||||||
</view>
|
class="device-item"
|
||||||
<view class="device-info">
|
v-for="(device, index) in deviceList"
|
||||||
<view class="device-header">
|
:key="device.id"
|
||||||
<view class="device-name">设备 3</view>
|
@click="goToDeviceDetail(device.id)"
|
||||||
<view class="device-status online">在线</view>
|
>
|
||||||
|
<view class="device-checkbox">
|
||||||
|
<u-checkbox
|
||||||
|
:size="40"
|
||||||
|
:iconSize="35"
|
||||||
|
v-model="device.selected"
|
||||||
|
shape="circle"
|
||||||
|
activeColor="#4080ff"
|
||||||
|
@click.stop
|
||||||
|
@change="handleDeviceSelectChange"
|
||||||
|
></u-checkbox>
|
||||||
</view>
|
</view>
|
||||||
<view class="device-imei">IMEI: sd123125</view>
|
<view class="device-info">
|
||||||
<view class="device-wx">微信号: wxid_yunzn4lp</view>
|
<view class="device-header">
|
||||||
<view class="device-likes">
|
<view class="device-name">{{ device.memo || '未命名设备' }}</view>
|
||||||
<text>好友数: 707</text>
|
<view :class="['device-status', device.alive === 1 ? 'online' : 'offline']">
|
||||||
<text class="today-stats">今日新增: +48</text>
|
{{ device.alive === 1 ? '在线' : '离线' }}
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
<view class="device-imei" @click.stop="showImeiDetail(device.imei)">
|
||||||
|
IMEI: <text class="imei-text">{{ formatImei(device.imei) }}</text>
|
||||||
|
</view>
|
||||||
|
<view class="device-wx">微信号: {{ device.wechatId || '未登录' }}</view>
|
||||||
|
<view class="device-likes">
|
||||||
|
<text>好友数: {{ device.totalFriend || 0 }}</text>
|
||||||
|
</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
|
||||||
|
<!-- 加载更多 -->
|
||||||
<!-- 设备项 4 -->
|
<view v-if="hasMoreData && !loadingMore" class="load-more" @click="loadMore">
|
||||||
<view class="device-item" @click="goToDeviceDetail(4)">
|
<text class="load-more-text">点击加载更多</text>
|
||||||
<view class="device-checkbox">
|
|
||||||
<u-checkbox size="40" iconSize="35" v-model="device4Selected" shape="circle" activeColor="#4080ff" @click.stop></u-checkbox>
|
|
||||||
</view>
|
</view>
|
||||||
<view class="device-info">
|
<view v-else-if="loadingMore" class="load-more">
|
||||||
<view class="device-header">
|
<u-loading-icon mode="circle" size="24"></u-loading-icon>
|
||||||
<view class="device-name">设备 4</view>
|
<text class="load-more-text">加载中...</text>
|
||||||
<view class="device-status offline">离线</view>
|
|
||||||
</view>
|
|
||||||
<view class="device-imei">IMEI: sd123126</view>
|
|
||||||
<view class="device-wx">微信号: wxid_4k39dnsc</view>
|
|
||||||
<view class="device-likes">
|
|
||||||
<text>好友数: 529</text>
|
|
||||||
<text class="today-stats">今日新增: +0</text>
|
|
||||||
</view>
|
|
||||||
</view>
|
</view>
|
||||||
</view>
|
<view v-else-if="deviceList.length >= 20" class="load-more">
|
||||||
|
<text class="load-more-text">没有更多数据了</text>
|
||||||
|
</view>
|
||||||
|
</template>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
@@ -190,13 +188,37 @@
|
|||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
|
<!-- IMEI详情模态框 -->
|
||||||
|
<view class="imei-modal" v-if="showImeiModal">
|
||||||
|
<view class="modal-mask" @click="closeImeiModal"></view>
|
||||||
|
<view class="modal-content">
|
||||||
|
<view class="modal-header">
|
||||||
|
<text class="modal-title">IMEI详情</text>
|
||||||
|
<view class="modal-close" @click="closeImeiModal">
|
||||||
|
<text class="close-icon">×</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
<view class="modal-body">
|
||||||
|
<view class="imei-detail">
|
||||||
|
<text class="imei-label">IMEI:</text>
|
||||||
|
<text class="imei-value">{{ currentImei }}</text>
|
||||||
|
</view>
|
||||||
|
<view class="copy-btn" @click="copyImei">
|
||||||
|
<text class="copy-text">复制IMEI</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
<!-- 底部导航栏 -->
|
<!-- 底部导航栏 -->
|
||||||
<CustomTabBar active="profile"></CustomTabBar>
|
<CustomTabBar active="device"></CustomTabBar>
|
||||||
</view>
|
</view>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
import CustomTabBar from '@/components/CustomTabBar.vue'
|
import CustomTabBar from '@/components/CustomTabBar.vue'
|
||||||
|
import * as DeviceApi from '@/api/device'
|
||||||
|
import Auth from '@/utils/auth'
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
components: {
|
components: {
|
||||||
@@ -204,12 +226,29 @@ export default {
|
|||||||
},
|
},
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
|
// 搜索相关
|
||||||
searchKeyword: '',
|
searchKeyword: '',
|
||||||
|
prevSearchKeyword: '', // 添加前一次搜索关键词
|
||||||
|
searchTimer: null, // 添加搜索防抖定时器
|
||||||
|
|
||||||
|
// 设备列表相关
|
||||||
|
deviceList: [],
|
||||||
|
page: 1,
|
||||||
|
limit: 20,
|
||||||
|
total: 0,
|
||||||
|
loading: false,
|
||||||
|
loadingMore: false,
|
||||||
|
hasMoreData: false,
|
||||||
|
|
||||||
|
// 统计相关
|
||||||
|
totalDeviceCount: 0,
|
||||||
|
onlineDeviceCount: 0,
|
||||||
|
|
||||||
|
// 选择相关
|
||||||
selectAll: false,
|
selectAll: false,
|
||||||
device1Selected: false,
|
selectedIds: [],
|
||||||
device2Selected: false,
|
|
||||||
device3Selected: false,
|
// 筛选相关
|
||||||
device4Selected: false,
|
|
||||||
statusPickerShow: false,
|
statusPickerShow: false,
|
||||||
statusOptions: [
|
statusOptions: [
|
||||||
{ text: '全部状态', value: 'all' },
|
{ text: '全部状态', value: 'all' },
|
||||||
@@ -217,40 +256,318 @@ export default {
|
|||||||
{ text: '离线', value: 'offline' }
|
{ text: '离线', value: 'offline' }
|
||||||
],
|
],
|
||||||
currentStatus: 'all',
|
currentStatus: 'all',
|
||||||
// 添加设备相关数据
|
|
||||||
|
// 添加设备相关
|
||||||
showAddDeviceModal: false,
|
showAddDeviceModal: false,
|
||||||
deviceId: ''
|
deviceId: '',
|
||||||
|
|
||||||
|
// IMEI详情相关
|
||||||
|
showImeiModal: false,
|
||||||
|
currentImei: '',
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
hasSelected() {
|
hasSelected() {
|
||||||
return this.device1Selected || this.device2Selected || this.device3Selected || this.device4Selected;
|
return this.selectedIds.length > 0;
|
||||||
},
|
},
|
||||||
statusText() {
|
statusText() {
|
||||||
const selected = this.statusOptions.find(option => option.value === this.currentStatus);
|
const selected = this.statusOptions.find(option => option.value === this.currentStatus);
|
||||||
return selected ? selected.text : '全部状态';
|
return selected ? selected.text : '全部状态';
|
||||||
|
},
|
||||||
|
queryParams() {
|
||||||
|
const params = {
|
||||||
|
page: this.page,
|
||||||
|
limit: this.limit
|
||||||
|
};
|
||||||
|
|
||||||
|
// 添加搜索关键词(添加trim,避免空格干扰)
|
||||||
|
if (this.searchKeyword && this.searchKeyword.trim()) {
|
||||||
|
// 同时搜索IMEI和备注(使用OR关系)
|
||||||
|
params.keyword = this.searchKeyword.trim();
|
||||||
|
}
|
||||||
|
|
||||||
|
// 添加状态筛选
|
||||||
|
if (this.currentStatus === 'online') {
|
||||||
|
params.alive = 1;
|
||||||
|
} else if (this.currentStatus === 'offline') {
|
||||||
|
params.alive = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log('请求参数:', params); // 调试输出,观察参数
|
||||||
|
return params;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
onLoad() {
|
||||||
|
// 检查登录状态
|
||||||
|
if (!Auth.isLogin()) {
|
||||||
|
uni.reLaunch({
|
||||||
|
url: '/pages/login/index'
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取设备统计数据
|
||||||
|
this.loadDeviceStats();
|
||||||
|
|
||||||
|
// 加载设备列表
|
||||||
|
this.loadDeviceList();
|
||||||
|
},
|
||||||
methods: {
|
methods: {
|
||||||
|
// 加载设备统计数据
|
||||||
|
async loadDeviceStats() {
|
||||||
|
try {
|
||||||
|
// 获取设备总数
|
||||||
|
const totalRes = await DeviceApi.getDeviceCount();
|
||||||
|
if (totalRes.code === 200) {
|
||||||
|
this.totalDeviceCount = totalRes.data.count || 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取在线设备数
|
||||||
|
const onlineRes = await DeviceApi.getDeviceCount({ alive: 1 });
|
||||||
|
if (onlineRes.code === 200) {
|
||||||
|
this.onlineDeviceCount = onlineRes.data.count || 0;
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error('加载设备统计数据失败', error);
|
||||||
|
uni.showToast({
|
||||||
|
title: '加载统计数据失败',
|
||||||
|
icon: 'none'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
// 加载设备列表
|
||||||
|
async loadDeviceList(isLoadMore = false) {
|
||||||
|
try {
|
||||||
|
if (isLoadMore) {
|
||||||
|
this.loadingMore = true;
|
||||||
|
} else {
|
||||||
|
this.loading = true;
|
||||||
|
|
||||||
|
if (!isLoadMore) {
|
||||||
|
// 重置页码
|
||||||
|
this.page = 1;
|
||||||
|
this.deviceList = [];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log('发送请求参数:', this.queryParams); // 查看请求参数
|
||||||
|
const res = await DeviceApi.getDeviceList(this.queryParams);
|
||||||
|
|
||||||
|
if (res.code === 200) {
|
||||||
|
const newDevices = res.data.list.map(item => ({
|
||||||
|
...item,
|
||||||
|
selected: false
|
||||||
|
}));
|
||||||
|
|
||||||
|
if (isLoadMore) {
|
||||||
|
this.deviceList = [...this.deviceList, ...newDevices];
|
||||||
|
} else {
|
||||||
|
this.deviceList = newDevices;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.total = res.data.total || 0;
|
||||||
|
this.hasMoreData = this.deviceList.length < this.total;
|
||||||
|
} else {
|
||||||
|
uni.showToast({
|
||||||
|
title: res.msg || '加载设备列表失败',
|
||||||
|
icon: 'none'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error('加载设备列表失败', error);
|
||||||
|
uni.showToast({
|
||||||
|
title: '加载设备列表失败',
|
||||||
|
icon: 'none'
|
||||||
|
});
|
||||||
|
} finally {
|
||||||
|
this.loading = false;
|
||||||
|
this.loadingMore = false;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
// 加载更多
|
||||||
|
loadMore() {
|
||||||
|
if (this.hasMoreData && !this.loadingMore) {
|
||||||
|
this.page++;
|
||||||
|
this.loadDeviceList(true);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
// 处理搜索输入(带防抖)
|
||||||
|
handleSearchInput(value) {
|
||||||
|
// 清除之前的定时器
|
||||||
|
if (this.searchTimer) {
|
||||||
|
clearTimeout(this.searchTimer);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 设置新的定时器(300ms防抖)
|
||||||
|
this.searchTimer = setTimeout(() => {
|
||||||
|
// 如果搜索关键词与前一次相同,不重新加载
|
||||||
|
if (this.searchKeyword.trim() === this.prevSearchKeyword.trim()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.prevSearchKeyword = this.searchKeyword.trim();
|
||||||
|
this.loadDeviceList();
|
||||||
|
}, 300);
|
||||||
|
},
|
||||||
|
|
||||||
|
// 处理搜索
|
||||||
|
handleSearch() {
|
||||||
|
if (this.searchKeyword.trim() === this.prevSearchKeyword.trim()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
this.prevSearchKeyword = this.searchKeyword.trim();
|
||||||
|
this.loadDeviceList();
|
||||||
|
},
|
||||||
|
|
||||||
|
// 清除搜索关键词
|
||||||
|
clearSearch() {
|
||||||
|
this.searchKeyword = '';
|
||||||
|
this.prevSearchKeyword = '';
|
||||||
|
this.loadDeviceList();
|
||||||
|
},
|
||||||
|
|
||||||
|
// 处理清除搜索(组件clear按钮触发)
|
||||||
|
handleClearSearch() {
|
||||||
|
this.searchKeyword = '';
|
||||||
|
this.prevSearchKeyword = '';
|
||||||
|
this.loadDeviceList();
|
||||||
|
},
|
||||||
|
|
||||||
|
// 刷新列表
|
||||||
|
refreshList() {
|
||||||
|
uni.showLoading({
|
||||||
|
title: '刷新中...'
|
||||||
|
});
|
||||||
|
|
||||||
|
Promise.all([
|
||||||
|
DeviceApi.refreshDevices(),
|
||||||
|
this.loadDeviceStats(),
|
||||||
|
this.loadDeviceList()
|
||||||
|
]).finally(() => {
|
||||||
|
uni.hideLoading();
|
||||||
|
uni.showToast({
|
||||||
|
title: '刷新成功',
|
||||||
|
icon: 'success'
|
||||||
|
});
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
// 显示状态筛选
|
||||||
|
showStatusPopup() {
|
||||||
|
this.statusPickerShow = true;
|
||||||
|
},
|
||||||
|
|
||||||
|
// 确认状态筛选
|
||||||
|
confirmStatus(e) {
|
||||||
|
this.currentStatus = e.value[0];
|
||||||
|
this.statusPickerShow = false;
|
||||||
|
|
||||||
|
// 重新加载设备列表
|
||||||
|
this.loadDeviceList();
|
||||||
|
},
|
||||||
|
|
||||||
|
// 取消状态筛选
|
||||||
|
cancelStatus() {
|
||||||
|
this.statusPickerShow = false;
|
||||||
|
},
|
||||||
|
|
||||||
|
// 处理全选状态变化
|
||||||
|
handleSelectAllChange(value) {
|
||||||
|
// 注意:这里的value是uView的checkbox传递的布尔值
|
||||||
|
console.log('全选状态变更为:', value);
|
||||||
|
|
||||||
|
// 更新所有设备的选择状态
|
||||||
|
this.deviceList.forEach(device => {
|
||||||
|
device.selected = value;
|
||||||
|
});
|
||||||
|
|
||||||
|
// 更新已选择的设备ID数组
|
||||||
|
this.selectedIds = value ? this.deviceList.map(device => device.id) : [];
|
||||||
|
},
|
||||||
|
|
||||||
|
// 处理设备选择状态变化
|
||||||
|
handleDeviceSelectChange() {
|
||||||
|
// 更新已选择的设备ID数组
|
||||||
|
this.selectedIds = this.deviceList
|
||||||
|
.filter(device => device.selected)
|
||||||
|
.map(device => device.id);
|
||||||
|
|
||||||
|
// 更新全选状态
|
||||||
|
this.selectAll = this.deviceList.length > 0 && this.selectedIds.length === this.deviceList.length;
|
||||||
|
console.log('更新全选状态为:', this.selectAll, '选中设备数:', this.selectedIds.length);
|
||||||
|
},
|
||||||
|
|
||||||
|
// 删除设备
|
||||||
|
deleteDevices() {
|
||||||
|
if (!this.hasSelected) return;
|
||||||
|
|
||||||
|
uni.showModal({
|
||||||
|
title: '删除设备',
|
||||||
|
content: `确定要删除已选择的 ${this.selectedIds.length} 台设备吗?`,
|
||||||
|
confirmColor: '#f56c6c',
|
||||||
|
success: async (res) => {
|
||||||
|
if (res.confirm) {
|
||||||
|
uni.showLoading({
|
||||||
|
title: '删除中...'
|
||||||
|
});
|
||||||
|
|
||||||
|
try {
|
||||||
|
const deletePromises = this.selectedIds.map(id => DeviceApi.deleteDevice(id));
|
||||||
|
await Promise.all(deletePromises);
|
||||||
|
|
||||||
|
// 刷新列表和统计
|
||||||
|
await this.loadDeviceStats();
|
||||||
|
await this.loadDeviceList();
|
||||||
|
|
||||||
|
uni.showToast({
|
||||||
|
title: '删除成功',
|
||||||
|
icon: 'success'
|
||||||
|
});
|
||||||
|
} catch (error) {
|
||||||
|
console.error('删除设备失败', error);
|
||||||
|
uni.showToast({
|
||||||
|
title: '删除设备失败',
|
||||||
|
icon: 'none'
|
||||||
|
});
|
||||||
|
} finally {
|
||||||
|
uni.hideLoading();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
// 返回上一页
|
// 返回上一页
|
||||||
goBack() {
|
goBack() {
|
||||||
uni.navigateBack();
|
uni.navigateBack();
|
||||||
},
|
},
|
||||||
|
|
||||||
|
// 前往设备详情页
|
||||||
|
goToDeviceDetail(id) {
|
||||||
|
uni.navigateTo({
|
||||||
|
url: `/pages/device/detail?id=${id}`
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
// 显示筛选
|
||||||
|
showFilter() {
|
||||||
|
uni.showToast({
|
||||||
|
title: '筛选功能开发中',
|
||||||
|
icon: 'none'
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
// 添加设备
|
// 添加设备
|
||||||
addDevice() {
|
addDevice() {
|
||||||
this.showAddDeviceModal = true;
|
this.showAddDeviceModal = true;
|
||||||
},
|
},
|
||||||
|
|
||||||
// 取消添加设备
|
|
||||||
cancelAddDevice() {
|
|
||||||
this.showAddDeviceModal = false;
|
|
||||||
this.deviceId = '';
|
|
||||||
},
|
|
||||||
|
|
||||||
// 确认添加设备
|
// 确认添加设备
|
||||||
confirmAddDevice() {
|
async confirmAddDevice() {
|
||||||
if (!this.deviceId.trim()) {
|
if (!this.deviceId) {
|
||||||
uni.showToast({
|
uni.showToast({
|
||||||
title: '请输入设备ID',
|
title: '请输入设备ID',
|
||||||
icon: 'none'
|
icon: 'none'
|
||||||
@@ -259,119 +576,87 @@ export default {
|
|||||||
}
|
}
|
||||||
|
|
||||||
uni.showLoading({
|
uni.showLoading({
|
||||||
title: '添加中'
|
title: '添加中...'
|
||||||
});
|
});
|
||||||
|
|
||||||
setTimeout(() => {
|
try {
|
||||||
uni.hideLoading();
|
const res = await DeviceApi.addDevice({
|
||||||
uni.showToast({
|
imei: this.deviceId,
|
||||||
title: '添加成功',
|
memo: `设备-${this.deviceId.slice(-6)}`
|
||||||
icon: 'success'
|
|
||||||
});
|
});
|
||||||
this.cancelAddDevice();
|
|
||||||
}, 1500);
|
|
||||||
},
|
|
||||||
|
|
||||||
// 刷新列表
|
|
||||||
refreshList() {
|
|
||||||
uni.showLoading({
|
|
||||||
title: '刷新中'
|
|
||||||
});
|
|
||||||
|
|
||||||
setTimeout(() => {
|
|
||||||
uni.hideLoading();
|
|
||||||
uni.showToast({
|
|
||||||
title: '刷新成功',
|
|
||||||
icon: 'success'
|
|
||||||
});
|
|
||||||
}, 1000);
|
|
||||||
},
|
|
||||||
|
|
||||||
// 显示筛选
|
|
||||||
showFilter() {
|
|
||||||
uni.showToast({
|
|
||||||
title: '筛选功能待实现',
|
|
||||||
icon: 'none'
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
// 显示状态选择
|
|
||||||
showStatusPopup() {
|
|
||||||
this.statusPickerShow = true;
|
|
||||||
},
|
|
||||||
|
|
||||||
// 确认状态选择
|
|
||||||
confirmStatus(e) {
|
|
||||||
this.currentStatus = e.value[0];
|
|
||||||
this.statusPickerShow = false;
|
|
||||||
|
|
||||||
// 应用筛选逻辑
|
|
||||||
this.applyStatusFilter();
|
|
||||||
},
|
|
||||||
|
|
||||||
// 应用状态筛选
|
|
||||||
applyStatusFilter() {
|
|
||||||
uni.showLoading({
|
|
||||||
title: '筛选中'
|
|
||||||
});
|
|
||||||
|
|
||||||
// 模拟筛选过程
|
|
||||||
setTimeout(() => {
|
|
||||||
uni.hideLoading();
|
|
||||||
|
|
||||||
// 提示用户
|
if (res.code === 200) {
|
||||||
|
uni.showToast({
|
||||||
|
title: '添加成功',
|
||||||
|
icon: 'success'
|
||||||
|
});
|
||||||
|
|
||||||
|
this.showAddDeviceModal = false;
|
||||||
|
this.deviceId = '';
|
||||||
|
|
||||||
|
// 刷新列表和统计
|
||||||
|
await this.loadDeviceStats();
|
||||||
|
await this.loadDeviceList();
|
||||||
|
} else {
|
||||||
|
uni.showToast({
|
||||||
|
title: res.msg || '添加失败',
|
||||||
|
icon: 'none'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error('添加设备失败', error);
|
||||||
uni.showToast({
|
uni.showToast({
|
||||||
title: `已筛选: ${this.statusText}`,
|
title: '添加设备失败',
|
||||||
icon: 'none'
|
icon: 'none'
|
||||||
});
|
});
|
||||||
|
} finally {
|
||||||
// 这里可以添加实际的设备筛选逻辑
|
uni.hideLoading();
|
||||||
// 根据 this.currentStatus 对设备列表进行筛选
|
}
|
||||||
}, 500);
|
|
||||||
},
|
},
|
||||||
|
|
||||||
// 取消状态选择
|
// 取消添加设备
|
||||||
cancelStatus() {
|
cancelAddDevice() {
|
||||||
this.statusPickerShow = false;
|
this.showAddDeviceModal = false;
|
||||||
|
this.deviceId = '';
|
||||||
},
|
},
|
||||||
|
|
||||||
// 删除设备
|
// 格式化IMEI,超过一定长度显示省略号
|
||||||
deleteDevices() {
|
formatImei(imei) {
|
||||||
if (!this.hasSelected) return;
|
if (!imei) return '';
|
||||||
|
|
||||||
uni.showModal({
|
// 如果IMEI长度超过16个字符,则截取前16个字符并添加省略号
|
||||||
title: '确认删除',
|
if (imei.length > 16) {
|
||||||
content: '确定要删除选中的设备吗?',
|
return imei.substring(0, 16) + '...';
|
||||||
success: (res) => {
|
}
|
||||||
if (res.confirm) {
|
|
||||||
uni.showToast({
|
return imei;
|
||||||
title: '删除成功',
|
},
|
||||||
icon: 'success'
|
|
||||||
});
|
// 显示IMEI详情
|
||||||
this.device1Selected = false;
|
showImeiDetail(imei) {
|
||||||
this.device2Selected = false;
|
this.currentImei = imei;
|
||||||
this.device3Selected = false;
|
this.showImeiModal = true;
|
||||||
this.device4Selected = false;
|
},
|
||||||
this.selectAll = false;
|
|
||||||
}
|
// 关闭IMEI详情模态框
|
||||||
|
closeImeiModal() {
|
||||||
|
this.showImeiModal = false;
|
||||||
|
this.currentImei = '';
|
||||||
|
},
|
||||||
|
|
||||||
|
// 复制IMEI到剪贴板
|
||||||
|
copyImei() {
|
||||||
|
uni.setClipboardData({
|
||||||
|
data: this.currentImei,
|
||||||
|
success: () => {
|
||||||
|
uni.showToast({
|
||||||
|
title: 'IMEI已复制',
|
||||||
|
icon: 'success'
|
||||||
|
});
|
||||||
|
this.closeImeiModal();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
// 跳转到设备详情页
|
|
||||||
goToDeviceDetail(deviceId) {
|
|
||||||
uni.navigateTo({
|
|
||||||
url: `/pages/device/detail?id=${deviceId}`
|
|
||||||
});
|
|
||||||
}
|
|
||||||
},
|
|
||||||
watch: {
|
|
||||||
selectAll(newVal) {
|
|
||||||
this.device1Selected = newVal;
|
|
||||||
this.device2Selected = newVal;
|
|
||||||
this.device3Selected = newVal;
|
|
||||||
this.device4Selected = newVal;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
@@ -518,8 +803,8 @@ export default {
|
|||||||
color: #333;
|
color: #333;
|
||||||
padding: 10rpx 20rpx;
|
padding: 10rpx 20rpx;
|
||||||
border-radius: 20rpx;
|
border-radius: 20rpx;
|
||||||
background-color: #fff;
|
background-color: #f0f5ff;
|
||||||
border: 1rpx solid #e5e5e5;
|
border: 1rpx solid #d6e4ff;
|
||||||
min-width: 180rpx;
|
min-width: 180rpx;
|
||||||
justify-content: space-between;
|
justify-content: space-between;
|
||||||
|
|
||||||
@@ -528,7 +813,35 @@ export default {
|
|||||||
}
|
}
|
||||||
|
|
||||||
&:active {
|
&:active {
|
||||||
background-color: #f8f8f8;
|
background-color: #e0ebff;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.filter-tag {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
font-size: 24rpx;
|
||||||
|
color: #4080ff;
|
||||||
|
padding: 6rpx 16rpx;
|
||||||
|
border-radius: 16rpx;
|
||||||
|
background-color: #f0f5ff;
|
||||||
|
border: 1rpx solid #d6e4ff;
|
||||||
|
margin-left: 16rpx;
|
||||||
|
margin-right: auto;
|
||||||
|
max-width: 250rpx;
|
||||||
|
overflow: hidden;
|
||||||
|
white-space: nowrap;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
|
||||||
|
.close-icon {
|
||||||
|
margin-left: 12rpx;
|
||||||
|
font-size: 28rpx;
|
||||||
|
line-height: 24rpx;
|
||||||
|
color: #999;
|
||||||
|
|
||||||
|
&:active {
|
||||||
|
color: #666;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -618,6 +931,20 @@ export default {
|
|||||||
color: #666;
|
color: #666;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.device-imei {
|
||||||
|
cursor: pointer;
|
||||||
|
|
||||||
|
.imei-text {
|
||||||
|
color: #4080ff;
|
||||||
|
padding-left: 10rpx;
|
||||||
|
font-size: 32rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
&:active {
|
||||||
|
opacity: 0.7;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
.device-likes {
|
.device-likes {
|
||||||
display: flex;
|
display: flex;
|
||||||
justify-content: space-between;
|
justify-content: space-between;
|
||||||
@@ -626,6 +953,33 @@ export default {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.loading-container, .empty-container {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
padding: 100rpx 0;
|
||||||
|
|
||||||
|
.loading-text {
|
||||||
|
font-size: 28rpx;
|
||||||
|
color: #999;
|
||||||
|
margin-top: 20rpx;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.load-more {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
padding: 30rpx 0;
|
||||||
|
|
||||||
|
.load-more-text {
|
||||||
|
font-size: 28rpx;
|
||||||
|
color: #999;
|
||||||
|
margin-left: 10rpx;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* 添加设备弹窗样式 */
|
/* 添加设备弹窗样式 */
|
||||||
@@ -740,4 +1094,104 @@ export default {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* IMEI详情模态框样式 */
|
||||||
|
.imei-modal {
|
||||||
|
position: fixed;
|
||||||
|
top: 0;
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
bottom: 0;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
z-index: 9999;
|
||||||
|
|
||||||
|
.modal-mask {
|
||||||
|
position: absolute;
|
||||||
|
top: 0;
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
bottom: 0;
|
||||||
|
background-color: rgba(0, 0, 0, 0.5);
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-content {
|
||||||
|
position: relative;
|
||||||
|
width: 600rpx;
|
||||||
|
background-color: #fff;
|
||||||
|
border-radius: 20rpx;
|
||||||
|
overflow: hidden;
|
||||||
|
box-shadow: 0 4rpx 16rpx rgba(0, 0, 0, 0.1);
|
||||||
|
|
||||||
|
.modal-header {
|
||||||
|
display: flex;
|
||||||
|
justify-content: space-between;
|
||||||
|
align-items: center;
|
||||||
|
padding: 30rpx 40rpx;
|
||||||
|
|
||||||
|
.modal-title {
|
||||||
|
font-size: 36rpx;
|
||||||
|
font-weight: bold;
|
||||||
|
color: #333;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-close {
|
||||||
|
padding: 10rpx;
|
||||||
|
|
||||||
|
.close-icon {
|
||||||
|
font-size: 44rpx;
|
||||||
|
color: #777;
|
||||||
|
line-height: 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-body {
|
||||||
|
padding: 20rpx 40rpx 40rpx;
|
||||||
|
|
||||||
|
.imei-detail {
|
||||||
|
background-color: #f5f7fa;
|
||||||
|
padding: 30rpx;
|
||||||
|
border-radius: 10rpx;
|
||||||
|
margin-bottom: 30rpx;
|
||||||
|
|
||||||
|
.imei-label {
|
||||||
|
display: block;
|
||||||
|
font-size: 28rpx;
|
||||||
|
color: #666;
|
||||||
|
margin-bottom: 10rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
.imei-value {
|
||||||
|
display: block;
|
||||||
|
font-size: 32rpx;
|
||||||
|
color: #333;
|
||||||
|
word-break: break-all;
|
||||||
|
font-family: monospace;
|
||||||
|
line-height: 1.5;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.copy-btn {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
background-color: #4080ff;
|
||||||
|
color: #fff;
|
||||||
|
padding: 20rpx 0;
|
||||||
|
border-radius: 10rpx;
|
||||||
|
|
||||||
|
.copy-text {
|
||||||
|
margin-left: 10rpx;
|
||||||
|
font-size: 28rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
&:active {
|
||||||
|
opacity: 0.8;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
@@ -91,6 +91,25 @@ function responseInterceptor(response) {
|
|||||||
return response.data;
|
return response.data;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 构建完整的URL,包括查询参数
|
||||||
|
* @param {string} baseUrl 基础URL
|
||||||
|
* @param {Object} params 查询参数
|
||||||
|
* @returns {string} 完整的URL
|
||||||
|
*/
|
||||||
|
function buildUrlWithParams(baseUrl, params) {
|
||||||
|
if (!params || Object.keys(params).length === 0) {
|
||||||
|
return baseUrl;
|
||||||
|
}
|
||||||
|
|
||||||
|
const queryString = Object.keys(params)
|
||||||
|
.filter(key => params[key] !== undefined && params[key] !== null)
|
||||||
|
.map(key => `${encodeURIComponent(key)}=${encodeURIComponent(params[key])}`)
|
||||||
|
.join('&');
|
||||||
|
|
||||||
|
return queryString ? `${baseUrl}${baseUrl.includes('?') ? '&' : '?'}${queryString}` : baseUrl;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 统一请求函数
|
* 统一请求函数
|
||||||
* @param {Object} options 请求选项
|
* @param {Object} options 请求选项
|
||||||
@@ -110,12 +129,24 @@ function request(options) {
|
|||||||
// 请求拦截
|
// 请求拦截
|
||||||
const interceptedConfig = requestInterceptor(config);
|
const interceptedConfig = requestInterceptor(config);
|
||||||
|
|
||||||
|
// 处理GET请求参数
|
||||||
|
let url = `${interceptedConfig.baseURL}${interceptedConfig.url}`;
|
||||||
|
const method = interceptedConfig.method || 'GET';
|
||||||
|
|
||||||
|
// 如果是GET请求并且有params参数,将其转换为URL查询字符串
|
||||||
|
if (method.toUpperCase() === 'GET' && interceptedConfig.params) {
|
||||||
|
url = buildUrlWithParams(url, interceptedConfig.params);
|
||||||
|
|
||||||
|
// 打印完整请求URL(便于调试)
|
||||||
|
console.log('完整请求URL:', url);
|
||||||
|
}
|
||||||
|
|
||||||
// 发起请求
|
// 发起请求
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
uni.request({
|
uni.request({
|
||||||
url: `${interceptedConfig.baseURL}${interceptedConfig.url}`,
|
url: url,
|
||||||
method: interceptedConfig.method || 'GET',
|
method: method,
|
||||||
data: interceptedConfig.data,
|
data: method.toUpperCase() === 'GET' ? undefined : interceptedConfig.data,
|
||||||
header: interceptedConfig.header,
|
header: interceptedConfig.header,
|
||||||
timeout: interceptedConfig.timeout,
|
timeout: interceptedConfig.timeout,
|
||||||
success: (res) => {
|
success: (res) => {
|
||||||
@@ -127,12 +158,25 @@ function request(options) {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
fail: (err) => {
|
fail: (err) => {
|
||||||
|
// 显示提示
|
||||||
uni.showToast({
|
uni.showToast({
|
||||||
title: '网络请求失败',
|
title: '网络请求失败',
|
||||||
icon: 'none',
|
icon: 'none',
|
||||||
duration: 2000
|
duration: 2000
|
||||||
});
|
});
|
||||||
reject(err);
|
|
||||||
|
// 增强错误对象,添加更多信息便于调试
|
||||||
|
const enhancedError = {
|
||||||
|
...err,
|
||||||
|
url: url,
|
||||||
|
method: method,
|
||||||
|
params: method.toUpperCase() === 'GET' ? interceptedConfig.params : undefined,
|
||||||
|
data: method.toUpperCase() === 'GET' ? undefined : interceptedConfig.data,
|
||||||
|
message: err.errMsg || '网络请求失败'
|
||||||
|
};
|
||||||
|
|
||||||
|
console.error('请求失败详情:', enhancedError);
|
||||||
|
reject(enhancedError);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -106,26 +106,14 @@ class Device extends Controller
|
|||||||
try {
|
try {
|
||||||
// 获取登录用户信息
|
// 获取登录用户信息
|
||||||
$userInfo = request()->userInfo;
|
$userInfo = request()->userInfo;
|
||||||
if (empty($userInfo)) {
|
|
||||||
return json([
|
|
||||||
'code' => 401,
|
|
||||||
'msg' => '未登录或登录已过期'
|
|
||||||
]);
|
|
||||||
}
|
|
||||||
|
|
||||||
// 获取查询条件
|
// 获取查询条件
|
||||||
$where = [];
|
$where = [];
|
||||||
|
|
||||||
// 设备IMEI
|
// 关键词搜索(同时搜索IMEI和备注)
|
||||||
$imei = Request::param('imei');
|
$keyword = Request::param('keyword');
|
||||||
if (!empty($imei)) {
|
if (!empty($keyword)) {
|
||||||
$where['d.imei'] = ['like', "%{$imei}%"];
|
// 使用复杂条件实现OR查询
|
||||||
}
|
$where[] = ['exp', "d.imei LIKE '%{$keyword}%' OR d.memo LIKE '%{$keyword}%'"];
|
||||||
|
|
||||||
// 设备备注
|
|
||||||
$memo = Request::param('memo');
|
|
||||||
if (!empty($memo)) {
|
|
||||||
$where['d.memo'] = ['like', "%{$memo}%"];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 设备在线状态
|
// 设备在线状态
|
||||||
|
|||||||
@@ -79,31 +79,25 @@ class Device extends Model
|
|||||||
$where['d.isDeleted'] = 0;
|
$where['d.isDeleted'] = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// 处理查询条件,避免排序规则冲突
|
// 构建查询对象
|
||||||
$conditions = [];
|
|
||||||
foreach ($where as $key => $value) {
|
|
||||||
// 对于涉及 JOIN 的字段特殊处理
|
|
||||||
if (strpos($key, 'imei') !== false) {
|
|
||||||
// 删除原本的 imei 条件,避免直接使用它
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
$conditions[$key] = $value;
|
|
||||||
}
|
|
||||||
|
|
||||||
$query = self::alias('d')
|
$query = self::alias('d')
|
||||||
->field(['d.id', 'd.imei', 'd.memo', 'w.wechatId', 'd.alive', 'w.totalFriend'])
|
->field(['d.id', 'd.imei', 'd.memo', 'w.wechatId', 'd.alive', 'w.totalFriend'])
|
||||||
->leftJoin('tk_wechat_account w', 'd.imei = w.imei COLLATE utf8mb4_unicode_ci')
|
->leftJoin('tk_wechat_account w', 'd.imei = w.imei COLLATE utf8mb4_unicode_ci');
|
||||||
->where($conditions);
|
|
||||||
|
|
||||||
// 单独处理 imei 搜索条件,确保使用相同的排序规则
|
// 处理查询条件
|
||||||
if (isset($where['imei'])) {
|
foreach ($where as $key => $value) {
|
||||||
if (is_array($where['imei']) && isset($where['imei'][0]) && $where['imei'][0] === 'like') {
|
// 处理特殊的exp表达式条件
|
||||||
$query->where('d.imei', 'like', $where['imei'][1]);
|
if (is_numeric($key) && is_array($value) && isset($value[0]) && $value[0] === 'exp') {
|
||||||
} else {
|
// 直接添加原始SQL表达式
|
||||||
$query->where('d.imei', $where['imei']);
|
$query->whereExp('', $value[1]);
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 处理普通条件
|
||||||
|
$query->where($key, $value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 返回分页结果
|
||||||
return $query->order($order)
|
return $query->order($order)
|
||||||
->paginate($limit, false, ['page' => $page]);
|
->paginate($limit, false, ['page' => $page]);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user