feat(tahesab): three-way mande decision UI including push to Tahesab

Clarify overwrite vs keep vs push-to-tahesab, warn when app balance is zero, and update colleague wait-callback help text.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-09-05 22:30:58 +03:30
co-authored by Cursor
parent e0b89223ac
commit 9ef381f00e
6 changed files with 208 additions and 42 deletions
+8 -1
View File
@@ -254,13 +254,20 @@ export interface TahesabWalletSyncResult {
/** همگام‌سازی مانده یک مشتری با ته‌حساب */ /** همگام‌سازی مانده یک مشتری با ته‌حساب */
export const syncCustomerWalletFromTahesab = async ( export const syncCustomerWalletFromTahesab = async (
customerId: number, customerId: number,
opts?: { overwrite?: boolean; keep?: boolean; ask_if_conflict?: boolean; always_ask?: boolean } opts?: {
overwrite?: boolean
keep?: boolean
push_to_tahesab?: boolean
ask_if_conflict?: boolean
always_ask?: boolean
}
) => ) =>
await useAxios.post<TahesabWalletSyncResult>( await useAxios.post<TahesabWalletSyncResult>(
`/admin/customer/${customerId}/tahesab/sync-wallet`, `/admin/customer/${customerId}/tahesab/sync-wallet`,
{ {
overwrite: opts?.overwrite ?? false, overwrite: opts?.overwrite ?? false,
keep: opts?.keep ?? false, keep: opts?.keep ?? false,
push_to_tahesab: opts?.push_to_tahesab ?? false,
ask_if_conflict: opts?.ask_if_conflict ?? true, ask_if_conflict: opts?.ask_if_conflict ?? true,
always_ask: opts?.always_ask ?? false, always_ask: opts?.always_ask ?? false,
} }
@@ -7,7 +7,7 @@
<AdminFieldHelp :text="accountingTahesabBalanceSyncIntro" size="sm" /> <AdminFieldHelp :text="accountingTahesabBalanceSyncIntro" size="sm" />
</div> </div>
<p class="tw-bulk__hint"> <p class="tw-bulk__hint">
همگام تکی: اول سندها و اختلاف را می‌بینید، بعد تأیید می‌کنید. دو مانده جمع نمی‌شوند. همگام تکی: اول سندها و اختلاف را می‌بینید، بعد یکی از سه مسیر را تأیید می‌کنید (ته‌حساب→اپ، اپ→ته‌حساب حتی اگر اپ صفر باشد، یا نگه داشتن). دو مانده جمع نمی‌شوند.
همگام همه فقط کیف خالی را می‌نشاند؛ تداخل برای تصمیم دستی می‌ماند. همگام همه فقط کیف خالی را می‌نشاند؛ تداخل برای تصمیم دستی می‌ماند.
</p> </p>
</div> </div>
@@ -154,6 +154,7 @@
<TahesabMandeDecisionModal <TahesabMandeDecisionModal
v-model:visible="decisionVisible" v-model:visible="decisionVisible"
source-label="ته‌حساب" source-label="ته‌حساب"
:allow-push="true"
:app-gold="decisionResult?.app_gold" :app-gold="decisionResult?.app_gold"
:app-cash="decisionResult?.app_cash" :app-cash="decisionResult?.app_cash"
:tahesab-gold="decisionResult?.tahesab_gold" :tahesab-gold="decisionResult?.tahesab_gold"
@@ -200,7 +201,7 @@ const failed = ref(0)
const errors = ref<TahesabBulkWalletSyncChunk['errors']>([]) const errors = ref<TahesabBulkWalletSyncChunk['errors']>([])
const decisions = ref<TahesabBulkWalletSyncChunk['decisions']>([]) const decisions = ref<TahesabBulkWalletSyncChunk['decisions']>([])
const decidingId = ref<number | null>(null) const decidingId = ref<number | null>(null)
const decidingMode = ref<'overwrite' | 'keep' | null>(null) const decidingMode = ref<'overwrite' | 'keep' | 'push' | null>(null)
const search = ref('') const search = ref('')
const page = ref(1) const page = ref(1)
@@ -209,7 +210,7 @@ const listTotal = ref(0)
const listLoading = ref(false) const listLoading = ref(false)
const rows = ref<TahesabWalletLinkedRow[]>([]) const rows = ref<TahesabWalletLinkedRow[]>([])
const syncingId = ref<number | null>(null) const syncingId = ref<number | null>(null)
const syncingMode = ref<'ask' | 'overwrite' | 'keep' | null>(null) const syncingMode = ref<'ask' | 'overwrite' | 'keep' | 'push' | null>(null)
const decisionVisible = ref(false) const decisionVisible = ref(false)
const decisionCustomerId = ref<number | null>(null) const decisionCustomerId = ref<number | null>(null)
const decisionResult = ref<TahesabWalletSyncResult['result'] | null>(null) const decisionResult = ref<TahesabWalletSyncResult['result'] | null>(null)
@@ -321,7 +322,7 @@ async function openReview(customerId: number) {
} }
} }
async function onReviewDecide(mode: 'overwrite' | 'keep') { async function onReviewDecide(mode: 'overwrite' | 'keep' | 'push') {
const customerId = decisionCustomerId.value const customerId = decisionCustomerId.value
decisionVisible.value = false decisionVisible.value = false
if (!customerId) return if (!customerId) return
@@ -337,22 +338,25 @@ function dismissResult() {
showDetails.value = false showDetails.value = false
} }
async function applyDecision(customerId: number, mode: 'overwrite' | 'keep') { async function applyDecision(customerId: number, mode: 'overwrite' | 'keep' | 'push') {
decidingId.value = customerId decidingId.value = customerId
decidingMode.value = mode decidingMode.value = mode
try { try {
const res = await syncCustomerWalletFromTahesab(customerId, { const res = await syncCustomerWalletFromTahesab(customerId, {
overwrite: mode === 'overwrite', overwrite: mode === 'overwrite',
keep: mode === 'keep', keep: mode === 'keep',
push_to_tahesab: mode === 'push',
ask_if_conflict: false, ask_if_conflict: false,
}) })
decisions.value = decisions.value.filter(d => d.id !== customerId) decisions.value = decisions.value.filter(d => d.id !== customerId)
needsDecision.value = Math.max(0, decisions.value.length) needsDecision.value = Math.max(0, decisions.value.length)
if (mode === 'keep') message.info(res.message || 'موجودی اپ حفظ شد') if (mode === 'keep') message.info(res.message || 'موجودی اپ حفظ شد')
else if (mode === 'push') message.success(res.message || 'مانده اپ روی ته‌حساب اعمال شد')
else message.success(res.message || 'مانده ته‌حساب اعمال شد') else message.success(res.message || 'مانده ته‌حساب اعمال شد')
await loadList() await loadList()
} catch { } catch (e: unknown) {
message.error('اعمال تصمیم ناموفق بود') const data = (e as { response?: { data?: { message?: string } } })?.response?.data
message.error(data?.message || 'اعمال تصمیم ناموفق بود')
} finally { } finally {
decidingId.value = null decidingId.value = null
decidingMode.value = null decidingMode.value = null
@@ -884,7 +884,7 @@ const KEY_HELP_FALLBACK: Record<string, string> = {
montzar_open_sell: montzar_open_sell:
'وضعیت واقعی از سرویس خارجی خوانده می‌شود. روشن: ثبت سفارش فروش از طریق قیمت همکار مجاز است. خاموش: ثبت سفارش فروش از طریق قیمت همکار غیرفعال است.', 'وضعیت واقعی از سرویس خارجی خوانده می‌شود. روشن: ثبت سفارش فروش از طریق قیمت همکار مجاز است. خاموش: ثبت سفارش فروش از طریق قیمت همکار غیرفعال است.',
montzar_order_wait_callback: montzar_order_wait_callback:
'روشن (پیش‌فرض): بعد از ارسال سفارش به همکار، تا کالبک وضعیت (تأیید=۲ / رد=۴ یا ۶) یا استعلام مسیر وضعیت صبر می‌شود و کیف ثبت نمی‌شود. خاموش: مثل قبل با همان پاسخ HTTP همکار سفارش قطعی می‌شود.', 'با منبع قیمت همکار، سفارش همیشه تا کالبک یا استعلام وضعیت در انتظار می‌ماند و کیف بعد از تأیید ثبت می‌شود. خاموش بودن این سوییچ دیگر مسیر قطعی بلافاصله را باز نمی‌کند. در رد همکار، SMS به ادمین‌های دارای ارسال پیامک می‌رود.',
montzar_order_status_path: montzar_order_status_path:
'مسیر GET روی دامنه همکار (montzar_base_url) برای استعلام وضعیت اگر کالبک نرسید. پیش‌فرض /server/customer/order — با شماره سفارش همکار می‌شود /server/customer/order/40000.', 'مسیر GET روی دامنه همکار (montzar_base_url) برای استعلام وضعیت اگر کالبک نرسید. پیش‌فرض /server/customer/order — با شماره سفارش همکار می‌شود /server/customer/order/40000.',
montzar_closed: montzar_closed:
@@ -39,6 +39,7 @@
<TahesabMandeDecisionModal <TahesabMandeDecisionModal
v-model:visible="decisionVisible" v-model:visible="decisionVisible"
:source-label="provider === 'zarin' ? 'زرین' : 'ته‌حساب'" :source-label="provider === 'zarin' ? 'زرین' : 'ته‌حساب'"
:allow-push="provider === 'tahesab'"
:app-gold="decision?.app_gold" :app-gold="decision?.app_gold"
:app-cash="decision?.app_cash" :app-cash="decision?.app_cash"
:tahesab-gold="decision?.tahesab_gold ?? decision?.zarin_gold" :tahesab-gold="decision?.tahesab_gold ?? decision?.zarin_gold"
@@ -120,8 +121,12 @@ async function saveCode(customerId: number, body: Record<string, string>) {
close() close()
} }
async function applyWalletDecision(customerId: number, mode: 'overwrite' | 'keep') { async function applyWalletDecision(customerId: number, mode: 'overwrite' | 'keep' | 'push') {
if (props.provider === 'zarin') { if (props.provider === 'zarin') {
if (mode === 'push') {
message.warning('اعمال مانده اپ روی زرین در این نسخه پشتیبانی نمی‌شود')
return { ok: false, message: 'پشتیبانی نمی‌شود' }
}
return syncCustomerWalletFromZarin(customerId, { return syncCustomerWalletFromZarin(customerId, {
overwrite: mode === 'overwrite', overwrite: mode === 'overwrite',
keep: mode === 'keep', keep: mode === 'keep',
@@ -131,11 +136,12 @@ async function applyWalletDecision(customerId: number, mode: 'overwrite' | 'keep
return syncCustomerWalletFromTahesab(customerId, { return syncCustomerWalletFromTahesab(customerId, {
overwrite: mode === 'overwrite', overwrite: mode === 'overwrite',
keep: mode === 'keep', keep: mode === 'keep',
push_to_tahesab: mode === 'push',
ask_if_conflict: false, ask_if_conflict: false,
}) })
} }
async function onDecide(mode: 'overwrite' | 'keep') { async function onDecide(mode: 'overwrite' | 'keep' | 'push') {
const pending = pendingPayload.value const pending = pendingPayload.value
decisionVisible.value = false decisionVisible.value = false
if (!pending) return if (!pending) return
@@ -144,6 +150,7 @@ async function onDecide(mode: 'overwrite' | 'keep') {
await saveCode(pending.customerId, pending.body) await saveCode(pending.customerId, pending.body)
const res = await applyWalletDecision(pending.customerId, mode) const res = await applyWalletDecision(pending.customerId, mode)
if (mode === 'keep') message.info(res.message || 'موجودی اپ حفظ شد') if (mode === 'keep') message.info(res.message || 'موجودی اپ حفظ شد')
else if (mode === 'push') message.success(res.message || 'مانده اپ روی ته‌حساب اعمال شد')
else message.success(res.message || 'مانده حسابداری روی کیف اعمال شد') else message.success(res.message || 'مانده حسابداری روی کیف اعمال شد')
emit('success') emit('success')
} catch (e) { } catch (e) {
@@ -1,16 +1,24 @@
<template> <template>
<BasicModal <BasicModal
v-model:visible="visibleProxy" v-model:visible="visibleProxy"
:width="isMobile ? '92vw' : '36rem'" :width="isMobile ? '92vw' : '40rem'"
title="تصمیم برای مانده حساب" title="تصمیم برای مانده حساب"
:custom-footer="true" :custom-footer="true"
cancel-text="بعداً" cancel-text="بعداً"
@close="close" @close="close"
> >
<div class="flex flex-col gap-3 text-sm" style="color: var(--admin-text)"> <div class="flex flex-col gap-3 text-sm" style="color: var(--admin-text)">
<p class="m-0" style="color: var(--admin-text-secondary)"> <p class="m-0 leading-6" style="color: var(--admin-text-secondary)">
موجودی اپ با مانده {{ sourceLabel }} فرق دارد. دو مانده جمع نمی‌شوند؛ یکی را پس از بررسی سندها تأیید کنید. موجودی اپ با مانده {{ sourceLabel }} فرق دارد. دو مانده جمع نمی‌شوند — یکی از سه مسیر زیر را انتخاب کنید.
</p> </p>
<div
v-if="appIsEmpty && allowPush"
class="rounded-lg border border-amber-200 bg-amber-50 px-3 py-2 text-xs leading-5 text-amber-900"
>
موجودی اپ صفر است. اگر «اعمال مانده اپ روی ته‌حساب» را بزنید، مانده ته‌حساب با سند تعدیل هم‌تراز صفر اپ می‌شود.
</div>
<div class="rounded-lg border border-base p-3 space-y-2" style="background: var(--admin-bg-muted)"> <div class="rounded-lg border border-base p-3 space-y-2" style="background: var(--admin-bg-muted)">
<div class="flex justify-between gap-2"> <div class="flex justify-between gap-2">
<span style="color: var(--admin-text-secondary)">موجودی اپ (طلا)</span> <span style="color: var(--admin-text-secondary)">موجودی اپ (طلا)</span>
@@ -84,12 +92,58 @@
</div> </div>
<div class="flex flex-col gap-2"> <div class="flex flex-col gap-2">
<a-button type="primary" block :loading="loading === 'overwrite'" :disabled="!!loading" @click="choose('overwrite')"> <button
اعمال مانده {{ sourceLabel }} روی کیف type="button"
</a-button> class="mande-choice mande-choice--primary"
<a-button block :loading="loading === 'keep'" :disabled="!!loading" @click="choose('keep')"> :disabled="!!loading"
نگه داشتن موجودی فعلی اپ @click="choose('overwrite')"
</a-button> >
<span class="mande-choice__title">
<a-spin v-if="loading === 'overwrite'" size="small" class="me-1" />
اعمال مانده {{ sourceLabel }} روی کیف اپ
</span>
<span class="mande-choice__hint">
موجودی اپ مثل {{ sourceLabel }} می‌شود. سند تعدیل روی کیف اپ ثبت می‌شود.
</span>
</button>
<button
v-if="allowPush"
type="button"
class="mande-choice"
:class="appIsEmpty ? 'mande-choice--warn' : 'mande-choice--secondary'"
:disabled="!!loading"
@click="choose('push')"
>
<span class="mande-choice__title">
<a-spin v-if="loading === 'push'" size="small" class="me-1" />
اعمال مانده اپ روی {{ sourceLabel }}
<span v-if="appIsEmpty" class="mande-choice__badge">اپ صفر</span>
</span>
<span class="mande-choice__hint">
{{
appIsEmpty
? `مانده ${sourceLabel} با سند تعدیل هم‌تراز صفر اپ می‌شود. کیف اپ تغییر نمی‌کند.`
: `مانده ${sourceLabel} مثل موجودی اپ می‌شود. کیف اپ تغییر نمی‌کند.`
}}
</span>
</button>
<button
type="button"
class="mande-choice"
:disabled="!!loading"
@click="choose('keep')"
>
<span class="mande-choice__title">
<a-spin v-if="loading === 'keep'" size="small" class="me-1" />
نگه داشتن وضعیت فعلی
</span>
<span class="mande-choice__hint">
نه کیف اپ عوض می‌شود نه {{ sourceLabel }}؛ اختلاف برای بعد می‌ماند.
</span>
</button>
<a-button type="link" block :disabled="!!loading" @click="close">بعداً</a-button> <a-button type="link" block :disabled="!!loading" @click="close">بعداً</a-button>
</div> </div>
</div> </div>
@@ -103,27 +157,34 @@ import BasicModal from '@/components/BasicModal.vue'
import { isMobile } from '@core/utils/is' import { isMobile } from '@core/utils/is'
import type { TahesabPreviewDoc } from '@/api/tahesab' import type { TahesabPreviewDoc } from '@/api/tahesab'
const props = defineProps<{ export type MandeDecisionMode = 'overwrite' | 'keep' | 'push'
visible: boolean
appGold?: number | null const props = withDefaults(
appCash?: number | null defineProps<{
tahesabGold?: number | null visible: boolean
tahesabCash?: number | null appGold?: number | null
sourceGold?: number | null appCash?: number | null
sourceCash?: number | null tahesabGold?: number | null
goldDelta?: number | null tahesabCash?: number | null
rialDelta?: number | null sourceGold?: number | null
sourceLabel?: string sourceCash?: number | null
walletDocs?: TahesabPreviewDoc[] goldDelta?: number | null
tahesabDocs?: TahesabPreviewDoc[] rialDelta?: number | null
}>() sourceLabel?: string
/** فقط ته‌حساب: اجازهٔ نوشتن مانده اپ روی حسابداری */
allowPush?: boolean
walletDocs?: TahesabPreviewDoc[]
tahesabDocs?: TahesabPreviewDoc[]
}>(),
{ allowPush: false }
)
const emit = defineEmits<{ const emit = defineEmits<{
(e: 'update:visible', value: boolean): void (e: 'update:visible', value: boolean): void
(e: 'decide', mode: 'overwrite' | 'keep'): void (e: 'decide', mode: MandeDecisionMode): void
}>() }>()
const loading = ref<'overwrite' | 'keep' | null>(null) const loading = ref<MandeDecisionMode | null>(null)
const sourceLabel = computed(() => props.sourceLabel || 'ته‌حساب') const sourceLabel = computed(() => props.sourceLabel || 'ته‌حساب')
const sourceGoldValue = computed(() => props.sourceGold ?? props.tahesabGold) const sourceGoldValue = computed(() => props.sourceGold ?? props.tahesabGold)
const sourceCashValue = computed(() => props.sourceCash ?? props.tahesabCash) const sourceCashValue = computed(() => props.sourceCash ?? props.tahesabCash)
@@ -140,6 +201,11 @@ const sourceDocs = computed(() => props.tahesabDocs ?? [])
const showDocs = computed( const showDocs = computed(
() => sourceLabel.value === 'ته‌حساب' || walletDocs.value.length > 0 || sourceDocs.value.length > 0 () => sourceLabel.value === 'ته‌حساب' || walletDocs.value.length > 0 || sourceDocs.value.length > 0
) )
const appIsEmpty = computed(() => {
const g = Math.abs(Number(props.appGold ?? 0))
const c = Math.abs(Number(props.appCash ?? 0))
return g < 0.0005 && c < 1
})
const visibleProxy = computed({ const visibleProxy = computed({
get: () => props.visible, get: () => props.visible,
@@ -186,8 +252,75 @@ function close() {
visibleProxy.value = false visibleProxy.value = false
} }
function choose(mode: 'overwrite' | 'keep') { function choose(mode: MandeDecisionMode) {
loading.value = mode loading.value = mode
emit('decide', mode) emit('decide', mode)
} }
</script> </script>
<style scoped>
.mande-choice {
display: flex;
flex-direction: column;
align-items: stretch;
gap: 0.25rem;
width: 100%;
text-align: right;
border-radius: 0.75rem;
border: 1px solid var(--admin-border, #e5e7eb);
background: var(--admin-surface, #fff);
padding: 0.75rem 0.875rem;
cursor: pointer;
transition: border-color 0.15s ease, background 0.15s ease;
}
.mande-choice:disabled {
opacity: 0.65;
cursor: not-allowed;
}
.mande-choice:not(:disabled):hover {
border-color: var(--admin-primary, #10913a);
}
.mande-choice--primary {
border-color: var(--admin-primary, #10913a);
background: color-mix(in srgb, var(--admin-primary, #10913a) 8%, white);
}
.mande-choice--secondary:not(:disabled):hover {
background: var(--admin-bg-muted, #f8fafc);
}
.mande-choice--warn {
border-color: #f59e0b;
background: #fffbeb;
}
.mande-choice__title {
display: flex;
flex-wrap: wrap;
align-items: center;
gap: 0.35rem;
font-size: 0.875rem;
font-weight: 700;
color: var(--admin-text, #111827);
}
.mande-choice__hint {
font-size: 0.75rem;
line-height: 1.5;
color: var(--admin-text-secondary, #6b7280);
}
.mande-choice__badge {
display: inline-flex;
align-items: center;
border-radius: 999px;
background: #fef3c7;
color: #92400e;
font-size: 0.6875rem;
font-weight: 700;
padding: 0.1rem 0.45rem;
}
</style>
+20 -5
View File
@@ -308,6 +308,7 @@
<TahesabMandeDecisionModal <TahesabMandeDecisionModal
v-model:visible="tahesabDecisionVisible" v-model:visible="tahesabDecisionVisible"
:source-label="walletDecisionLabel" :source-label="walletDecisionLabel"
:allow-push="walletDecisionProvider === 'tahesab'"
:app-gold="tahesabDecision?.app_gold" :app-gold="tahesabDecision?.app_gold"
:app-cash="tahesabDecision?.app_cash" :app-cash="tahesabDecision?.app_cash"
:tahesab-gold="tahesabDecision?.tahesab_gold ?? tahesabDecision?.zarin_gold" :tahesab-gold="tahesabDecision?.tahesab_gold ?? tahesabDecision?.zarin_gold"
@@ -855,7 +856,7 @@ function openTahesabDecision(result?: TahesabWalletSyncResult['result'], provide
tahesabDecisionVisible.value = true tahesabDecisionVisible.value = true
} }
async function syncTahesabWallet(mode: 'ask' | 'overwrite' | 'keep' = 'ask') { async function syncTahesabWallet(mode: 'ask' | 'overwrite' | 'keep' | 'push' = 'ask') {
if (!userInfo.value?.id || !tahesabWalletCanSync.value || tahesabSyncLoading.value) return if (!userInfo.value?.id || !tahesabWalletCanSync.value || tahesabSyncLoading.value) return
tahesabSyncLoading.value = true tahesabSyncLoading.value = true
try { try {
@@ -877,6 +878,7 @@ async function syncTahesabWallet(mode: 'ask' | 'overwrite' | 'keep' = 'ask') {
ask_if_conflict: false, ask_if_conflict: false,
overwrite: mode === 'overwrite', overwrite: mode === 'overwrite',
keep: mode === 'keep', keep: mode === 'keep',
push_to_tahesab: mode === 'push',
}) })
if (res.needs_decision || res.result?.needs_decision) { if (res.needs_decision || res.result?.needs_decision) {
@@ -885,7 +887,14 @@ async function syncTahesabWallet(mode: 'ask' | 'overwrite' | 'keep' = 'ask') {
} }
if (res.result?.applied || res.ok) { if (res.result?.applied || res.ok) {
message.success(res.message || 'مانده از ته‌حساب روی کیف اعمال شد') message.success(
res.message ||
(mode === 'push'
? 'مانده اپ روی ته‌حساب اعمال شد'
: mode === 'keep'
? 'موجودی اپ حفظ شد'
: 'مانده از ته‌حساب روی کیف اعمال شد')
)
} else { } else {
message.info(res.message || 'تغییری برای اعمال نبود') message.info(res.message || 'تغییری برای اعمال نبود')
} }
@@ -902,18 +911,24 @@ async function syncTahesabWallet(mode: 'ask' | 'overwrite' | 'keep' = 'ask') {
refreshTable() refreshTable()
if (data?.result?.applied || data?.ok) { if (data?.result?.applied || data?.ok) {
message.success(data?.message || 'مانده از ته‌حساب روی کیف اعمال شد') message.success(data?.message || 'مانده با ته‌حساب هم‌تراز شد')
} else if (status !== 422) { } else if (status !== 422) {
message.warning(data?.message || 'اعمال مانده از ته‌حساب ناموفق بود') message.warning(data?.message || 'اعمال مانده با ته‌حساب ناموفق بود')
} else if (data?.message) {
message.warning(data.message)
} }
} finally { } finally {
tahesabSyncLoading.value = false tahesabSyncLoading.value = false
} }
} }
async function onTahesabMandeDecide(mode: 'overwrite' | 'keep') { async function onTahesabMandeDecide(mode: 'overwrite' | 'keep' | 'push') {
tahesabDecisionVisible.value = false tahesabDecisionVisible.value = false
if (walletDecisionProvider.value === 'zarin') { if (walletDecisionProvider.value === 'zarin') {
if (mode === 'push') {
message.warning('اعمال مانده اپ روی زرین در این نسخه پشتیبانی نمی‌شود')
return
}
await syncZarinWallet(mode) await syncZarinWallet(mode)
return return
} }