From 28d0b81c5a70bf5764290fdced928b0f96856b6d Mon Sep 17 00:00:00 2001 From: ouyangxq <775153912@qq.com> Date: Fri, 7 Aug 2026 19:23:43 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BC=98=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../CustomerBillingRulesPanel.test.ts | 99 +++-- .../components/CustomerBillingRulesPanel.vue | 415 +++++++++--------- src/modules/dimension-config/api.test.ts | 54 +++ src/modules/dimension-config/api.ts | 35 ++ src/modules/dimension-config/index.ts | 10 + src/modules/dimension-config/types.ts | 15 + .../fba-pricing/customer-rules/api.test.ts | 82 ---- src/modules/fba-pricing/customer-rules/api.ts | 59 --- .../fba-pricing/customer-rules/types.ts | 49 --- src/modules/fba-pricing/index.ts | 14 - .../WeightOcrPanel.behavior.test.ts | 236 +++++++++- .../weight/components/WeightOcrPanel.vue | 29 +- 12 files changed, 627 insertions(+), 470 deletions(-) create mode 100644 src/modules/dimension-config/api.test.ts create mode 100644 src/modules/dimension-config/api.ts create mode 100644 src/modules/dimension-config/index.ts create mode 100644 src/modules/dimension-config/types.ts delete mode 100644 src/modules/fba-pricing/customer-rules/api.test.ts delete mode 100644 src/modules/fba-pricing/customer-rules/api.ts delete mode 100644 src/modules/fba-pricing/customer-rules/types.ts delete mode 100644 src/modules/fba-pricing/index.ts diff --git a/src/modules/customers/components/CustomerBillingRulesPanel.test.ts b/src/modules/customers/components/CustomerBillingRulesPanel.test.ts index 33f289df..591326b3 100644 --- a/src/modules/customers/components/CustomerBillingRulesPanel.test.ts +++ b/src/modules/customers/components/CustomerBillingRulesPanel.test.ts @@ -3,32 +3,24 @@ import { createPinia, setActivePinia } from 'pinia' import { enableAutoUnmount, flushPromises, mount } from '@vue/test-utils' import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest' import { - getCustomerPricingRule, - listCustomerPricingRules, - type CustomerPricingRule, -} from '@/modules/fba-pricing' + getCustomerDimensionConfig, + updateCustomerDimensionConfig, + type CustomerDimensionConfig, +} from '@/modules/dimension-config' import { useAccessPreviewStore } from '@/core/access/accessPreview' import { useAuthStore } from '@/core/auth/auth' import CustomerBillingRulesPanel from './CustomerBillingRulesPanel.vue' -vi.mock('@/modules/fba-pricing', () => ({ - createCustomerPricingRuleVersion: vi.fn(), - disableCustomerPricingRule: vi.fn(), - getCustomerPricingRule: vi.fn(), - listCustomerPricingRules: vi.fn(), +vi.mock('@/modules/dimension-config', () => ({ + getCustomerDimensionConfig: vi.fn(), + updateCustomerDimensionConfig: vi.fn(), })) -class ResizeObserverStub implements ResizeObserver { - observe() {} - unobserve() {} - disconnect() {} -} - -const rule: CustomerPricingRule = { - id: '91', tenantId: '8', ruleCode: 'FBA-SEA-KG', customerId: '8', customerName: '柏悦物流', - businessType: 'FBA_SEA', chargeMode: 'KG', taxMode: 'TAX_INCLUDED', conversionFactor: 167, - roundingScale: 3, roundingMode: 'CEILING', currency: 'CNY', effectiveFrom: '2026-08-01T00:00:00', - effectiveTo: null, ruleVersion: 2, status: 'ACTIVE', remark: '标准规则', createdAt: null, updatedAt: null, +const rule: CustomerDimensionConfig = { + tenantId: '8', + edgeAdditionCm: 2, + version: 3, + updatedAt: '2026-08-07T10:20:00', } enableAutoUnmount(afterEach) @@ -36,19 +28,18 @@ enableAutoUnmount(afterEach) describe('CustomerBillingRulesPanel', () => { beforeEach(() => { vi.clearAllMocks() - vi.stubGlobal('ResizeObserver', ResizeObserverStub) document.body.innerHTML = '' const pinia = createPinia() setActivePinia(pinia) const auth = useAuthStore() auth.token = 'token' - auth.permissions = ['firstleg:fba-pricing:rule:view', 'firstleg:fba-pricing:rule:edit'] + auth.permissions = ['firstleg:dimension-config:view', 'firstleg:dimension-config:edit'] useAccessPreviewStore().initializeAfterLogin() - vi.mocked(listCustomerPricingRules).mockResolvedValue([rule]) - vi.mocked(getCustomerPricingRule).mockResolvedValue(rule) + vi.mocked(getCustomerDimensionConfig).mockResolvedValue(rule) + vi.mocked(updateCustomerDimensionConfig).mockResolvedValue({ ...rule, version: 4 }) }) - it('loads only the current customer rules and exposes version actions', async () => { + it('shows one customer dimension rule instead of the old pricing versions', async () => { mount(CustomerBillingRulesPanel, { attachTo: document.body, props: { customerId: '8', customerName: '柏悦物流', customerCode: 'TEN8' }, @@ -56,15 +47,17 @@ describe('CustomerBillingRulesPanel', () => { }) await flushPromises() - expect(listCustomerPricingRules).toHaveBeenCalledWith({ tenantId: '8' }) - expect(document.body.textContent).toContain('FBA-SEA-KG') - expect(document.body.textContent).toContain('FBA 海运') - expect(document.body.textContent).toContain('新建规则') - expect(document.body.textContent).toContain('新版本') - expect(document.body.textContent).toContain('停用') + expect(getCustomerDimensionConfig).toHaveBeenCalledWith('8') + expect(document.body.textContent).toContain('尺寸计算规则') + expect(document.body.textContent).toContain('当前每侧加宽') + expect(document.body.textContent).toContain('+2cm') + expect(document.body.textContent).toContain('34 × 24 × 24 cm') + expect(document.body.textContent).toContain('0.020 CBM') + expect(document.body.textContent).not.toContain('规则版本') + expect(document.body.textContent).not.toContain('小箱') }) - it('loads rule details with the customer tenant scope', async () => { + it('edits the single value and submits the optimistic lock version', async () => { mount(CustomerBillingRulesPanel, { attachTo: document.body, props: { customerId: '8', customerName: '柏悦物流' }, @@ -72,13 +65,43 @@ describe('CustomerBillingRulesPanel', () => { }) await flushPromises() - const detailButtons = [...document.querySelectorAll('button')] - .filter((button) => button.textContent?.trim() === '详情') - const detailButton = detailButtons.at(-1) - detailButton?.click() + const editButton = [...document.querySelectorAll('button')] + .find((button) => button.textContent?.trim() === '编辑规则') + editButton?.click() await flushPromises() - expect(getCustomerPricingRule).toHaveBeenCalledWith('8', '91') - expect(document.body.textContent).toContain('标准规则') + expect(document.body.textContent).toContain('编辑尺寸计算规则') + expect(document.body.textContent).toContain('实际内径 30 × 20 × 20 cm') + const saveButton = [...document.querySelectorAll('button')] + .find((button) => button.textContent?.trim() === '保存规则') + saveButton?.click() + await flushPromises() + + expect(updateCustomerDimensionConfig).toHaveBeenCalledWith('8', { + edgeAdditionCm: 2, + version: 3, + }) + }) + + it('keeps the editor open when the versioned save fails', async () => { + vi.mocked(updateCustomerDimensionConfig).mockRejectedValueOnce(new Error('规则已被其他人更新')) + mount(CustomerBillingRulesPanel, { + attachTo: document.body, + props: { customerId: '8', customerName: '柏悦物流' }, + global: { plugins: [ElementPlus] }, + }) + await flushPromises() + + const editButton = [...document.querySelectorAll('button')] + .find((button) => button.textContent?.trim() === '编辑规则') + editButton?.click() + await flushPromises() + const saveButton = [...document.querySelectorAll('button')] + .find((button) => button.textContent?.trim() === '保存规则') + saveButton?.click() + await flushPromises() + + expect(document.body.textContent).toContain('编辑尺寸计算规则') + expect(updateCustomerDimensionConfig).toHaveBeenCalledWith('8', expect.objectContaining({ version: 3 })) }) }) diff --git a/src/modules/customers/components/CustomerBillingRulesPanel.vue b/src/modules/customers/components/CustomerBillingRulesPanel.vue index b1852211..fd5d2964 100644 --- a/src/modules/customers/components/CustomerBillingRulesPanel.vue +++ b/src/modules/customers/components/CustomerBillingRulesPanel.vue @@ -1,21 +1,18 @@