Files
client-web/src/modules/first-leg/views/CustomsDocumentsView.test.mjs
T

92 lines
4.7 KiB
JavaScript
Raw Normal View History

import assert from 'node:assert/strict'
import test from 'node:test'
import { readFileSync } from 'node:fs'
import ts from 'typescript'
import * as vue from 'vue'
function evaluate(source, dependencies = {}) {
const code = ts.transpileModule(source, { compilerOptions: { module: ts.ModuleKind.CommonJS, target: ts.ScriptTarget.ES2022 } }).outputText
const exports = {}
new Function('require', 'exports', code)(id => {
assert.ok(id in dependencies, `Unexpected dependency ${id}`)
return dependencies[id]
}, exports)
return exports
}
const eligibility = evaluate(readFileSync(new URL('../utils/customsEligibility.ts', import.meta.url), 'utf8'))
const order = (id, status = 'LOADED', taxMode = 'TAX_REFUND') => ({ id, status, taxMode, orderNo: `ORDER-${id}`, businessSummary: { inboundCode: `IN-${id}` } })
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 = { orders, loadError: '', load: async () => {} }, calls = []
const source = readFileSync(new URL('./CustomsDocumentsView.vue', import.meta.url), 'utf8').match(/<script setup lang="ts">([\s\S]*?)<\/script>/)[1]
const scope = vue.effectScope()
const view = scope.run(() => evaluate(source + '\nexport { load, records, loading, errorMessage, openDetail, selectedOrderId, selectedDetail, dialogOpen, search, queryModel, filteredRecords }', {
vue: { ...vue, onMounted() {} },
'../public': { useFirstLegOrdersStore: () => store },
'../utils/customsEligibility': eligibility,
'../api/customs': { getMerchantCustomsForOrder: id => { calls.push(id); return getDetail(id) }, isMerchantCustomsUnavailable: error => error?.code === 'A0404' },
}))
t.after(() => scope.stop())
return { view, store, calls }
}
test('tax-refund documents remain accessible through delivered and completed orders; buy orders and preloading are excluded', async t => {
const stages = ['DRAFT', 'PENDING_REVIEW', 'WAIT_MEASURE', 'WAIT_PALLETIZE', 'WAIT_SPLIT', 'LOADING', 'LOADED', 'DELIVERED', 'COMPLETED']
const orders = stages.flatMap(status => [order(status, status), order(`BUY-${status}`, status, 'BUY_DECLARATION')])
const { view, calls } = harness(t, orders)
await view.load()
assert.deepEqual(calls, ['LOADED', 'DELIVERED', 'COMPLETED'])
assert.deepEqual(view.records.value.map(row => row.order.id), calls)
const completed = view.records.value.find(row => row.order.id === 'COMPLETED')
view.openDetail(completed)
assert.equal(view.selectedOrderId.value, 'COMPLETED')
assert.equal(view.selectedDetail.value.status, 'COMPLETED')
assert.equal(view.dialogOpen.value, true)
view.queryModel.value.status = 'COMPLETED'; view.search()
assert.equal(view.filteredRecords.value.length, 3)
assert.equal(calls.length, 3, 'local filtering does not refetch documents')
})
test('only matching server-returned tax-refund ownership is displayed', async t => {
const { view } = harness(t, [order('one'), order('two')], async id => id === 'one' ? detail('someone-else') : { inbounds: [{ orderId: id, taxMode: 'BUY_DECLARATION' }] })
await view.load()
assert.equal(view.records.value.length, 0)
})
test('partial failures are visible and retry replaces the result; unavailable customs is not a transport failure', async t => {
let fail = true
const { view } = harness(t, [order('ok'), order('retry'), order('unavailable')], async id => {
if (id === 'unavailable') throw Object.assign(new Error('not associated'), { code: 'A0404' })
if (id === 'retry' && fail) throw new Error('network')
return detail(id)
})
await view.load()
assert.equal(view.records.value.length, 1)
assert.equal(view.errorMessage.value, '1 票订单的报关资料加载失败,请重新加载')
fail = false; await view.load()
assert.equal(view.records.value.length, 2)
assert.equal(view.errorMessage.value, '')
})
test('order query failure is shown instead of a successful empty result', async t => {
const { view, store, calls } = harness(t, [order('old')])
await view.load()
store.loadError = '订单查询失败'; await view.load()
assert.equal(view.records.value.length, 0)
assert.equal(view.errorMessage.value, '订单查询失败')
assert.equal(calls.length, 1)
assert.equal(view.loading.value, false)
})
test('repeated refresh during an active load does not duplicate requests', async t => {
let resolve
const pending = new Promise(done => { resolve = done })
const { view, calls } = harness(t, [order('one')], () => pending)
const first = view.load()
await Promise.resolve()
await view.load()
assert.deepEqual(calls, ['one'])
resolve(detail('one')); await first
assert.equal(view.loading.value, false)
})