151 lines
4.2 KiB
TypeScript
151 lines
4.2 KiB
TypeScript
function formatGroupedPrice(price: string | number | null | undefined, digit: boolean) {
|
|
let value = price === null || price === undefined ? '' : String(price)
|
|
if (digit) {
|
|
value = value.replace(/\B(?=(\d{3})+(?!\d))/g, ',')
|
|
}
|
|
return value
|
|
}
|
|
|
|
/** مبلغ ریالی — بدون اعشار، گرد به بالا */
|
|
export function ceilRial(price?: number | string | null): number {
|
|
const num = Number(price ?? 0)
|
|
if (!Number.isFinite(num)) {
|
|
return 0
|
|
}
|
|
|
|
return Math.ceil(num)
|
|
}
|
|
|
|
export function formatNumber(value: string | number | null | undefined, grouped = false): string {
|
|
return formatGroupedPrice(value, grouped)
|
|
}
|
|
|
|
export function usePrice(price: number, digit = true, unit = 'ریال') {
|
|
const formatted = formatGroupedPrice(ceilRial(price), digit)
|
|
return `${formatted} ${unit}`
|
|
}
|
|
|
|
export function usePriceWithoutType(price?: number, digit = true) {
|
|
return formatGroupedPrice(ceilRial(price), digit)
|
|
}
|
|
|
|
export function useTowDecimal(num: string | number): string | number {
|
|
const temp = num.toString().match(/^-?\d+(?:\.\d{0,2})?/)
|
|
if (temp && temp.length > 0) return formatGroupedPrice(temp[0], false)
|
|
return formatGroupedPrice(Math.round(+num * 100) / 100, false)
|
|
}
|
|
|
|
export function formatSignedPercentChange(value: number): string {
|
|
if (!value) return '0%'
|
|
|
|
const formatted = useTowDecimal(Math.abs(value))
|
|
const prefix = value > 0 ? '+' : '-'
|
|
return `${prefix}${formatted}%`
|
|
}
|
|
|
|
export function useFormat(num: string | number, unit = '') {
|
|
return usePrice(Math.abs(+useTowDecimal(num)), true, unit)
|
|
}
|
|
|
|
type TransactionPriceSource = {
|
|
cash?: number | null
|
|
gold?: number | null
|
|
order?: {
|
|
price?: number | null
|
|
total_price?: number | null
|
|
amount?: number | null
|
|
sts?: number | null
|
|
sts_str?: string | number | null
|
|
payment_sts?: number | null
|
|
} | null
|
|
withdraw?: {
|
|
sts?: number | null
|
|
sts_str?: string | number | null
|
|
} | null
|
|
order_id?: number | null
|
|
}
|
|
|
|
const ORDER_STATUS_LABELS: Record<number, string> = {
|
|
1: 'باز',
|
|
2: 'موفق',
|
|
3: 'ناموفق',
|
|
}
|
|
|
|
export function getTransactionTradePrice(item: TransactionPriceSource): number {
|
|
const orderPrice = Number(item.order?.price)
|
|
if (Number.isFinite(orderPrice) && orderPrice > 0) {
|
|
return Math.round(orderPrice)
|
|
}
|
|
|
|
const cashAmount = Math.abs(Number(item.cash) || 0)
|
|
const goldAmount =
|
|
Math.abs(Number(item.gold) || 0) || Math.abs(Number(item.order?.amount) || 0)
|
|
|
|
if (goldAmount > 0 && cashAmount > 0) {
|
|
return Math.round(cashAmount / goldAmount)
|
|
}
|
|
|
|
const totalPrice = Number(item.order?.total_price)
|
|
if (Number.isFinite(totalPrice) && totalPrice > 0) {
|
|
return Math.round(totalPrice)
|
|
}
|
|
|
|
return 0
|
|
}
|
|
|
|
export function resolveTransactionStatusLabel(item?: TransactionPriceSource | null): string {
|
|
if (!item) return ''
|
|
|
|
const raw = item.order?.sts_str ?? item.withdraw?.sts_str
|
|
if (typeof raw === 'string') {
|
|
const trimmed = raw.trim()
|
|
if (trimmed && trimmed !== 'بدون مقدار') {
|
|
return trimmed
|
|
}
|
|
}
|
|
|
|
if (typeof raw === 'number' || (typeof raw === 'string' && /^\d+$/.test(String(raw).trim()))) {
|
|
const mapped = ORDER_STATUS_LABELS[Number(raw)]
|
|
if (mapped) return mapped
|
|
}
|
|
|
|
const sts = item.order?.sts ?? item.withdraw?.sts
|
|
if (sts != null && ORDER_STATUS_LABELS[Number(sts)]) {
|
|
return ORDER_STATUS_LABELS[Number(sts)]
|
|
}
|
|
|
|
if (item.order_id && Number(item.order?.payment_sts) === 4) {
|
|
return 'موفق'
|
|
}
|
|
|
|
return ''
|
|
}
|
|
|
|
export function getTransactionGoldAmount(item: TransactionPriceSource): number {
|
|
const gold = Number(item.gold) || 0
|
|
if (Math.abs(gold) > 0) {
|
|
return gold
|
|
}
|
|
|
|
const orderAmount = Number(item.order?.amount) || 0
|
|
if (orderAmount > 0) {
|
|
const cash = Number(item.cash) || 0
|
|
if (cash < 0) return orderAmount
|
|
if (cash > 0) return -orderAmount
|
|
return orderAmount
|
|
}
|
|
|
|
return gold
|
|
}
|
|
|
|
export function formatGoldAmount(amount?: number | null): string {
|
|
const num = Number(amount)
|
|
if (!Number.isFinite(num)) return '0'
|
|
return formatGroupedPrice(Number(num.toFixed(3)), false)
|
|
}
|
|
|
|
/** وزن فلز (گرم/کیلو) — بدون گرد کردن به بالا (برخلاف usePriceWithoutType) */
|
|
export function formatWeightAmount(amount?: number | null): string {
|
|
return formatGoldAmount(amount)
|
|
}
|