修复总结后的问题,详见企业微信文档

This commit is contained in:
gyq
2026-05-07 14:34:03 +08:00
parent ffad9432c5
commit ea5a4c14e9
41 changed files with 2678 additions and 1120 deletions

View File

@@ -386,6 +386,7 @@ const emit = defineEmits<{
editClick: [row: IObject];
operatClick: [data: IOperatData];
filterChange: [data: IObject];
selectChange: []
}>();
// 主键
@@ -490,6 +491,7 @@ function handleSelectionChange(selection: any[]) {
console.log("defaultSelData.value", defaultSelData.value);
selectionData.value = selection;
removeIds.value = selection.map((item) => item[pk]);
emit('selectChange', getselectTable())
}
// 获取选中的表格数据
function getselectTable() {

View File

@@ -5,18 +5,8 @@
<el-input v-model="searhForm.name" placeholder="商品名称"></el-input>
</el-form-item>
<el-form-item>
<el-select
style="width: 200px"
v-model="searhForm.category"
placeholder="商品分类"
:disabled="disableCategory"
>
<el-option
:label="item.name"
:value="item.id"
v-for="item in categoryList"
:key="item.id"
></el-option>
<el-select style="width: 200px" v-model="searhForm.category" placeholder="商品分类" :disabled="disableCategory">
<el-option :label="item.name" :value="item.id" v-for="item in categoryList" :key="item.id"></el-option>
</el-select>
</el-form-item>
<el-form-item>
@@ -25,7 +15,7 @@
</el-form-item>
</el-form>
<div class="head-container">
<el-table ref="table" :data="tableData.list" height="500" v-loading="tableData.loading">
<el-table ref="table" :data="tableData.list" height="500" border stripe v-loading="tableData.loading">
<el-table-column type="selection" width="55" align="center" v-if="!radio"></el-table-column>
<el-table-column label="商品信息">
<template v-slot="scope">
@@ -72,14 +62,9 @@
</el-table-column>
</el-table>
</div>
<el-pagination
:total="tableData.total"
:current-page="tableData.page"
:page-size="tableData.size"
@current-change="paginationChange"
@size-change="sizeChange"
layout="total, sizes, prev, pager, next, jumper"
></el-pagination>
<el-pagination :total="tableData.total" :current-page="tableData.page" :page-size="tableData.size"
@current-change="paginationChange" @size-change="sizeChange"
layout="total, sizes, prev, pager, next, jumper"></el-pagination>
<template #footer>
<span class="dialog-footer" v-if="!radio">
<el-button @click="dialogVisible = false"> </el-button>
@@ -132,7 +117,7 @@ export default {
},
// 确定选商品
confirmHandle() {
let res = this.$refs.table.selection;
let res = this.$refs.table.getSelectionRows();
console.log(res);
if (!res) {
return ElMessage.error("请选择商品");
@@ -148,6 +133,7 @@ export default {
this.tableData.page = 1;
this.tableData.size = 10;
this.tableData.list = [];
this.getTableData();
},
// 分页大小改变
sizeChange(e) {

View File

@@ -0,0 +1,123 @@
<template>
<!-- 验证码按钮 - 纯功能高度定制版 -->
<el-button :type="buttonType" :size="buttonSize" :disabled="disabled || isCountingDown" :loading="isLoading"
class="captcha-btn" @click="handleGetCaptcha">
<!-- 倒计时状态展示 -->
<span v-if="isCountingDown">{{ countDown }} 秒后重新获取</span>
<!-- 正常状态展示 -->
<span v-else>{{ buttonText }}</span>
</el-button>
</template>
<script setup>
import { ref } from 'vue'
import { getSms } from "@/api/common";
// 接收父组件传递的自定义参数
const props = defineProps({
// 验证码类型
// editShopInfoOpePwd 店铺操作密码
// wxMiniPwd 微信小程序用户登录密码
// shopPwd 店铺登录密码
type: {
type: String,
default: 'editShopInfoOpePwd'
},
// 按钮类型primary/success/warning/danger/info/default
buttonType: {
type: String,
default: 'primary'
},
// 按钮尺寸large/default/small
buttonSize: {
type: String,
default: 'default'
},
// 正常状态按钮文字
buttonText: {
type: String,
default: '获取验证码'
},
// 倒计时总秒数
countDownNum: {
type: Number,
default: 60
},
// 手动控制按钮禁用状态
disabled: {
type: Boolean,
default: false
}
})
// 发射事件给父组件
const emit = defineEmits(['get-captcha'])
// 加载状态(请求验证码时)
const isLoading = ref(false)
// 是否正在倒计时
const isCountingDown = ref(false)
// 倒计时秒数
const countDown = ref(0)
// 倒计时定时器
let timer = null
// 获取验证码点击事件
const handleGetCaptcha = async () => {
// 倒计时中 / 加载中 / 禁用状态 禁止点击
if (isCountingDown.value || isLoading.value || props.disabled) return
try {
// 开启加载状态
isLoading.value = true
// 触发父组件的请求方法(真正的接口请求写在父组件)
await getSms({ type: props.type });
ElNotification.success({
title: '成功',
message: '验证码已发送,请注意查收',
});
// ======================
// 请求成功 → 开始倒计时
// ======================
startCountDown()
} catch (error) {
// 请求失败 → 不触发倒计时,控制台提示
console.error('', error)
} finally {
// 关闭加载状态
setTimeout(() => {
isLoading.value = false
}, 500) // 适当延迟,避免闪烁
}
}
// 倒计时核心逻辑
const startCountDown = () => {
// 初始化倒计时时间
countDown.value = props.countDownNum
isCountingDown.value = true
// 开启定时器
timer = setInterval(() => {
countDown.value--
// 倒计时结束
if (countDown.value <= 0) {
clearInterval(timer)
timer = null
isCountingDown.value = false
}
}, 1000)
}
// 页面销毁时清除定时器(防止内存泄漏)
onUnmounted(() => {
if (timer) clearInterval(timer)
})
</script>
<style scoped>
/* 你可以在这里自定义按钮默认样式,也可以在父组件覆盖 */
.captcha-btn {
min-width: 120px;
}
</style>

View File

@@ -0,0 +1,180 @@
<template>
<el-dialog title="修改密码" modal-append-to-body append-to-body v-model="dialogVisible" @close="reset" width="400px">
<el-form ref="refForm" :model="form" :rules="rules" label-width="100px">
<el-form-item label="手机号">
<el-input :value="maskPhone(shopInfo.phone)" disabled></el-input>
</el-form-item>
<el-form-item label="旧密码" prop="originalPassword">
<el-input type="password" show-password v-model="form.originalPassword" placeholder="请输入旧密码"></el-input>
</el-form-item>
<el-form-item label="新密码" prop="password">
<el-input type="password" show-password v-model="form.password" placeholder="请输入新密码"></el-input>
</el-form-item>
<el-form-item style="margin-top: -10px;"><el-text :type="isPws ? 'danger' : 'info'" size="small"
style="line-height: 16px;">注意新密码必须至少包含字母数字特殊符号中的两种且长度6-18</el-text></el-form-item>
<el-form-item label="确认新密码" prop="checkPassword">
<el-input type="password" show-password v-model="form.checkPassword" placeholder="请再次输入新密码"></el-input>
</el-form-item>
<el-form-item label="验证码" prop="code">
<div class="center">
<el-input v-model="form.code" placeholder="请输入验证码"></el-input>
<captcha-btn type="shopPwd" />
</div>
</el-form-item>
</el-form>
<template #footer>
<span class="dialog-footer">
<el-button @click="dialogVisible = false"> </el-button>
<el-button type="primary" :loading="formLoading" @click="submitHandle"> </el-button>
</span>
</template>
</el-dialog>
</template>
<script setup lang="ts">
import sysUser from "@/api/account/sysUser";
import { ElNotification } from "element-plus";
import { maskPhone } from "@/utils";
import CaptchaBtn from "./CaptchaBtn.vue";
const props = defineProps({
// 修改成功后的跳转类型 1- 跳转到登录页 2- 留在当前页
type: {
type: [String, Number],
default: 1
}
})
const shopInfo = ref({
phone: ''
})
const router = useRouter();
const dialogVisible = ref(false);
const formLoading = ref(false);
const isPws = ref(false);
const form = reactive({
id: '',
originalPassword: "", // 原密码
code: '', // 验证码
checkPassword: "", // 确认新密码
password: "", // 新密码
});
function reset() {
form.originalPassword = "";
form.checkPassword = "";
form.password = "";
form.code = "";
refForm.value.resetFields();
}
const reg = /^(?![0-9]+$)(?![a-zA-Z]+$)(?![^\da-zA-Z]+$).{6,}$/;
const validateNewPass = (rule: any, value: string, callback: (error?: Error) => void) => {
if (!form.password) {
callback(new Error(" "));
} else if (form.password === form.originalPassword) {
callback(new Error("请输入与旧密码不同的新密码"));
} else if (form.password.length < 6 || form.password.length > 18) {
// 密码长度6 - 18位
callback(new Error("密码长度应为6-18位"));
} else if (!reg.test(form.password)) {
// 新密码长度不能小于6 需包含字母、数字、特殊符号中至少两种
isPws.value = true;
callback(new Error(""));
} else {
isPws.value = false;
callback();
}
};
const validateRnewPass = (rule: any, value: string, callback: (error?: Error) => void) => {
if (!form.checkPassword) {
callback(new Error(" "));
} else if (form.checkPassword !== form.password) {
callback(new Error("两次密码输入不一致"));
} else {
callback();
}
};
const rules = {
originalPassword: [
{
required: true,
message: " ",
trigger: "blur",
},
],
password: [
{
required: true,
validator: validateNewPass,
trigger: "blur",
},
],
checkPassword: [
{
required: true,
validator: validateRnewPass,
trigger: "blur",
},
],
code: [
{
required: true,
message: " ",
trigger: "blur",
},
],
};
const emit = defineEmits(['success'])
const refForm = ref();
// 提交修改密码
function submitHandle() {
refForm.value.validate(async (vaild: boolean) => {
if (vaild) {
try {
formLoading.value = true;
await sysUser.pwd(form);
if (props.type == 1) {
ElNotification.success("密码修改成功,请重新登录");
setTimeout(() => {
router.push("/login");
}, 1000);
} else {
ElNotification.success("密码修改成功");
dialogVisible.value = false;
}
emit('success')
} catch (error) {
formLoading.value = false;
console.log(error);
}
}
});
}
function show(e: object) {
console.log(e);
shopInfo.value = e
form.id = e.id
dialogVisible.value = true
}
defineExpose({
show,
});
</script>
<style lang="scss" scoped>
.center {
display: flex;
align-items: center;
gap: 10px;
}
</style>