更新细节

This commit is contained in:
yaooo 2023-12-05 20:08:24 +08:00
parent 56ef497aac
commit e7209ce566
12 changed files with 187 additions and 25 deletions

View File

@ -21,6 +21,7 @@
"highlight.js": "^11.6.0", "highlight.js": "^11.6.0",
"nprogress": "^0.2.0", "nprogress": "^0.2.0",
"pinia": "^2.0.14", "pinia": "^2.0.14",
"uuid": "^9.0.1",
"vue": "^3.2.37", "vue": "^3.2.37",
"vue-clipboard3": "^2.0.0", "vue-clipboard3": "^2.0.0",
"vue-echarts": "^6.2.3", "vue-echarts": "^6.2.3",
@ -34,6 +35,7 @@
"@types/lodash-es": "^4.17.6", "@types/lodash-es": "^4.17.6",
"@types/node": "^16.11.41", "@types/node": "^16.11.41",
"@types/nprogress": "^0.2.0", "@types/nprogress": "^0.2.0",
"@types/uuid": "^9.0.7",
"@vitejs/plugin-legacy": "^2.3.1", "@vitejs/plugin-legacy": "^2.3.1",
"@vitejs/plugin-vue": "^3.0.0", "@vitejs/plugin-vue": "^3.0.0",
"@vitejs/plugin-vue-jsx": "^2.0.0", "@vitejs/plugin-vue-jsx": "^2.0.0",
@ -899,6 +901,12 @@
"@types/node": "*" "@types/node": "*"
} }
}, },
"node_modules/@types/uuid": {
"version": "9.0.7",
"resolved": "https://registry.npmmirror.com/@types/uuid/-/uuid-9.0.7.tgz",
"integrity": "sha512-WUtIVRUZ9i5dYXefDEAI7sh9/O7jGvHg7Df/5O/gtH3Yabe5odI3UWopVR1qbPXQtvOxWu3mM4XxlYeZtMWF4g==",
"dev": true
},
"node_modules/@types/web-bluetooth": { "node_modules/@types/web-bluetooth": {
"version": "0.0.14", "version": "0.0.14",
"resolved": "https://registry.npmmirror.com/@types/web-bluetooth/-/web-bluetooth-0.0.14.tgz", "resolved": "https://registry.npmmirror.com/@types/web-bluetooth/-/web-bluetooth-0.0.14.tgz",
@ -7046,6 +7054,14 @@
"integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==",
"dev": true "dev": true
}, },
"node_modules/uuid": {
"version": "9.0.1",
"resolved": "https://registry.npmmirror.com/uuid/-/uuid-9.0.1.tgz",
"integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==",
"bin": {
"uuid": "dist/bin/uuid"
}
},
"node_modules/v8-compile-cache": { "node_modules/v8-compile-cache": {
"version": "2.3.0", "version": "2.3.0",
"resolved": "https://registry.npmmirror.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", "resolved": "https://registry.npmmirror.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz",
@ -8097,6 +8113,12 @@
"@types/node": "*" "@types/node": "*"
} }
}, },
"@types/uuid": {
"version": "9.0.7",
"resolved": "https://registry.npmmirror.com/@types/uuid/-/uuid-9.0.7.tgz",
"integrity": "sha512-WUtIVRUZ9i5dYXefDEAI7sh9/O7jGvHg7Df/5O/gtH3Yabe5odI3UWopVR1qbPXQtvOxWu3mM4XxlYeZtMWF4g==",
"dev": true
},
"@types/web-bluetooth": { "@types/web-bluetooth": {
"version": "0.0.14", "version": "0.0.14",
"resolved": "https://registry.npmmirror.com/@types/web-bluetooth/-/web-bluetooth-0.0.14.tgz", "resolved": "https://registry.npmmirror.com/@types/web-bluetooth/-/web-bluetooth-0.0.14.tgz",
@ -13056,6 +13078,11 @@
"integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==",
"dev": true "dev": true
}, },
"uuid": {
"version": "9.0.1",
"resolved": "https://registry.npmmirror.com/uuid/-/uuid-9.0.1.tgz",
"integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA=="
},
"v8-compile-cache": { "v8-compile-cache": {
"version": "2.3.0", "version": "2.3.0",
"resolved": "https://registry.npmmirror.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", "resolved": "https://registry.npmmirror.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz",

View File

@ -22,6 +22,7 @@
"highlight.js": "^11.6.0", "highlight.js": "^11.6.0",
"nprogress": "^0.2.0", "nprogress": "^0.2.0",
"pinia": "^2.0.14", "pinia": "^2.0.14",
"uuid": "^9.0.1",
"vue": "^3.2.37", "vue": "^3.2.37",
"vue-clipboard3": "^2.0.0", "vue-clipboard3": "^2.0.0",
"vue-echarts": "^6.2.3", "vue-echarts": "^6.2.3",
@ -35,6 +36,7 @@
"@types/lodash-es": "^4.17.6", "@types/lodash-es": "^4.17.6",
"@types/node": "^16.11.41", "@types/node": "^16.11.41",
"@types/nprogress": "^0.2.0", "@types/nprogress": "^0.2.0",
"@types/uuid": "^9.0.7",
"@vitejs/plugin-legacy": "^2.3.1", "@vitejs/plugin-legacy": "^2.3.1",
"@vitejs/plugin-vue": "^3.0.0", "@vitejs/plugin-vue": "^3.0.0",
"@vitejs/plugin-vue-jsx": "^2.0.0", "@vitejs/plugin-vue-jsx": "^2.0.0",

View File

@ -38,4 +38,9 @@ export function apiLandDetail(params: any) {
// 绑定产品 // 绑定产品
export function apiLandBind(params: any) { export function apiLandBind(params: any) {
return request.post({ url: '/land.land/bind', params }) return request.post({ url: '/land.land/bind', params })
}
// 用户信息
export function getUserInfo() {
return request.get({ url: '/auth.admin/mySelf' })
} }

View File

@ -2,7 +2,7 @@ import request from '@/utils/request'
// 用户列表 // 用户列表
export function getUserList(params: any) { export function getUserList(params: any) {
return request.get({ url: '/user.user/lists', params }, { ignoreCancelToken: true }) return request.get({ url: '/user.user/datas', params }, { ignoreCancelToken: true })
} }
// 土地表列表 // 土地表列表
@ -44,4 +44,9 @@ export function apiProductDetail(params: any) {
// 绑定设备 // 绑定设备
export function apiProductBind(params: any) { export function apiProductBind(params: any) {
return request.post({ url: '/land.product/bind', params }) return request.post({ url: '/land.product/bind', params })
}
// 用户信息
export function getUserInfo() {
return request.get({ url: '/auth.admin/mySelf' })
} }

View File

@ -2,8 +2,8 @@ const config = {
terminal: 1, //终端 terminal: 1, //终端
title: '后台管理系统', //网站默认标题 title: '后台管理系统', //网站默认标题
version: '1.6.0', //版本号 version: '1.6.0', //版本号
baseUrl: `${import.meta.env.VITE_APP_BASE_URL || ''}/`, //请求接口域名 // baseUrl: `${import.meta.env.VITE_APP_BASE_URL || ''}/`, //请求接口域名
// baseUrl: 'http://127.0.0.1:30005/', baseUrl: 'http://127.0.0.1:30005/',
urlPrefix: 'adminapi', //请求默认前缀 urlPrefix: 'adminapi', //请求默认前缀
timeout: 10 * 1000 //请求超时时长 timeout: 10 * 1000 //请求超时时长
} }

View File

@ -92,7 +92,7 @@
<script lang="ts" setup name="landEdit"> <script lang="ts" setup name="landEdit">
import type { FormInstance } from 'element-plus' import type { FormInstance } from 'element-plus'
import Popup from '@/components/popup/index.vue' import Popup from '@/components/popup/index.vue'
import { apiLandAdd, apiLandEdit, apiLandDetail, getUserList } from '@/api/land' import { apiLandAdd, apiLandEdit, apiLandDetail, getUserList, getUserInfo } from '@/api/land'
import { timeFormat } from '@/utils/util' import { timeFormat } from '@/utils/util'
import type { PropType } from 'vue' import type { PropType } from 'vue'
defineProps({ defineProps({
@ -224,6 +224,14 @@ const handleSubmit = async () => {
const open = (type = 'add') => { const open = (type = 'add') => {
mode.value = type mode.value = type
popupRef.value?.open() popupRef.value?.open()
getUserInfo()
.then((res: any) => {
const root = res.user.root ?? 0
formData.root = root
})
.catch((err: any) => {
console.log('err', err)
})
} }
// //

View File

@ -13,8 +13,28 @@
<el-input v-model="formData.name" clearable placeholder="请输入产品名称" /> <el-input v-model="formData.name" clearable placeholder="请输入产品名称" />
</el-form-item> </el-form-item>
<el-form-item label="产品编号" prop="code"> <el-form-item label="产品编号" prop="code">
<el-input v-model="formData.code" clearable placeholder="请输入产品编号" /> <el-input v-model="formData.code" clearable disabled placeholder="请输入产品编号" />
</el-form-item> </el-form-item>
<el-form-item v-if="formData.root == 1" label="所属用户" prop="user_id">
<el-select
v-model="formData.user_id"
remote
filterable
placeholder="请输入用户信息"
:remote-method="queryUser"
@change="selectedUser"
:loading="loading"
>
<el-option
v-for="(item, index) in optionsData.user"
:key="index"
:label="item.userinfo"
:value="item.id"
/>
</el-select>
</el-form-item>
<el-form-item label="所属土地" prop="land_id"> <el-form-item label="所属土地" prop="land_id">
<el-select <el-select
v-model="formData.land_id" v-model="formData.land_id"
@ -39,10 +59,12 @@
</template> </template>
<script lang="ts" setup name="productEdit"> <script lang="ts" setup name="productEdit">
import { useDictOptions } from '@/hooks/useDictOptions'
import type { FormInstance } from 'element-plus' import type { FormInstance } from 'element-plus'
import Popup from '@/components/popup/index.vue' import Popup from '@/components/popup/index.vue'
import { apiProductAdd, apiProductEdit, apiProductDetail, getUserList, apiLandLists } from '@/api/product' import { apiProductAdd, apiProductEdit, apiProductDetail, getUserList, getUserInfo, apiLandLists } from '@/api/product'
import { timeFormat } from '@/utils/util' import { timeFormat } from '@/utils/util'
import type { PropType } from 'vue' import type { PropType } from 'vue'
defineProps({ defineProps({
dictData: { dictData: {
@ -64,6 +86,8 @@ const popupTitle = computed(() => {
// //
const formData = reactive({ const formData = reactive({
id: '', id: '',
user_id: '',
root: 0,
land_id: '', land_id: '',
code: '', code: '',
name: '', name: '',
@ -106,6 +130,14 @@ const getDetail = async (row: Record<string, any>) => {
setFormData(data) setFormData(data)
} }
const { optionsData } = useDictOptions<{
user: any[]
}>({
user: {
api: getUserList
}
})
interface ListItem { interface ListItem {
value: string value: string
label: string label: string
@ -114,41 +146,65 @@ interface ListItem {
const landOptions = ref<ListItem[]>([]) const landOptions = ref<ListItem[]>([])
const loading = ref(false) const loading = ref(false)
const queryUser = async (query: string) => {
loading.value = true
const userList = await getUserList({
keyword: query ?? ''
})
optionsData.user = userList
loading.value = false
}
const selectedUser = (value: any) => {
console.log(value)
}
const queryLand = async (query: string) => { const queryLand = async (query: string) => {
if (query) { loading.value = true
loading.value = true const landList = await apiLandLists({
const landList = await apiLandLists({ title: query ?? ''
title: query })
loading.value = false
if (landList.count > 0) {
landOptions.value = landList.lists.map((land: any) => {
return { value: `${land.id}`, label: `ID: ${land.id} / 名称: ${land.title}` }
}) })
loading.value = false
if (landList.count > 0) {
landOptions.value = landList.lists.map((land: any) => {
return { value: `${land.id}`, label: `ID: ${land.id} / 名称: ${land.title}` }
})
} else {
landOptions.value = []
}
loading.value = false
} else { } else {
landOptions.value = [] landOptions.value = []
} }
loading.value = false
} }
// //
const handleSubmit = async () => { const handleSubmit = async () => {
await formRef.value?.validate() await formRef.value?.validate()
const data = { ...formData, } const data = { ...formData }
mode.value == 'edit' mode.value == 'edit' ? await apiProductEdit(data) : await apiProductAdd(data)
? await apiProductEdit(data)
: await apiProductAdd(data)
popupRef.value?.close() popupRef.value?.close()
emit('success') emit('success')
} }
const generateUuid = () => {
return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function (c) {
const r = (Math.random() * 16) | 0
const v = c == 'x' ? r : (r & 0x3) | 0x8
return v.toString(16)
})
}
// //
const open = (type = 'add') => { const open = (type = 'add') => {
mode.value = type mode.value = type
popupRef.value?.open() popupRef.value?.open()
formData.code = generateUuid()
getUserInfo()
.then((res: any) => {
const root = res.user.root ?? 0
formData.root = root
})
.catch((err: any) => {
console.log('err', err)
})
} }
// //

View File

@ -497,6 +497,11 @@
dependencies: dependencies:
"@types/node" "*" "@types/node" "*"
"@types/uuid@^9.0.7":
version "9.0.7"
resolved "https://registry.npmmirror.com/@types/uuid/-/uuid-9.0.7.tgz"
integrity sha512-WUtIVRUZ9i5dYXefDEAI7sh9/O7jGvHg7Df/5O/gtH3Yabe5odI3UWopVR1qbPXQtvOxWu3mM4XxlYeZtMWF4g==
"@types/web-bluetooth@^0.0.14": "@types/web-bluetooth@^0.0.14":
version "0.0.14" version "0.0.14"
resolved "https://registry.npmmirror.com/@types/web-bluetooth/-/web-bluetooth-0.0.14.tgz" resolved "https://registry.npmmirror.com/@types/web-bluetooth/-/web-bluetooth-0.0.14.tgz"
@ -4202,6 +4207,11 @@ util-deprecate@^1.0.1, util-deprecate@^1.0.2:
resolved "https://registry.npmmirror.com/util-deprecate/-/util-deprecate-1.0.2.tgz" resolved "https://registry.npmmirror.com/util-deprecate/-/util-deprecate-1.0.2.tgz"
integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw== integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==
uuid@^9.0.1:
version "9.0.1"
resolved "https://registry.npmmirror.com/uuid/-/uuid-9.0.1.tgz"
integrity sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==
v8-compile-cache@^2.0.3: v8-compile-cache@^2.0.3:
version "2.3.0" version "2.3.0"
resolved "https://registry.npmmirror.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz" resolved "https://registry.npmmirror.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz"

View File

@ -38,6 +38,17 @@ class UserController extends BaseAdminController
return $this->dataLists(new UserLists()); return $this->dataLists(new UserLists());
} }
/**
* @notes 用户列表
* @return \think\response\Json
* @author 段誉
* @date 2022/9/22 16:16
*/
public function datas()
{
$datas = (new UserLogic())->datas(input(''));
return $this->success('', $datas);
}
/** /**
* @notes 获取用户详情 * @notes 获取用户详情

View File

@ -114,7 +114,18 @@ class LandLogic extends BaseLogic
'master_phone' => $params['master_phone'], 'master_phone' => $params['master_phone'],
'pic' => json_encode($params['pic']), 'pic' => json_encode($params['pic']),
]); ]);
$productIdArray = Db::name('product')->alias('p')
->where('lp.land_id', $params['id'])
->leftJoin('land_product lp','lp.product_id = p.id')
->field('p.*')
->column('p.id');
Db::name('product')->whereIn('id', $productIdArray)->update(['user_id'=>$userId]);
$deviceIdArray = Db::name('device')->alias('d')
->whereIn('pd.product_id', $productIdArray)
->leftJoin('product_device pd','pd.device_id = d.id')
->field('d.*')
->column('d.id');
Db::name('device')->whereIn('id', $deviceIdArray)->update(['user_id'=>$userId]);
Db::commit(); Db::commit();
return true; return true;
} catch (\Exception $e) { } catch (\Exception $e) {

View File

@ -51,6 +51,33 @@ class UserLogic extends BaseLogic
return $user->toArray(); return $user->toArray();
} }
public function datas($params): array
{
$userWhere['id'] = 0;
// 超级管理员数据
if (request()->adminInfo['root'] && !request()->adminInfo['user_id']) {
unset($userWhere['id']);
}
// 普通用户数据
if (!request()->adminInfo['root'] && request()->adminInfo['user_id']) {
$userWhere['id'] = request()->adminInfo['user_id'];
}
$where = [];
if (!empty($params['keyword'])) {
$where[] = ['sn|nickname|account|mobile', 'like', '%' . $params['keyword'] . '%'];
}
$field = "id,sn,nickname,sex,avatar,account,mobile,channel,is_disable,create_time";
$lists = User::where($userWhere)->where($where)
->limit(0, 100)
->field($field)
->order('id desc')
->select()->toArray();
foreach ($lists as &$item) {
$item['userinfo'] = $item['id'] . ' / ' . $item['nickname'] . ' / ' . $item['account'];
}
return $lists;
}
/** /**
* @notes 更新用户信息 * @notes 更新用户信息

View File

@ -54,7 +54,7 @@ class User extends BaseModel
public function searchKeywordAttr($query, $value, $data) public function searchKeywordAttr($query, $value, $data)
{ {
if ($value) { if ($value) {
$query->where('sn|nickname|mobile', 'like', '%' . $value . '%'); $query->where('sn|nickname|account|mobile', 'like', '%' . $value . '%');
} }
} }