From 0de0ad9e9d4fbf1d2c6ef16de6eac0cd3852ee3d Mon Sep 17 00:00:00 2001 From: yml2213 Date: Thu, 30 Jul 2026 14:30:34 +0800 Subject: [PATCH] =?UTF-8?q?=E8=B4=A7=E5=B8=81=E4=BD=93=E7=B3=BB:=20?= =?UTF-8?q?=E5=85=A8=E5=B9=B3=E5=8F=B0=E7=BB=9F=E4=B8=80=E4=BD=BF=E7=94=A8?= =?UTF-8?q?=E7=A7=AF=E5=88=86(POINT)=E6=9B=BF=E4=BB=A3=E4=BA=BA=E6=B0=91?= =?UTF-8?q?=E5=B8=81(CNY)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 后端: - 模型 currency 默认值 CNY→POINT (MerchantProduct/WalletAccount/FulfillmentOrder) - DashboardStats TotalSales/TotalFees 从 float64 改为 int64,去掉 /100.0 转换 - 上游 OpenOrderQuery.Amount 从 float64 改为 int64,直接返回积分整数 - 钱包/商品创建时 currency 默认 POINT 前端: - 去掉 centsToYuan/yuanToCents 转换函数,金额直接用整数积分 - money() 显示从 ¥X.XX 改为 X 积分 - 商品售价/成本表单字段名改回 price_amount/cost_amount,precision 改 0 - 钱包调整表单 amount_yuan→amount,precision 改 0 - 手续费固定金额表单 precision 改 0,label 改积分 - 币种选项 CNY→POINT - Dashboard 成交金额/手续费 suffix 元→积分,去掉 precision 数据库: - 新增迁移 004: currency 默认值 CNY→POINT,存量数据更新 --- backend/internal/database/migrate.go | 2 +- .../migrations/004_currency_point.sql | 7 ++++ backend/internal/model/merchant.go | 6 +-- backend/internal/service/fulfillment.go | 20 +++++----- backend/internal/service/fulfillment_test.go | 4 +- backend/internal/service/merchant.go | 4 +- frontend/src/pages/Dashboard.tsx | 8 ++-- frontend/src/pages/MerchantCenter.tsx | 40 ++++++------------- frontend/src/pages/PlatformMerchants.tsx | 30 +++++--------- 9 files changed, 52 insertions(+), 69 deletions(-) create mode 100644 backend/internal/database/migrations/004_currency_point.sql diff --git a/backend/internal/database/migrate.go b/backend/internal/database/migrate.go index fc4c1d5..2d242a1 100644 --- a/backend/internal/database/migrate.go +++ b/backend/internal/database/migrate.go @@ -163,6 +163,6 @@ func ensureSelfMerchant(tx *gorm.DB) (*model.Merchant, error) { func ensureWallet(tx *gorm.DB, merchantID uint) error { return tx.Clauses(clause.OnConflict{DoNothing: true}).Create(&model.WalletAccount{ MerchantID: merchantID, - Currency: "CNY", + Currency: "POINT", }).Error } diff --git a/backend/internal/database/migrations/004_currency_point.sql b/backend/internal/database/migrations/004_currency_point.sql new file mode 100644 index 0000000..8b0a28e --- /dev/null +++ b/backend/internal/database/migrations/004_currency_point.sql @@ -0,0 +1,7 @@ +-- 全平台统一使用积分(POINT)作为结算货币,不再使用人民币(CNY)。 +ALTER TABLE merchant_products ALTER COLUMN currency SET DEFAULT 'POINT'; +ALTER TABLE wallet_accounts ALTER COLUMN currency SET DEFAULT 'POINT'; +ALTER TABLE fulfillment_orders ALTER COLUMN currency SET DEFAULT 'POINT'; +UPDATE merchant_products SET currency = 'POINT' WHERE currency = 'CNY'; +UPDATE wallet_accounts SET currency = 'POINT' WHERE currency = 'CNY'; +UPDATE fulfillment_orders SET currency = 'POINT' WHERE currency = 'CNY'; diff --git a/backend/internal/model/merchant.go b/backend/internal/model/merchant.go index d152081..4278433 100644 --- a/backend/internal/model/merchant.go +++ b/backend/internal/model/merchant.go @@ -155,7 +155,7 @@ type MerchantProduct struct { DisplayName string `gorm:"size:160" json:"display_name"` PriceAmount int64 `gorm:"not null;default:0" json:"price_amount"` CostAmount int64 `gorm:"not null;default:0" json:"cost_amount"` - Currency string `gorm:"size:12;not null;default:CNY" json:"currency"` + Currency string `gorm:"size:12;not null;default:POINT" json:"currency"` Stock int64 `gorm:"not null;default:-1" json:"stock"` Status string `gorm:"size:16;not null;default:active;index" json:"status"` FulfillmentConfig string `gorm:"type:text" json:"fulfillment_config"` @@ -170,7 +170,7 @@ type WalletAccount struct { CreatedAt time.Time `json:"created_at"` UpdatedAt time.Time `json:"updated_at"` MerchantID uint `gorm:"not null;uniqueIndex" json:"merchant_id"` - Currency string `gorm:"size:12;not null;default:CNY" json:"currency"` + Currency string `gorm:"size:12;not null;default:POINT" json:"currency"` AvailableBalance int64 `gorm:"not null;default:0" json:"available_balance"` FrozenBalance int64 `gorm:"not null;default:0" json:"frozen_balance"` } @@ -211,7 +211,7 @@ type FulfillmentOrder struct { FeeFixedAmount int64 `gorm:"not null;default:0" json:"fee_fixed_amount"` ServiceFeeAmount int64 `gorm:"not null;default:0" json:"service_fee_amount"` Amount int64 `gorm:"not null" json:"amount"` - Currency string `gorm:"size:12;not null;default:CNY" json:"currency"` + Currency string `gorm:"size:12;not null;default:POINT" json:"currency"` PaymentStatus string `gorm:"size:16;not null;default:pending;index" json:"payment_status"` FulfillmentStatus string `gorm:"size:16;not null;default:pending;index" json:"fulfillment_status"` BuyerReference string `gorm:"size:128" json:"buyer_reference"` diff --git a/backend/internal/service/fulfillment.go b/backend/internal/service/fulfillment.go index d24670c..434b80b 100644 --- a/backend/internal/service/fulfillment.go +++ b/backend/internal/service/fulfillment.go @@ -581,12 +581,12 @@ func orderCallbackData(order *model.FulfillmentOrder) map[string]interface{} { // DashboardStats 仪表盘聚合指标。 type DashboardStats struct { - ProductCount int64 `json:"product_count"` - MerchantCount int64 `json:"merchant_count"` - OrderCount int64 `json:"order_count"` - TotalSales float64 `json:"total_sales"` - TotalFees float64 `json:"total_fees"` - PendingOrderCount int64 `json:"pending_order_count"` + ProductCount int64 `json:"product_count"` + MerchantCount int64 `json:"merchant_count"` + OrderCount int64 `json:"order_count"` + TotalSales int64 `json:"total_sales"` + TotalFees int64 `json:"total_fees"` + PendingOrderCount int64 `json:"pending_order_count"` } // Dashboard 汇总商户维度的商品、商户、订单与金额统计。 @@ -605,11 +605,11 @@ func (s *FulfillmentService) Dashboard(merchantID uint, isPlatformAdmin bool) (* s.db.Model(&model.FulfillmentOrder{}). Where("merchant_id = ?", merchantID). Where("payment_status = ?", model.PaymentStatusPaid). - Select("COALESCE(SUM(amount),0) / 100.0").Scan(&stats.TotalSales) + Select("COALESCE(SUM(amount),0)").Scan(&stats.TotalSales) s.db.Model(&model.FulfillmentOrder{}). Where("merchant_id = ?", merchantID). Where("payment_status = ?", model.PaymentStatusPaid). - Select("COALESCE(SUM(service_fee_amount),0) / 100.0").Scan(&stats.TotalFees) + Select("COALESCE(SUM(service_fee_amount),0)").Scan(&stats.TotalFees) return stats, nil } @@ -623,7 +623,7 @@ type OpenOrderQuery struct { CannotShipReason string `json:"cannot_ship_reason,omitempty"` Product *OpenOrderProduct `json:"product,omitempty"` BuyerName string `json:"buyer_name"` - Amount float64 `json:"amount"` + Amount int64 `json:"amount"` ProviderOrderNo string `json:"provider_order_no,omitempty"` CreatedAt time.Time `json:"created_at"` ShippedAt *time.Time `json:"shipped_at"` @@ -691,7 +691,7 @@ func (s *FulfillmentService) QueryOpenOrder(orderNo string) (*OpenOrderQuery, er CanShip: canShip, CannotShipReason: reason, BuyerName: order.BuyerReference, - Amount: float64(order.Amount) / 100.0, + Amount: order.Amount, ProviderOrderNo: order.ProviderOrderNo, CreatedAt: order.CreatedAt, ShippedAt: order.DeliveredAt, diff --git a/backend/internal/service/fulfillment_test.go b/backend/internal/service/fulfillment_test.go index 8cca1dc..a774337 100644 --- a/backend/internal/service/fulfillment_test.go +++ b/backend/internal/service/fulfillment_test.go @@ -32,7 +32,7 @@ func seedFulfillmentMerchant(t *testing.T, db *gorm.DB, code string, balance, st } if err := db.Create(&model.WalletAccount{ MerchantID: merchant.ID, - Currency: "CNY", + Currency: "POINT", AvailableBalance: balance, }).Error; err != nil { t.Fatalf("create wallet: %v", err) @@ -47,7 +47,7 @@ func seedFulfillmentMerchant(t *testing.T, db *gorm.DB, code string, balance, st SKU: "sku-basic", DisplayName: "测试商品", PriceAmount: price, - Currency: "CNY", + Currency: "POINT", Stock: stock, Status: model.ProductStatusActive, } diff --git a/backend/internal/service/merchant.go b/backend/internal/service/merchant.go index c59e4d6..1b7cc07 100644 --- a/backend/internal/service/merchant.go +++ b/backend/internal/service/merchant.go @@ -91,7 +91,7 @@ func (s *MerchantService) CreateMerchant(in CreateMerchantInput, actorUserID uin if err := tx.Create(merchant).Error; err != nil { return err } - if err := tx.Create(&model.WalletAccount{MerchantID: merchant.ID, Currency: "CNY"}).Error; err != nil { + if err := tx.Create(&model.WalletAccount{MerchantID: merchant.ID, Currency: "POINT"}).Error; err != nil { return err } if err := tx.Create(&model.MerchantMember{ @@ -332,7 +332,7 @@ func (s *MerchantService) CreateMerchantProduct(merchantID uint, in CreateMercha return nil, errors.New("库存只能为 -1 或非负整数") } if in.Currency == "" { - in.Currency = "CNY" + in.Currency = "POINT" } in.Currency = strings.ToUpper(in.Currency) if in.Status == "" { diff --git a/frontend/src/pages/Dashboard.tsx b/frontend/src/pages/Dashboard.tsx index 12b0839..ccc358a 100644 --- a/frontend/src/pages/Dashboard.tsx +++ b/frontend/src/pages/Dashboard.tsx @@ -54,11 +54,10 @@ export default function Dashboard() { } - suffix="元" + suffix="积分" /> @@ -67,9 +66,8 @@ export default function Dashboard() { } - suffix="元" + suffix="积分" /> diff --git a/frontend/src/pages/MerchantCenter.tsx b/frontend/src/pages/MerchantCenter.tsx index a14460a..e1c8b25 100644 --- a/frontend/src/pages/MerchantCenter.tsx +++ b/frontend/src/pages/MerchantCenter.tsx @@ -212,11 +212,11 @@ export default function MerchantCenter() { setEditingProduct(null) productForm.resetFields() productForm.setFieldsValue({ - currency: 'CNY', + currency: 'POINT', stock: -1, status: 'active', - price_yuan: 0, - cost_yuan: 0, + price_amount: 0, + cost_amount: 0, }) setProductOpen(true) } @@ -225,8 +225,6 @@ export default function MerchantCenter() { setEditingProduct(record) productForm.setFieldsValue({ ...record, - price_yuan: centsToYuan(record.price_amount), - cost_yuan: centsToYuan(record.cost_amount), }) setProductOpen(true) } @@ -236,11 +234,7 @@ export default function MerchantCenter() { try { const payload = { ...values, - price_amount: yuanToCents(values.price_yuan), - cost_amount: yuanToCents(values.cost_yuan), } - delete payload.price_yuan - delete payload.cost_yuan if (editingProduct) { await merchantApi.updateProduct(editingProduct.id, payload) message.success('商品已更新') @@ -259,7 +253,7 @@ export default function MerchantCenter() { const values = await walletForm.validateFields() try { const walletData = await merchantApi.adjustWallet({ - amount: yuanToCents(values.amount_yuan), + amount: values.amount, idempotency_key: values.idempotency_key, note: values.note, }) @@ -497,7 +491,7 @@ export default function MerchantCenter() { {money(wallet?.available_balance ?? 0)} {money(wallet?.frozen_balance ?? 0)} - {wallet?.currency || 'CNY'} + {wallet?.currency || 'POINT'} {canFinance && (