feat: flatten transport plan list rows to one product per line
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
1 parent
6abfb6e251
commit
e241a17077
2 files changed
+184
-7
No files matched your search
@@ -0,0 +1,95 @@
|
||||
import assert from 'node:assert/strict'
|
||||
import { describe, it } from 'node:test'
|
||||
import type { Plan, PlanStopProduct } from '@/api/pl'
|
||||
import {
|
||||
flattenPlanArchivePairRows,
|
||||
matchLoadProduct
|
||||
} from './pl-plan-list-display-rows'
|
||||
|
||||
function sp(partial: Partial<PlanStopProduct> & Pick<PlanStopProduct, 'productId'>): PlanStopProduct {
|
||||
return {
|
||||
productNo: partial.productNo || 'P',
|
||||
productName: partial.productName || '货',
|
||||
unit: partial.unit || '吨',
|
||||
...partial
|
||||
}
|
||||
}
|
||||
|
||||
function samplePlan(): Plan {
|
||||
return {
|
||||
id: 'plan-1',
|
||||
planNo: 'JH001',
|
||||
load: {
|
||||
customerName: '云栋化工',
|
||||
products: [
|
||||
sp({ planProductId: 'pp-u', productId: 'u', productName: '尿素', planQty: 30 }),
|
||||
sp({ planProductId: 'pp-a', productId: 'a', productName: '液氨', planQty: 10 })
|
||||
]
|
||||
},
|
||||
deliveries: [
|
||||
{
|
||||
seq: 1,
|
||||
customerName: '宜昌磷肥厂',
|
||||
products: [
|
||||
sp({ planProductId: 'pp-u', productId: 'u', productName: '尿素', planQty: 20 }),
|
||||
sp({ planProductId: 'pp-a', productId: 'a', productName: '液氨', planQty: 8 })
|
||||
]
|
||||
},
|
||||
{
|
||||
seq: 2,
|
||||
customerName: '荆州农资',
|
||||
products: [sp({ planProductId: 'pp-u', productId: 'u', productName: '尿素', planQty: 12 })]
|
||||
}
|
||||
]
|
||||
} as Plan
|
||||
}
|
||||
|
||||
describe('matchLoadProduct', () => {
|
||||
it('prefers planProductId then productId', () => {
|
||||
const load = [
|
||||
sp({ planProductId: 'pp-u', productId: 'u', productName: '尿素-装' }),
|
||||
sp({ planProductId: 'pp-x', productId: 'u', productName: '尿素-旧' })
|
||||
]
|
||||
const hit = matchLoadProduct(load, sp({ planProductId: 'pp-u', productId: 'u' }))
|
||||
assert.equal(hit?.productName, '尿素-装')
|
||||
const byId = matchLoadProduct(load, sp({ productId: 'u' }))
|
||||
assert.equal(byId?.planProductId, 'pp-u')
|
||||
})
|
||||
})
|
||||
|
||||
describe('flattenPlanArchivePairRows product rows', () => {
|
||||
it('splits 2 deliveries / 3 products with two-level spans', () => {
|
||||
const rows = flattenPlanArchivePairRows([samplePlan()])
|
||||
assert.equal(rows.length, 3)
|
||||
assert.equal(rows[0].planRowSpan, 3)
|
||||
assert.equal(rows[0].deliveryRowSpan, 2)
|
||||
assert.equal(rows[0].isPlanFirstRow, true)
|
||||
assert.equal(rows[0].isDeliveryFirstRow, true)
|
||||
assert.equal(rows[1].isDeliveryFirstRow, false)
|
||||
assert.equal(rows[1].deliveryRowSpan, 2)
|
||||
assert.equal(rows[2].isPlanLastRow, true)
|
||||
assert.equal(rows[2].isDeliveryFirstRow, true)
|
||||
assert.equal(rows[2].deliveryRowSpan, 1)
|
||||
assert.equal(rows[0].deliveryProduct?.productName, '尿素')
|
||||
assert.equal(rows[0].loadProduct?.planQty, 30)
|
||||
assert.equal(rows[2].deliveryProduct?.planQty, 12)
|
||||
assert.equal(rows[0].rowKey, 'plan-1-pair-1-pp-u')
|
||||
})
|
||||
|
||||
it('keeps one placeholder row when delivery has no products', () => {
|
||||
const plan = samplePlan()
|
||||
plan.deliveries = [{ seq: 1, customerName: '宜昌磷肥厂', products: [] }] as Plan['deliveries']
|
||||
const rows = flattenPlanArchivePairRows([plan])
|
||||
assert.equal(rows.length, 1)
|
||||
assert.equal(rows[0].deliveryProduct, undefined)
|
||||
assert.equal(rows[0].planRowSpan, 1)
|
||||
})
|
||||
|
||||
it('recomputes spans after product name filter', () => {
|
||||
const rows = flattenPlanArchivePairRows([samplePlan()], { productKeywords: ['液氨'] })
|
||||
assert.equal(rows.length, 1)
|
||||
assert.equal(rows[0].deliveryProduct?.productName, '液氨')
|
||||
assert.equal(rows[0].planRowSpan, 1)
|
||||
assert.equal(rows[0].deliveryRowSpan, 1)
|
||||
})
|
||||
})
|
||||
Reference in new issue
Block a user