From 2c67c2b23b271eaab2b5e52409c7457cf335a229 Mon Sep 17 00:00:00 2001 From: Denis Shatskiy Date: Tue, 5 Aug 2025 23:40:06 +0700 Subject: [PATCH] feat: Add payment history section to BillingManager, update form labels to Russian, and remove country flag display for improved clarity --- frontend/src/BillingManager.jsx | 129 +++++++++++++++++++++++--------- 1 file changed, 93 insertions(+), 36 deletions(-) diff --git a/frontend/src/BillingManager.jsx b/frontend/src/BillingManager.jsx index 6cf6718..4f8d075 100644 --- a/frontend/src/BillingManager.jsx +++ b/frontend/src/BillingManager.jsx @@ -17,7 +17,8 @@ import { IconDownload, IconUpload, IconEye, - IconEyeOff + IconEyeOff, + IconHistory } from '@tabler/icons-react'; const API_URL = '/api'; @@ -166,7 +167,7 @@ function BillingManager() { const handleAddSubmit = () => { if (!newItem.hostName || !newItem.country || !newItem.provider) { - setError('Пожалуйста, заполните обязательные поля: Host Name, Country, Provider'); + setError('Пожалуйста, заполните обязательные поля: Имя хоста, Страна, Провайдер'); return; } @@ -180,7 +181,7 @@ function BillingManager() { const handleEditSubmit = () => { if (!editingItem.hostName || !editingItem.country || !editingItem.provider) { - setError('Пожалуйста, заполните обязательные поля: Host Name, Country, Provider'); + setError('Пожалуйста, заполните обязательные поля: Имя хоста, Страна, Провайдер'); return; } @@ -249,15 +250,6 @@ function BillingManager() { const uniqueCountries = [...new Set(billingData.map(item => item.country).filter(Boolean))]; const uniqueStatuses = [...new Set(billingData.map(item => item.status).filter(Boolean))]; - function countryToFlag(isoCode) { - if (!isoCode) return '🌍'; - const codePoints = isoCode - .toUpperCase() - .split('') - .map(char => 127397 + char.charCodeAt()); - return String.fromCodePoint(...codePoints); - } - function formatDate(dateString) { if (!dateString) return 'Не указано'; try { @@ -428,7 +420,7 @@ function BillingManager() { > {uniqueCountries.map(country => ( - + ))} @@ -615,9 +607,6 @@ function BillingManager() {
- - {countryToFlag(item.country)} -
{item.hostName}
{item.loginUrl && ( @@ -638,7 +627,6 @@ function BillingManager() {
- {countryToFlag(item.country)} {item.country}
@@ -743,6 +731,71 @@ function BillingManager() {
+ {/* История платежей */} +
+
+

+ + История платежей +

+
+
+
+ + + + + + + + + + + + {billingData + .filter(item => item.lastPaymentDate && item.lastPaymentAmount) + .sort((a, b) => new Date(b.lastPaymentDate) - new Date(a.lastPaymentDate)) + .slice(0, 10) + .map(item => ( + + + + + + + + ))} + {billingData.filter(item => item.lastPaymentDate && item.lastPaymentAmount).length === 0 && ( + + + + )} + +
Имя хостераДата платежаСуммаВалютаСтатус
+
{item.hostName}
+
{item.provider}
+
{formatDate(item.lastPaymentDate)} +
+ {formatCurrency(item.lastPaymentAmount, item.lastPaymentCurrency)} +
+
+ {formatCurrencyInRUB(item.lastPaymentAmount, item.lastPaymentCurrency)} +
+
+ + {item.lastPaymentCurrency || 'USD'} + + + + Оплачен + +
+ История платежей пуста +
+
+
+
+ {/* Модальные окна */} +
@@ -785,7 +838,7 @@ function AddBillingModal({ show, item, onItemChange, onSubmit, onClose }) {
- +
- +
- +
- + onItemChange({ ...item, loginUrl: e.target.value })} + placeholder="example.com" />
- + onItemChange({ ...item, monthlyCost: parseFloat(e.target.value) || 0 })} />
- +
- +
- +
- +
- + onItemChange({ ...item, loginUrl: e.target.value })} + placeholder="example.com" />
- + onItemChange({ ...item, monthlyCost: parseFloat(e.target.value) || 0 })} />
- +
- +