fix(jst): 补齐存量SKU主数据兜底

This commit is contained in:
WuYongJie 2026-06-04 22:37:15 +08:00
parent b4f088d70a
commit e26f958de0
2 changed files with 52 additions and 6 deletions

View File

@ -262,6 +262,7 @@ describe('syncJstSkuStockProducts', () => {
skuItems: expect.arrayContaining([
expect.objectContaining({
barcode: 'BAR001',
model: 'SPU001',
skuCode: 'SPJ00001',
sourceTable: 'jst_sku',
}),
@ -289,6 +290,7 @@ describe('syncJstSkuStockProducts', () => {
createMany: {
data: expect.arrayContaining([
expect.objectContaining({
model: 'SPU001',
skuCode: 'SPJ00001',
specName: '测试存量商品 1200*600*750',
barcode: 'BAR001',
@ -302,6 +304,45 @@ describe('syncJstSkuStockProducts', () => {
)
})
it('apply 创建存量商品时用聚水潭 sku_id 兜底缺失的 SKU 编码', async () => {
createConnectionMock(
createSourceRow({
sku_id: 'bar001',
other_7: '',
}),
)
const result = await syncJstSkuStockProducts({ apply: true, batchSize: 1, limit: 1 })
expect(result.created).toBe(1)
expect(mockedPrisma.intakeNonIntegratedProduct.create).toHaveBeenCalledWith(
expect.objectContaining({
data: expect.objectContaining({
payload: expect.objectContaining({
skuItems: expect.arrayContaining([
expect.objectContaining({
barcode: 'BAR001',
skuCode: 'BAR001',
sourceSkuId: 'BAR001',
}),
]),
}),
skuItems: {
createMany: {
data: expect.arrayContaining([
expect.objectContaining({
barcode: 'BAR001',
skuCode: 'BAR001',
sourceSkuId: 'BAR001',
}),
]),
},
},
}),
}),
)
})
it('apply 更新存量商品时 upsert 产品 profile 并刷新结构化 SKU 明细', async () => {
createConnectionMock(createSourceRow({ name: '更新后的存量商品 1200*600*750' }))
mockedPrisma.intakeNonIntegratedProduct.findUnique.mockResolvedValue({
@ -340,6 +381,7 @@ describe('syncJstSkuStockProducts', () => {
data: expect.arrayContaining([
expect.objectContaining({
barcode: 'BAR001',
model: 'SPU001',
skuCode: 'SPJ00001',
sourceTable: 'jst_sku',
}),

View File

@ -209,7 +209,11 @@ function mergeDefinedSourceFields<T extends Record<string, unknown>>(
return next
}
function buildSourceSkuItem(row: JstSkuSourceRow, sequence: number): NonIntegratedSkuItem {
function buildSourceSkuItem(
row: JstSkuSourceRow,
sequence: number,
sourceSpu: string,
): NonIntegratedSkuItem {
const skuId = normalizeSkuId(row.sku_id)
const name = normalizeSourceString(row.name)
const image = pickSourceImage(row)
@ -225,8 +229,8 @@ function buildSourceSkuItem(row: JstSkuSourceRow, sequence: number): NonIntegrat
packageSuffix: '',
image,
imageName: pickImageName(skuId, image),
model: '',
skuCode: normalizeSourceString(row.other_7),
model: sourceSpu,
skuCode: normalizeSourceString(row.other_7) || skuId,
setCount: normalizeSetCount(row.other_8),
specName: name,
barcode: skuId,
@ -300,7 +304,7 @@ function shouldExcludeStockCategory(category: string) {
return category.trim() === EXCLUDED_STOCK_CATEGORY
}
function buildSourceSkuItems(rows: JstSkuSourceRow[]) {
function buildSourceSkuItems(rows: JstSkuSourceRow[], sourceSpu: string) {
const seenSkuIds = new Set<string>()
return rows
@ -311,7 +315,7 @@ function buildSourceSkuItems(rows: JstSkuSourceRow[]) {
return row
})
.filter((row): row is JstSkuSourceRow => row !== null)
.map((row, index) => buildSourceSkuItem(row, index + 1))
.map((row, index) => buildSourceSkuItem(row, index + 1, sourceSpu))
}
function buildSourceProductPayload(
@ -322,7 +326,7 @@ function buildSourceProductPayload(
if (!sourceSpu) return null
const skuContentRows = pickSkuContentRows(group.rows)
const skuItems = buildSourceSkuItems(skuContentRows)
const skuItems = buildSourceSkuItems(skuContentRows, sourceSpu)
if (skuItems.length === 0) return null
const representativeRow = pickRepresentativeSourceRow(group.rows)