修复bug

This commit is contained in:
zhanchao 2026-08-13 19:01:37 +08:00
parent edb9ee5c38
commit 92fe63f308
4 changed files with 142 additions and 88 deletions

View File

@ -44,6 +44,7 @@ const { getExternalUserId } = useAccount()
const corpId = ref('');
const corpName = ref('');
const corpUserId = ref('');
const bindCustomerId = ref('');
const referenceCustomerId = ref('');
const customer = ref({});
const customerId = ref('');
@ -59,6 +60,7 @@ const visible = ref(false);
const referenceCustomer = ref(null)
const healthTypes = ref([]);
const enableHis = ref(false);
const source = ref('');
const formData = computed(() => {
return { ...customer.value, ...form.value, mobile: account.value?.mobile }
@ -166,6 +168,11 @@ async function addArchive() {
set('home-invite-team-info', { teamId: teamId.value })
if (res && res.success) {
uni.$emit('reloadTeamCustomers')
if (source.value === 'experienceCoupon') {
await toast('档案创建成功');
uni.navigateBack();
return;
}
// getTeam(corpId.value, teamId.value, res.data.id);
if (healthTypes.value.length) {
const nextType = healthTypes.value[0];
@ -187,6 +194,16 @@ async function getResponsiblePerson() {
return res && res.data ? res.data : ''
}
function backAfterArchiveBound() {
if (source.value === 'experienceCoupon') {
uni.navigateBack()
return;
}
uni.switchTab({
url: '/pages/home/home'
})
}
async function bindArchive(customerId) {
let responsiblePerson = '';
if (externalUserId.value) {
@ -197,9 +214,7 @@ async function bindArchive(customerId) {
if (res && res.success) {
await toast('绑定成功');
uni.$emit('reloadTeamCustomers')
uni.switchTab({
url: '/pages/home/home'
})
backAfterArchiveBound()
} else {
toast(res?.message || '绑定失败');
}
@ -210,9 +225,13 @@ async function init() {
await getCustomer();
} else {
await getExternalUserId(corpId.value);
const res = await getArchives();
const res = bindCustomerId.value ? await getExperienceCouponBindArchive() : await getArchives();
if (res.length > 0) {
visible.value = true;
} else if (source.value === 'experienceCoupon') {
await toast('体验券发放档案不存在或已绑定');
uni.navigateBack();
return;
}
getTeam(corpId.value, teamId.value)
}
@ -223,6 +242,15 @@ async function init() {
}
async function getExperienceCouponBindArchive() {
const res = await api('getCustomerByCustomerId', { corpId: corpId.value, customerId: bindCustomerId.value });
const data = res && res.success && res.data ? res.data : null;
customers.value = data ? [data] : [];
corpName.value = res && res.corpName ? res.corpName : corpName.value;
enableHis.value = false;
return customers.value;
}
async function getArchives() {
const res = await api('getUnbindMiniAppCustomers', { corpId: corpId.value, mobile: account.value?.mobile || '', externalUserId: externalUserId.value });
customers.value = res && Array.isArray(res.data) ? res.data : [];
@ -305,8 +333,10 @@ onLoad(options => {
teamId.value = options.teamId;
corpId.value = options.corpId;
customerId.value = options.id || '';
bindCustomerId.value = options.bindCustomerId || '';
corpUserId.value = options.corpUserId || '';
referenceCustomerId.value = options.referenceCustomerId || '';
source.value = options.source || '';
if (referenceCustomerId.value) {
getReferenceCustomer();
}

View File

@ -1,20 +1,22 @@
<template>
<full-page>
<view class="claim-page">
<view v-if="tip" class="tip">{{ tip }}</view>
<view v-else class="tip">加载中...</view>
</view>
<view>
<full-page>
<view class="claim-page">
<view v-if="tip" class="tip">{{ tip }}</view>
<view v-else class="tip">加载中...</view>
</view>
<view v-if="posterVisible" class="poster-mask">
<view class="poster-dialog">
<image class="poster-image" :src="issue?.posterUrl || ''" mode="widthFix" />
<view class="poster-content">{{ buildClaimContent() }}</view>
<view class="poster-btn" :class="{ disabled: claiming }" @click="acceptCoupon">
{{ claiming ? "领取中..." : "接受" }}
<view v-if="posterVisible" class="poster-mask">
<view class="poster-dialog">
<image class="poster-image" :src="issue?.posterUrl || ''" mode="widthFix" />
<view class="poster-content">{{ buildClaimContent() }}</view>
<view class="poster-btn" :class="{ disabled: claiming }" @click="acceptCoupon">
{{ claiming ? "领取中..." : "接受" }}
</view>
</view>
</view>
</view>
</full-page>
</full-page>
</view>
</template>
<script setup>
@ -23,7 +25,8 @@ import { storeToRefs } from "pinia";
import { onLoad, onShow } from "@dcloudio/uni-app";
import useAccount from "@/store/account";
import api from "@/utils/api";
import { confirm, hideLoading, loading, toast } from "@/utils/widget";
import { set } from "@/utils/cache";
import { hideLoading, loading, toast } from "@/utils/widget";
import { normalizeCorpId } from "@/utils/api-base-config";
import FullPage from "@/components/full-page.vue";
@ -36,11 +39,14 @@ const corpId = ref("");
const issueId = ref("");
const memberId = ref("");
const issue = ref(null);
const issueCustomer = ref(null);
const tip = ref("");
const claiming = ref(false);
const autoPrompted = ref(false);
const posterVisible = ref(false);
const archiveBindPending = ref(false);
const bindingTeamId = ref("");
const bindCorpName = ref("");
const projectNameText = computed(() => {
const projects = Array.isArray(issue.value?.projectSnapshot) ? issue.value.projectSnapshot : [];
@ -80,8 +86,9 @@ async function loadIssueDetail() {
return true;
}
async function getIssueCustomer() {
async function getIssueCustomer({ force = false } = {}) {
if (!corpId.value || !memberId.value) return null;
if (issueCustomer.value && !force) return issueCustomer.value;
try {
const detail = await api(
@ -90,6 +97,8 @@ async function getIssueCustomer() {
false
);
const customer = detail?.data || null;
issueCustomer.value = customer;
bindCorpName.value = detail?.corpName || issue.value?.corpName || "";
const teamIds = Array.isArray(customer?.teamId) ? customer.teamId : [customer?.teamId];
bindingTeamId.value = teamIds.find(Boolean) || "";
return customer;
@ -103,7 +112,7 @@ async function hasBoundArchive() {
const openid = account.value?.openid || "";
if (!openid) return false;
const customer = await getIssueCustomer();
const customer = await getIssueCustomer({ force: true });
return Boolean(customer && String(customer.miniAppId || "") === String(openid));
}
@ -116,13 +125,31 @@ function buildClaimUrl() {
return `/pages/experience-coupon/claim?${params}`;
}
function buildTeamLoginUrl() {
const query = [
"source=teamInvite",
`redirectUrl=${encodeURIComponent(buildClaimUrl())}`,
].join("&");
return `/pages/login/login?${query}`;
}
async function ensurePhoneAuthorized() {
if (account.value?.mobile) return true;
tip.value = "请先授权手机号后再领取体验券";
uni.navigateTo({
url: `/pages/login/login?redirectUrl=${encodeURIComponent(buildClaimUrl())}`,
const customer = await getIssueCustomer();
if (!customer || !bindingTeamId.value) {
tip.value = "体验券发放档案缺少所属团队,暂无法领取";
return false;
}
set("invite-team-info", {
corpId: corpId.value,
teamId: bindingTeamId.value,
corpName: bindCorpName.value || issue.value?.corpName || "",
teamName: issue.value?.teamName || "",
avatars: [],
});
tip.value = "请先授权手机号后再领取体验券";
uni.navigateTo({ url: buildTeamLoginUrl() });
return false;
}
@ -141,13 +168,8 @@ async function ensureTeamAdded() {
);
if (linked) return true;
tip.value = "请先添加体验券所属团队后再领取";
loading("添加团队中...");
try {
await confirm("请先添加体验券所属团队后再领取", {
title: "提示",
confirmText: "添加团队",
cancelText: "取消",
});
const res = await api(
"bindWxappWithTeam",
{
@ -159,49 +181,36 @@ async function ensureTeamAdded() {
false
);
if (!res?.success) {
toast(res?.message || "添加团队失败");
tip.value = res?.message || "添加团队失败";
toast(tip.value);
return false;
}
await getTeams();
return true;
} catch {
return false;
}
}
async function bindIssueArchive() {
if (!memberId.value) {
toast("体验券发放档案不存在");
return;
}
loading("绑定档案中...");
try {
const res = await api(
"bindMiniAppArchive",
{
id: memberId.value,
corpId: corpId.value,
teamId: bindingTeamId.value,
miniAppId: account.value?.openid || "",
},
false
);
if (!res?.success) {
tip.value = res?.message || "绑定档案失败";
toast(tip.value);
return;
}
toast("档案绑定成功");
tip.value = "";
autoPrompted.value = false;
await promptClaim();
} finally {
hideLoading();
}
}
function buildArchiveBindUrl() {
const params = [
`corpId=${encodeURIComponent(corpId.value || "")}`,
`teamId=${encodeURIComponent(bindingTeamId.value || "")}`,
`bindCustomerId=${encodeURIComponent(memberId.value || "")}`,
`source=experienceCoupon`,
].join("&");
return `/pages/archive/edit-archive?${params}`;
}
function openArchiveBindPage() {
if (!issueCustomer.value || !bindingTeamId.value) {
toast("体验券发放档案不存在");
return;
}
archiveBindPending.value = true;
uni.navigateTo({ url: buildArchiveBindUrl() });
}
function isExpiredIssue() {
const expireAt = Number(issue.value?.projectExpireTime || 0);
if (expireAt && Date.now() > expireAt) return true;
@ -227,6 +236,10 @@ async function acceptCoupon() {
if (!res?.success) {
tip.value = res?.message || "领取失败";
toast(tip.value);
if (tip.value.includes("绑定本体验券发放的档案")) {
posterVisible.value = false;
openArchiveBindPage();
}
return;
}
toast("领取成功");
@ -270,17 +283,7 @@ async function promptClaim() {
const bound = await hasBoundArchive();
if (!bound) {
tip.value = "请先绑定档案后再领取体验券";
try {
await confirm("请先绑定档案后再领取体验券", {
title: "提示",
confirmText: "去绑定",
cancelText: "取消",
});
await bindIssueArchive();
} catch {
// ignore
}
openArchiveBindPage();
return;
}
@ -336,9 +339,11 @@ onLoad((opts = {}) => {
});
onShow(() => {
if (issue.value && issue.value.status === "issued" && tip.value.includes("绑定")) {
if (archiveBindPending.value && issue.value && issue.value.status === "issued") {
archiveBindPending.value = false;
autoPrompted.value = false;
promptClaim();
tip.value = "";
posterVisible.value = true;
}
});
</script>

View File

@ -3,7 +3,7 @@
<view class="page-body">
<view v-if="loading" class="empty">加载中...</view>
<view v-else-if="!options.length" class="empty">暂无可用档案</view>
<view v-else class="archive-list">
<scroll-view v-else scroll-y class="archive-list">
<view
v-for="item in options"
:key="item.key"
@ -22,7 +22,7 @@
<view class="archive-id">证件号{{ item.idCardText }}</view>
<view class="archive-corp">{{ item.corpName }}</view>
</view>
</view>
</scroll-view>
</view>
</full-page>
</template>
@ -195,12 +195,16 @@ onLoad(async (optionsData = {}) => {
<style scoped>
.page-body {
min-height: 100%;
height: 100vh;
padding: 24rpx;
box-sizing: border-box;
background: #f5f6fa;
}
.archive-list {
height: 100%;
}
.archive-card {
background: #fff;
border-radius: 18rpx;

View File

@ -133,10 +133,12 @@ async function bindTeam() {
}
await syncExternalUserRelation();
const res1 = await api('getWxAppCustomerCount', { miniAppId: account.value.openid, corpId: team.value.corpId, teamId: team.value.teamId });
if (res1 && res1.data > 0) {
if (redirectUrl.value) {
attempToPage(redirectUrl.value)
} else if (res1 && res1.data > 0) {
toHome();
} else {
attempToPage(redirectUrl.value)
attempToPage(`/pages/archive/edit-archive?corpUserId=${team.value.corpUserId || ''}&teamId=${team.value.teamId}&corpId=${team.value.corpId}`)
}
}
@ -156,20 +158,33 @@ async function getPhoneNumber(e) {
}
async function attempToPage(url) {
const res1 = attempRedirect(url);
if (res1) return;
const res2 = attempSwitchTab(url);
if (res2) return;
toHome();
if (!url) {
toHome();
return;
}
try {
await attempRedirect(url);
return;
} catch {
// redirectTo tabBar switchTab
}
try {
await attempSwitchTab(url);
return;
} catch {
toHome();
}
}
onLoad((opts) => {
redirectUrl.value = opts.redirectUrl || "";
if (opts.source === "teamInvite") {
team.value = get("invite-team-info");
redirectUrl.value = `/pages/archive/edit-archive?corpUserId=${team.value.corpUserId || ''}&teamId=${team.value.teamId}&corpId=${team.value.corpId}`;
if (!redirectUrl.value && team.value) {
redirectUrl.value = `/pages/archive/edit-archive?corpUserId=${team.value.corpUserId || ''}&teamId=${team.value.teamId}&corpId=${team.value.corpId}`;
}
return;
}
redirectUrl.value = opts.redirectUrl || "";
});
</script>
<style scoped>