|
|
@@ -68,10 +68,10 @@
|
|
|
</el-radio>
|
|
|
</el-radio-group>
|
|
|
</el-form-item>
|
|
|
- <el-form-item label="" prop="validityDays" v-if="voucherModel.expirationType == 0">
|
|
|
+ <el-form-item label="" prop="expirationDate" v-if="voucherModel.expirationType == 0">
|
|
|
<div class="expiration-date-container">
|
|
|
<span class="expiration-label">用户购买</span>
|
|
|
- <el-input-number v-model="voucherModel.validityDays" placeholder="请输入" :min="0" class="expiration-input" />
|
|
|
+ <el-input-number v-model="voucherModel.expirationDate" placeholder="请输入" :min="0" class="expiration-input" />
|
|
|
<span class="expiration-label">天内有效</span>
|
|
|
</div>
|
|
|
</el-form-item>
|
|
|
@@ -79,7 +79,7 @@
|
|
|
<el-date-picker
|
|
|
v-model="voucherModel.validityPeriod"
|
|
|
type="daterange"
|
|
|
- value-format="YYYY-MM-DD"
|
|
|
+ value-format="x"
|
|
|
range-separator="-"
|
|
|
start-placeholder="开始时间"
|
|
|
end-placeholder="结束时间"
|
|
|
@@ -236,7 +236,7 @@ import { ElMessage } from "element-plus";
|
|
|
import { Plus, Delete } from "@element-plus/icons-vue";
|
|
|
import { useRoute, useRouter } from "vue-router";
|
|
|
import type { FormInstance } from "element-plus";
|
|
|
-import { getVoucherDetail, getHolidayList } from "@/api/modules/voucherManagement";
|
|
|
+import { getVoucherDetail, getHolidayList, addOrUpdateCoupon } from "@/api/modules/voucherManagement";
|
|
|
import {
|
|
|
validatePositiveNumber,
|
|
|
validatePositiveInteger,
|
|
|
@@ -248,6 +248,7 @@ import {
|
|
|
validatePriceFormat,
|
|
|
validatePriceComparison
|
|
|
} from "@/utils/eleValidate";
|
|
|
+import { localGet } from "@/utils";
|
|
|
|
|
|
// ==================== 响应式数据定义 ====================
|
|
|
|
|
|
@@ -303,28 +304,60 @@ const rules = reactive({
|
|
|
startDate: [
|
|
|
{ required: true, message: "请选择开始售卖时间" },
|
|
|
{
|
|
|
- validator: validateDateRange(
|
|
|
- () => voucherModel.value.startDate,
|
|
|
- () => voucherModel.value.endDate,
|
|
|
- "开始售卖时间不能早于当前时间",
|
|
|
- "结束售卖时间不能早于当前时间",
|
|
|
- "开始售卖时间必须早于结束售卖时间",
|
|
|
- true
|
|
|
- ),
|
|
|
+ validator: (rule: any, value: any, callback: any) => {
|
|
|
+ if (!value) {
|
|
|
+ callback();
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ const selectedDate = new Date(value);
|
|
|
+ const today = new Date();
|
|
|
+ today.setHours(0, 0, 0, 0);
|
|
|
+ // 验证不能早于今天
|
|
|
+ if (selectedDate < today) {
|
|
|
+ callback(new Error("开始售卖时间不能早于当前时间"));
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ // 验证开始时间必须早于结束时间
|
|
|
+ const endDate = voucherModel.value.endDate;
|
|
|
+ if (endDate) {
|
|
|
+ const end = new Date(endDate);
|
|
|
+ if (selectedDate >= end) {
|
|
|
+ callback(new Error("开始售卖时间必须早于结束售卖时间"));
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ callback();
|
|
|
+ },
|
|
|
trigger: "change"
|
|
|
}
|
|
|
],
|
|
|
endDate: [
|
|
|
{ required: true, message: "请选择结束售卖时间" },
|
|
|
{
|
|
|
- validator: validateDateRange(
|
|
|
- () => voucherModel.value.startDate,
|
|
|
- () => voucherModel.value.endDate,
|
|
|
- "开始售卖时间不能早于当前时间",
|
|
|
- "结束售卖时间不能早于当前时间",
|
|
|
- "开始售卖时间必须早于结束售卖时间",
|
|
|
- true
|
|
|
- ),
|
|
|
+ validator: (rule: any, value: any, callback: any) => {
|
|
|
+ if (!value) {
|
|
|
+ callback();
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ const selectedDate = new Date(value);
|
|
|
+ const today = new Date();
|
|
|
+ today.setHours(0, 0, 0, 0);
|
|
|
+ // 验证不能早于今天
|
|
|
+ if (selectedDate < today) {
|
|
|
+ callback(new Error("结束售卖时间不能早于当前时间"));
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ // 验证结束时间必须晚于开始时间
|
|
|
+ const startDate = voucherModel.value.startDate;
|
|
|
+ if (startDate) {
|
|
|
+ const start = new Date(startDate);
|
|
|
+ if (selectedDate <= start) {
|
|
|
+ callback(new Error("开始售卖时间必须早于结束售卖时间"));
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ callback();
|
|
|
+ },
|
|
|
trigger: "change"
|
|
|
}
|
|
|
],
|
|
|
@@ -342,7 +375,7 @@ const rules = reactive({
|
|
|
}
|
|
|
],
|
|
|
expirationType: [{ required: true, message: "请选择有效期类型" }],
|
|
|
- validityDays: [
|
|
|
+ expirationDate: [
|
|
|
{
|
|
|
required: true,
|
|
|
validator: (rule: any, value: any, callback: any) => {
|
|
|
@@ -426,12 +459,70 @@ const rules = reactive({
|
|
|
{
|
|
|
validator: validatePositiveInteger("单日可用数量必须为正整数", { required: false }),
|
|
|
trigger: "blur"
|
|
|
+ },
|
|
|
+ {
|
|
|
+ validator: (rule: any, value: any, callback: any) => {
|
|
|
+ // 如果值为空,不进行验证
|
|
|
+ if (!value || value.toString().trim() === "") {
|
|
|
+ callback();
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ const stock = voucherModel.value.singleQty;
|
|
|
+ // 如果库存为空,不进行验证(由库存的验证规则处理)
|
|
|
+ if (!stock || stock.toString().trim() === "") {
|
|
|
+ callback();
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ const useNum = Number(value);
|
|
|
+ const stockNum = Number(stock);
|
|
|
+ // 如果转换失败,不进行验证(由其他验证规则处理)
|
|
|
+ if (isNaN(useNum) || isNaN(stockNum)) {
|
|
|
+ callback();
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ // 验证单日可用数量不能多于库存
|
|
|
+ if (useNum > stockNum) {
|
|
|
+ callback(new Error("单日可用数量不能多于库存"));
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ callback();
|
|
|
+ },
|
|
|
+ trigger: "blur"
|
|
|
}
|
|
|
],
|
|
|
purchaseLimitCode: [
|
|
|
{
|
|
|
validator: validatePositiveInteger("限购数量必须为正整数", { required: false }),
|
|
|
trigger: "blur"
|
|
|
+ },
|
|
|
+ {
|
|
|
+ validator: (rule: any, value: any, callback: any) => {
|
|
|
+ // 如果值为空,不进行验证
|
|
|
+ if (!value || value.toString().trim() === "") {
|
|
|
+ callback();
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ const stock = voucherModel.value.singleQty;
|
|
|
+ // 如果库存为空,不进行验证(由库存的验证规则处理)
|
|
|
+ if (!stock || stock.toString().trim() === "") {
|
|
|
+ callback();
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ const limitNum = Number(value);
|
|
|
+ const stockNum = Number(stock);
|
|
|
+ // 如果转换失败,不进行验证(由其他验证规则处理)
|
|
|
+ if (isNaN(limitNum) || isNaN(stockNum)) {
|
|
|
+ callback();
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ // 验证限购数量不能多于库存
|
|
|
+ if (limitNum > stockNum) {
|
|
|
+ callback(new Error("限购数量不能多于库存"));
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ callback();
|
|
|
+ },
|
|
|
+ trigger: "blur"
|
|
|
}
|
|
|
],
|
|
|
applyDesc: [
|
|
|
@@ -470,13 +561,13 @@ const voucherModel = ref<any>({
|
|
|
// 使用时间(虚拟字段,用于表单验证)
|
|
|
usageTime: null,
|
|
|
// 有效期类型:0-指定天数,1-指定时间段内可用
|
|
|
- expirationType: 0,
|
|
|
+ expirationType: "0",
|
|
|
// 有效期天数(当expirationType为0时使用)
|
|
|
- validityDays: 0,
|
|
|
+ expirationDate: 0,
|
|
|
// 有效期时间段(当expirationType为1时使用)
|
|
|
validityPeriod: [],
|
|
|
// 不可用日期类型:0-全部日期可用,1-限制日期
|
|
|
- unusedType: 0,
|
|
|
+ unusedType: "0",
|
|
|
// 限制日期 - 星期选择(数组,存储选中的星期值)
|
|
|
unavailableWeekdays: [],
|
|
|
// 限制日期 - 节日选择(数组,存储选中的节日值)
|
|
|
@@ -490,7 +581,7 @@ const voucherModel = ref<any>({
|
|
|
// 限购数量
|
|
|
purchaseLimitCode: "",
|
|
|
// 适用范围类型:0-全场通用,1-部分不可用
|
|
|
- applyType: 1,
|
|
|
+ applyType: "1",
|
|
|
// 适用范围(当applyType为1时使用)
|
|
|
applyDesc: "",
|
|
|
// 补充说明
|
|
|
@@ -509,21 +600,21 @@ const hourOptions = ref(
|
|
|
|
|
|
// 有效期类型列表
|
|
|
const validityPeriodList = ref([
|
|
|
- { value: 0, label: "指定天数" },
|
|
|
- { value: 1, label: "指定时间段内可用" }
|
|
|
+ { value: "0", label: "指定天数" },
|
|
|
+ { value: "1", label: "指定时间段内可用" }
|
|
|
]);
|
|
|
|
|
|
// 不可用日期类型列表
|
|
|
const unavailableDateTypeList = ref([
|
|
|
- { value: 0, label: "全部日期可用" },
|
|
|
- { value: 1, label: "限制日期" },
|
|
|
- { value: 2, label: "自定义不可用日期" }
|
|
|
+ { value: "0", label: "全部日期可用" },
|
|
|
+ { value: "1", label: "限制日期" }
|
|
|
+ // { value: '2', label: "自定义不可用日期" }
|
|
|
]);
|
|
|
|
|
|
// 适用范围类型列表
|
|
|
const applicableScopeList = ref([
|
|
|
- { value: 1, label: "全场通用" },
|
|
|
- { value: 2, label: "部分不可用" }
|
|
|
+ { value: "1", label: "全场通用" },
|
|
|
+ { value: "2", label: "部分不可用" }
|
|
|
]);
|
|
|
|
|
|
// 星期选项列表
|
|
|
@@ -603,6 +694,26 @@ watch(
|
|
|
);
|
|
|
|
|
|
/**
|
|
|
+ * 监听库存变化
|
|
|
+ * 当库存改变时,重新验证单日可用数量和限购数量
|
|
|
+ */
|
|
|
+watch(
|
|
|
+ () => voucherModel.value.singleQty,
|
|
|
+ () => {
|
|
|
+ if (voucherModel.value.singleCanUse) {
|
|
|
+ nextTick(() => {
|
|
|
+ ruleFormRef.value?.validateField("singleCanUse");
|
|
|
+ });
|
|
|
+ }
|
|
|
+ if (voucherModel.value.purchaseLimitCode) {
|
|
|
+ nextTick(() => {
|
|
|
+ ruleFormRef.value?.validateField("purchaseLimitCode");
|
|
|
+ });
|
|
|
+ }
|
|
|
+ }
|
|
|
+);
|
|
|
+
|
|
|
+/**
|
|
|
* 监听使用开始时间变化
|
|
|
* 更新虚拟字段以支持表单验证
|
|
|
*/
|
|
|
@@ -674,21 +785,30 @@ onMounted(async () => {
|
|
|
|
|
|
// 编辑模式下加载数据
|
|
|
if (type.value != "add") {
|
|
|
- // TODO: 加载代金券详情数据
|
|
|
- // let res: any = await getVoucherDetail({ id: id.value });
|
|
|
- // voucherModel.value = res.data;
|
|
|
- // 确保星期和节日字段存在
|
|
|
- // if (voucherModel.value.unusedType == 1) {
|
|
|
- // const listVal = voucherModel.value.unusedDate ? voucherModel.value.unusedDate.split(";") : [];
|
|
|
- // voucherModel.value.unavailableWeekdays = listVal[0] ? listVal[0].split(",").filter((item: string) => item) : [];
|
|
|
- // voucherModel.value.unavailableHolidays = listVal[1] ? listVal[1].split(",").filter((item: string) => item) : [];
|
|
|
- // }
|
|
|
- // 确保自定义不可用日期字段存在
|
|
|
- // if (voucherModel.value.unusedType === 2) {
|
|
|
- // if (!voucherModel.value.disableDateList || voucherModel.value.disableDateList.length === 0) {
|
|
|
- // voucherModel.value.disableDateList = [null];
|
|
|
- // }
|
|
|
- // }
|
|
|
+ let res: any = await getVoucherDetail({ id: id.value });
|
|
|
+ voucherModel.value = { ...voucherModel.value, ...res.data };
|
|
|
+ // 处理有效期时间段:将时间戳字符串转换为数字数组
|
|
|
+ if (voucherModel.value.validityPeriod && voucherModel.value.expirationType == 1) {
|
|
|
+ const periodArray = voucherModel.value.validityPeriod.split(",");
|
|
|
+ voucherModel.value.validityPeriod = periodArray
|
|
|
+ .map((item: string) => Number(item.trim()))
|
|
|
+ .filter((item: number) => !isNaN(item));
|
|
|
+ } else {
|
|
|
+ voucherModel.value.validityPeriod = [];
|
|
|
+ }
|
|
|
+ // 确保星期和节日字段存在;
|
|
|
+ if (voucherModel.value.unusedType == 1) {
|
|
|
+ const listVal = voucherModel.value.unusedDate ? voucherModel.value.unusedDate.split(";") : [];
|
|
|
+ voucherModel.value.unavailableWeekdays = listVal[0] ? listVal[0].split(",").filter((item: string) => item) : [];
|
|
|
+ voucherModel.value.unavailableHolidays = listVal[1] ? listVal[1].split(",").filter((item: string) => item) : [];
|
|
|
+ }
|
|
|
+ // 确保自定义不可用日期字段存在;
|
|
|
+ if (voucherModel.value.unusedType === 2) {
|
|
|
+ if (!voucherModel.value.disableDateList || voucherModel.value.disableDateList.length === 0) {
|
|
|
+ voucherModel.value.disableDateList = [null];
|
|
|
+ }
|
|
|
+ }
|
|
|
+ console.log(voucherModel.value);
|
|
|
}
|
|
|
});
|
|
|
|
|
|
@@ -776,12 +896,17 @@ const ruleFormRef = ref<FormInstance>(); // 表单引用
|
|
|
* 提交数据(新增/编辑)
|
|
|
* 验证表单,通过后调用相应的API接口
|
|
|
*/
|
|
|
-const handleSubmit = (submitType?: string) => {
|
|
|
+const handleSubmit = async (submitType?: string) => {
|
|
|
// 组装提交参数
|
|
|
let params: any = { ...voucherModel.value };
|
|
|
- // 处理有效期
|
|
|
- if (params.expirationType == 1) {
|
|
|
+ params.storeId = localGet("createdId");
|
|
|
+ params.status = 1;
|
|
|
+ // 处理有效期:只有当expirationType为1(指定时间段内可用)时才处理validityPeriod
|
|
|
+ if (params.expirationType == 1 && params.validityPeriod && Array.isArray(params.validityPeriod)) {
|
|
|
params.validityPeriod = params.validityPeriod.join(",");
|
|
|
+ } else if (params.expirationType == 0) {
|
|
|
+ // 指定天数模式,不需要validityPeriod字段
|
|
|
+ params.validityPeriod = "";
|
|
|
}
|
|
|
// 处理不可用日期
|
|
|
if (params.unusedType == 1) {
|
|
|
@@ -795,31 +920,30 @@ const handleSubmit = (submitType?: string) => {
|
|
|
.join(";");
|
|
|
}
|
|
|
}
|
|
|
-
|
|
|
+ params.dataType = submitType ? 1 : 0;
|
|
|
delete params.unavailableWeekdays;
|
|
|
delete params.unavailableHolidays;
|
|
|
delete params.disableDateList;
|
|
|
console.log("提交参数:", params);
|
|
|
if (submitType) {
|
|
|
+ if (!voucherModel.value.name) {
|
|
|
+ ElMessage.warning("请填写代金券名称");
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ let res: any = await addOrUpdateCoupon(params);
|
|
|
+ if (res && res.code == 200) {
|
|
|
+ ElMessage.success("保存成功");
|
|
|
+ goBack();
|
|
|
+ }
|
|
|
return;
|
|
|
}
|
|
|
-
|
|
|
// 验证表单
|
|
|
ruleFormRef.value!.validate(async (valid: boolean) => {
|
|
|
if (!valid) return;
|
|
|
-
|
|
|
- // TODO: 调用API保存数据
|
|
|
- // if (submitType === 'draft') {
|
|
|
- // await saveVoucherDraft(params);
|
|
|
- // } else {
|
|
|
- // await saveVoucher(params);
|
|
|
- // }
|
|
|
-
|
|
|
- if (submitType === "draft") {
|
|
|
- ElMessage.success("草稿保存成功");
|
|
|
- } else {
|
|
|
- ElMessage.success("代金券创建成功");
|
|
|
- router.go(-1);
|
|
|
+ let res: any = await addOrUpdateCoupon(params);
|
|
|
+ if (res && res.code == 200) {
|
|
|
+ ElMessage.success("保存成功");
|
|
|
+ goBack();
|
|
|
}
|
|
|
});
|
|
|
};
|