Files
2026-08-02 22:32:08 +03:30

101 lines
3.5 KiB
TypeScript
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { User } from "@/types/user";
import { Purchase } from "@/types/purchase";
// Single source of truth for product type labels lives in types/product.ts
// (kept in sync with the backend Product::TYPES). Re-exported here so existing
// `@/lib/utils` imports keep working without a divergent (previously wrong) map.
export { getProductTypeLabel } from "@/types/product";
// قیمت نهایی خرید — shared between purchases table and accounting page.
// اگر محصول تخفیف داشته باشد قیمت تخفیف‌خورده، در غیر این صورت قیمت اصلی، و در نهایت مبلغ تراکنش.
export const getPurchaseFinalPrice = (purchase: Purchase): number => {
const product = purchase.product;
// اگر محصول تخفیف دارد، قیمت نهایی همان قیمت تخفیف‌خورده است
const discountedPrice = product?.discounted_price;
if (discountedPrice) {
const parsed = parseInt(discountedPrice.replace(/[^\d]/g, ''), 10);
if (!Number.isNaN(parsed) && parsed > 0) return parsed;
}
// بدون تخفیف → قیمت اصلی محصول
if (product?.price) return product.price;
// برگشت به مبلغ ثبت‌شدهٔ تراکنش وقتی محصول در دسترس نیست
return purchase.amount || 0;
};
// Parse a percentage input (e.g. "۱۵%" / "15") and clamp to 0100.
export const parseStoreRate = (value: string | number): number => {
if (value === null || value === undefined || value === '') return 0;
const str = String(value).replace(/[^\d]/g, '');
if (!str) return 0;
const n = parseInt(str, 10);
if (Number.isNaN(n)) return 0;
return Math.min(100, Math.max(0, n));
};
// Parse a non-negative integer input (e.g. transaction fee in Rial).
export const parseFee = (value: string | number): number => {
if (value === null || value === undefined || value === '') return 0;
const str = String(value).replace(/[^\d]/g, '');
if (!str) return 0;
const n = parseInt(str, 10);
if (Number.isNaN(n)) return 0;
return Math.max(0, n);
};
export const formatDate = (dateString: string | null): string => {
if (!dateString) return 'نامشخص';
try {
const date = new Date(dateString);
return new Intl.DateTimeFormat('fa-IR', {
year: 'numeric',
month: 'long',
day: 'numeric',
}).format(date);
} catch {
return 'نامشخص';
}
};
export const formatPrice = (price: number | null): string => {
if (price === null || price === undefined) return '0';
return new Intl.NumberFormat('fa-IR').format(price);
};
export const getFullName = (user: User): string => {
if (user.full_name) return user.full_name;
const firstName = user.first_name || '';
const lastName = user.last_name || '';
if (firstName || lastName) {
return `${firstName} ${lastName}`.trim();
}
return 'نامشخص';
};
export const getEmail = (email: string | null): string => {
return email || 'ایمیل ثبت نشده';
};
export const getMobile = (mobile: string | null): string => {
return mobile || 'شماره موبایل ثبت نشده';
};
export const formatTime = (dateString: string | null): string => {
if (!dateString) return '';
try {
const date = new Date(dateString);
return new Intl.DateTimeFormat('fa-IR', {
hour: '2-digit',
minute: '2-digit',
}).format(date);
} catch {
return '';
}
};