perf(customs): request only tax refund orders

This commit is contained in:
2026-10-02 14:45:09 +08:00
parent c3a213d039
commit c06c105836
4 changed files with 49 additions and 14 deletions
@@ -1,9 +1,28 @@
import assert from 'node:assert/strict'
import { readFileSync } from 'node:fs'
import test from 'node:test'
import ts from 'typescript'
const source = readFileSync(new URL('./unifiedOrders.ts', import.meta.url), 'utf8')
test('forwards optional tax mode and pagination through the current GET endpoint', async () => {
const calls = []
const code = ts.transpileModule(source, { compilerOptions: { module: ts.ModuleKind.CommonJS } }).outputText
const api = {}
new Function('require', 'exports', code)(id => {
assert.equal(id, '@/api/http')
return { apiRequest: async config => { calls.push(config); return { records: [] } } }
}, api)
await api.getMerchantUnifiedOrders({ page: 2, size: 200, taxMode: 'TAX_REFUND' })
await api.getMerchantUnifiedOrders({ taxMode: 'BUY_DECLARATION' })
await api.getMerchantUnifiedOrders()
assert.deepEqual(calls, [
{ method: 'GET', url: '/merchant/v1/orders', params: { page: 2, size: 200, taxMode: 'TAX_REFUND' } },
{ method: 'GET', url: '/merchant/v1/orders', params: { page: 1, size: 200, taxMode: 'BUY_DECLARATION' } },
{ method: 'GET', url: '/merchant/v1/orders', params: { page: 1, size: 200 } },
])
})
test('keeps the merchant unified-order boundary and one-click palletization status', () => {
assert.match(source, /const unifiedOrderBaseUrl = '\/merchant\/v1\/orders'/)
assert.match(source, /ApiUnifiedOrderMainStatus[\s\S]*?'WAIT_PALLETIZE'/)
@@ -141,6 +141,7 @@ export interface MerchantUnifiedOrderDetail {
}
export interface MerchantUnifiedOrderQuery {
taxMode?: ApiTaxMode
keyword?: string
fbaCode?: string
orderNo?: string
@@ -16,7 +16,7 @@ export async function readCustomsDocuments() {
let failedCount = 0
const size = 200
for (let page = 1; ; page += 1) {
const response = await getMerchantUnifiedOrders({ page, size })
const response = await getMerchantUnifiedOrders({ page, size, taxMode: 'TAX_REFUND' })
const total = Number(response.total)
const pages = Number(response.pages)
if (!Number.isSafeInteger(total) || total < 0 || Number(response.page) !== page
@@ -18,14 +18,22 @@ const order = (id, status = 'LOADED', taxMode = 'TAX_REFUND') => ({ id, status,
const detail = id => ({ status: 'COMPLETED', merchantStatus: 'CUSTOMS_COMPLETED', inbounds: [{ orderId: id, taxMode: 'TAX_REFUND' }] })
function harness(t, orders, getDetail = async id => detail(id)) {
const store = { loadError: '', failPage: 0, transformPage: value => value }, calls = [], pageCalls = []
const unifiedApi = evaluate(readFileSync(new URL('../api/unifiedOrders.ts', import.meta.url), 'utf8'), {
'@/api/http': { apiRequest: async ({ method, url, params: { page, size, taxMode } }) => {
assert.equal(method, 'GET')
assert.equal(url, '/merchant/v1/orders')
pageCalls.push({ page, size, taxMode })
if (store.loadError || store.failPage === page) throw new Error(store.loadError || '第二页订单查询失败')
// Model server filtering BEFORE pagination and COUNT, using the actual
// request produced by the production API. Missing taxMode scans all rows.
const filtered = taxMode ? orders.filter(row => row.taxMode === taxMode) : orders
return store.transformPage({ page, size, total: filtered.length, pages: Math.ceil(filtered.length / size),
records: filtered.slice((page - 1) * size, page * size).map(row => ({ orderId: row.id, orderNo: row.orderNo, mainStatus: row.status, taxMode: row.taxMode, inboundCode: row.businessSummary.inboundCode })) })
} },
})
const reader = evaluate(readFileSync(new URL('../utils/customsDocumentsReader.ts', import.meta.url), 'utf8'), {
'./customsEligibility': eligibility,
'../api/unifiedOrders': { getMerchantUnifiedOrders: async ({ page, size }) => {
pageCalls.push({ page, size })
if (store.loadError || store.failPage === page) throw new Error(store.loadError || '第二页订单查询失败')
return store.transformPage({ page, size, total: orders.length, pages: Math.ceil(orders.length / size),
records: orders.slice((page - 1) * size, page * size).map(row => ({ orderId: row.id, orderNo: row.orderNo, mainStatus: row.status, taxMode: row.taxMode, inboundCode: row.businessSummary.inboundCode })) })
} },
'../api/unifiedOrders': unifiedApi,
'../api/customs': { getMerchantCustomsForOrder: id => { calls.push(id); return getDetail(id) }, isMerchantCustomsUnavailable: error => error?.code === 'A0404' },
})
const source = readFileSync(new URL('./CustomsDocumentsView.vue', import.meta.url), 'utf8').match(/<script setup lang="ts">([\s\S]*?)<\/script>/)[1]
@@ -38,14 +46,20 @@ function harness(t, orders, getDetail = async id => detail(id)) {
return { view, store, calls, pageCalls }
}
test('finds historical refund documents beyond the first 200 unified orders', async t => {
const orders = Array.from({ length: 200 }, (_, i) => order(`buy-${i}`, 'COMPLETED', 'BUY_DECLARATION'))
orders.push(order('historical', 'COMPLETED'))
test('server-filtered request reaches five refund records originally on page 28 without scanning buy orders', async t => {
const orders = Array.from({ length: 5528 }, (_, i) => order(`buy-${i}`, 'COMPLETED', 'BUY_DECLARATION'))
orders.push(...Array.from({ length: 5 }, (_, i) => order(`historical-${i}`, 'COMPLETED')))
const { view, calls, pageCalls } = harness(t, orders)
await view.load()
assert.deepEqual(calls, ['historical'])
assert.equal(view.records.value[0].order.id, 'historical')
assert.deepEqual(pageCalls, [{ page: 1, size: 200 }, { page: 2, size: 200 }])
assert.deepEqual(calls, Array.from({ length: 5 }, (_, i) => `historical-${i}`))
assert.equal(view.records.value.length, 5)
assert.deepEqual(pageCalls, [{ page: 1, size: 200, taxMode: 'TAX_REFUND' }])
view.queryModel.value.inboundCode = 'historical-4'; view.search()
assert.equal(view.filteredRecords.value.length, 1)
view.queryModel.value = { orderNo: '', inboundCode: '', containerNo: '', status: '' }; view.search()
assert.equal(view.filteredRecords.value.length, 5)
assert.equal(pageCalls.length, 1)
assert.equal(calls.length, 5)
})
test('second page failure is explicit and retry does not retain an incomplete result', async t => {
@@ -68,7 +82,7 @@ test('empty pages, duplicate records and changing totals cannot silently truncat
response => response.page === 2 ? { ...response, records: [{ ...response.records[0], orderId: '0' }] } : response,
response => response.page === 2 ? { ...response, total: 202 } : response,
]) {
const { view, store, pageCalls } = harness(t, Array.from({ length: 201 }, (_, i) => order(String(i), 'COMPLETED', 'BUY_DECLARATION')))
const { view, store, pageCalls } = harness(t, Array.from({ length: 201 }, (_, i) => order(String(i), 'COMPLETED')))
store.transformPage = change
await view.load()
assert.ok(view.errorMessage.value)
@@ -90,6 +104,7 @@ test('document fetch concurrency never exceeds four and each candidate is reques
assert.equal(new Set(calls).size, 205)
assert.equal(calls.length, 205)
assert.equal(pageCalls.length, 2)
assert.deepEqual(pageCalls, [{ page: 1, size: 200, taxMode: 'TAX_REFUND' }, { page: 2, size: 200, taxMode: 'TAX_REFUND' }])
assert.equal(view.records.value.length, 205)
})