diff --git a/apps/mini-user/src/lib/datetime.ts b/apps/mini-user/src/lib/datetime.ts new file mode 100644 index 0000000..dbc16b7 --- /dev/null +++ b/apps/mini-user/src/lib/datetime.ts @@ -0,0 +1,16 @@ +/** 格式化为 Asia/Shanghai:2026-08-03 15:14:30(不依赖 Intl,兼容微信小程序) */ +export function formatShanghaiDateTime(input?: string | Date | null): string { + if (input == null || input === '') return '—'; + if (typeof input === 'string') { + const s = input.trim(); + if (/^\d{4}-\d{2}-\d{2}[ T]\d{2}:\d{2}/.test(s)) { + return s.slice(0, 19).replace('T', ' '); + } + } + const d = input instanceof Date ? input : new Date(input); + if (Number.isNaN(d.getTime())) return '—'; + // 用 UTC 读数 + 固定东八区偏移,避免依赖 Intl / 设备时区 API 差异 + const sh = new Date(d.getTime() + 8 * 60 * 60 * 1000); + const p = (n: number) => String(n).padStart(2, '0'); + return `${sh.getUTCFullYear()}-${p(sh.getUTCMonth() + 1)}-${p(sh.getUTCDate())} ${p(sh.getUTCHours())}:${p(sh.getUTCMinutes())}:${p(sh.getUTCSeconds())}`; +} diff --git a/apps/mini-user/src/pages/redeem-success/index.tsx b/apps/mini-user/src/pages/redeem-success/index.tsx index 54a41a2..bcf392f 100644 --- a/apps/mini-user/src/pages/redeem-success/index.tsx +++ b/apps/mini-user/src/pages/redeem-success/index.tsx @@ -4,6 +4,7 @@ import Taro, { useRouter } from '@tarojs/taro'; import PageShell from '../../components/PageShell'; import SubPageHeader from '../../components/SubPageHeader'; import { request, toast } from '../../lib/api'; +import { formatShanghaiDateTime } from '../../lib/datetime'; const LAST_REDEEM_RESULT_KEY = 'lastRedeemResult'; @@ -17,26 +18,17 @@ type RedeemRecord = { }; function formatMoney(amount: number) { - return amount.toLocaleString('zh-CN', { minimumFractionDigits: 2, maximumFractionDigits: 2 }); + const n = Number(amount); + if (!Number.isFinite(n)) return '0.00'; + const fixed = n.toFixed(2); + const [intPart, dec] = fixed.split('.'); + const withComma = intPart.replace(/\B(?=(\d{3})+(?!\d))/g, ','); + return `${withComma}.${dec}`; } /** 与权益「历史记录」一致:2026-08-03 13:53:03(Asia/Shanghai) */ function formatChinaDateTime(input?: string | null) { - const d = input ? new Date(input) : new Date(); - if (Number.isNaN(d.getTime())) return '—'; - const parts = new Intl.DateTimeFormat('en-CA', { - timeZone: 'Asia/Shanghai', - year: 'numeric', - month: '2-digit', - day: '2-digit', - hour: '2-digit', - minute: '2-digit', - second: '2-digit', - hour12: false, - }).formatToParts(d); - const get = (type: Intl.DateTimeFormatPartTypes) => - parts.find((p) => p.type === type)?.value ?? ''; - return `${get('year')}-${get('month')}-${get('day')} ${get('hour')}:${get('minute')}:${get('second')}`; + return formatShanghaiDateTime(input ?? new Date()); } function StarRating({ diff --git a/apps/mini-user/src/pages/store-detail/index.tsx b/apps/mini-user/src/pages/store-detail/index.tsx index 6926edd..2aea632 100644 --- a/apps/mini-user/src/pages/store-detail/index.tsx +++ b/apps/mini-user/src/pages/store-detail/index.tsx @@ -15,6 +15,7 @@ import ShareNavButton from '../../components/ShareNavButton'; import StoreRedeemMarquee from '../../components/StoreRedeemMarquee'; import WechatShareReady from '../../components/WechatShareReady'; import { request, toast } from '../../lib/api'; +import { formatShanghaiDateTime } from '../../lib/datetime'; import { DEFAULT_SHARE_DESC, DEFAULT_SHARE_TITLE, @@ -91,26 +92,7 @@ function pickStoreId(raw?: string | null) { /** 与历史记录一致:2026-08-03 15:14:30(Asia/Shanghai) */ function formatRedeemTime(input?: string | null) { - const d = input ? new Date(input) : new Date(); - if (Number.isNaN(d.getTime())) { - // 后端若已是 "2026-08-03 15:14:30" 直接展示 - const s = String(input || '').trim(); - if (/^\d{4}-\d{2}-\d{2}/.test(s)) return s.slice(0, 19).replace('T', ' '); - return '—'; - } - const parts = new Intl.DateTimeFormat('en-CA', { - timeZone: 'Asia/Shanghai', - year: 'numeric', - month: '2-digit', - day: '2-digit', - hour: '2-digit', - minute: '2-digit', - second: '2-digit', - hour12: false, - }).formatToParts(d); - const get = (type: Intl.DateTimeFormatPartTypes) => - parts.find((p) => p.type === type)?.value ?? ''; - return `${get('year')}-${get('month')}-${get('day')} ${get('hour')}:${get('minute')}:${get('second')}`; + return formatShanghaiDateTime(input); } function formatRedeemAmountYuan(amount: number | string) {