forked from lunanting/cangku
256 lines
8.3 KiB
JavaScript
256 lines
8.3 KiB
JavaScript
'use strict';
|
|
|
|
const assert = require('node:assert/strict');
|
|
const test = require('node:test');
|
|
const fs = require('node:fs');
|
|
const path = require('node:path');
|
|
const {
|
|
buildSkuDraftRows,
|
|
getSourceDimensions,
|
|
normalizeDraftResponse,
|
|
publishPddGoodsDraft,
|
|
validateGoodsProperties,
|
|
validateSpecMappings,
|
|
} = require('../src/services/pddOpenPlatformDraftPublisher');
|
|
|
|
function createTwoDimensionItem() {
|
|
return {
|
|
id: 7,
|
|
skuSceneImages: { selectedSkuCodes: ['SOURCE-RED-80', 'SOURCE-BLUE-100'] },
|
|
metadata: {
|
|
sourceRow: {
|
|
product: {
|
|
skuDimensions: [
|
|
{ name: '颜色', values: ['红色', '蓝色', '未选颜色'] },
|
|
{ name: '尺寸', values: ['80cm', '100cm'] },
|
|
],
|
|
},
|
|
},
|
|
},
|
|
skuSnapshot: {
|
|
rows: [
|
|
{
|
|
skuCode: 'SOURCE-RED-80',
|
|
raw: { specs: [{ name: '颜色', value: '红色' }, { name: '尺寸', value: '80cm' }] },
|
|
},
|
|
{
|
|
skuCode: 'SOURCE-BLUE-100',
|
|
raw: { specs: [{ name: '颜色', value: '蓝色' }, { name: '尺寸', value: '100cm' }] },
|
|
},
|
|
],
|
|
},
|
|
pricingRows: [
|
|
{
|
|
skuCode: 'SOURCE-RED-80',
|
|
internalProductCode: 'COMPANY-RED-80',
|
|
generatedImageUrl: 'https://img.example/red.jpg',
|
|
finalPrice: 109,
|
|
groupPrice: 99,
|
|
},
|
|
{
|
|
skuCode: 'SOURCE-BLUE-100',
|
|
internalProductCode: 'COMPANY-BLUE-100',
|
|
generatedImageUrl: 'https://img.example/blue.jpg',
|
|
finalPrice: 119,
|
|
groupPrice: 109,
|
|
},
|
|
],
|
|
activityPricingRows: [
|
|
{ skuCode: 'SOURCE-RED-80', finalGroupPrice: 95 },
|
|
{ skuCode: 'SOURCE-BLUE-100', finalGroupPrice: 105 },
|
|
],
|
|
};
|
|
}
|
|
|
|
test('selected 1688 SKU rows retain two-dimensional coordinates', () => {
|
|
const item = createTwoDimensionItem();
|
|
const dimensions = getSourceDimensions(item);
|
|
assert.deepEqual(dimensions, [
|
|
{ name: '颜色', values: ['红色', '蓝色'] },
|
|
{ name: '尺寸', values: ['80cm', '100cm'] },
|
|
]);
|
|
|
|
const mappings = [
|
|
{ sourceDimensionName: '颜色', parentSpecId: 1215 },
|
|
{ sourceDimensionName: '尺寸', parentSpecId: 1216 },
|
|
];
|
|
const mappingByName = validateSpecMappings(dimensions, mappings, [
|
|
{ parentSpecId: 1215, name: '颜色' },
|
|
{ parentSpecId: 1216, name: '尺寸' },
|
|
]);
|
|
const specIds = new Map([
|
|
['颜色\u0000红色', 101],
|
|
['颜色\u0000蓝色', 102],
|
|
['尺寸\u000080cm', 201],
|
|
['尺寸\u0000100cm', 202],
|
|
]);
|
|
const images = new Map([
|
|
['SOURCE-RED-80', 'https://img.example/red.jpg'],
|
|
['SOURCE-BLUE-100', 'https://img.example/blue.jpg'],
|
|
]);
|
|
const rows = buildSkuDraftRows(item, {
|
|
quantity: 20,
|
|
weight: 12_000,
|
|
limitQuantity: 999,
|
|
}, dimensions, mappingByName, specIds, images);
|
|
|
|
assert.equal(rows.length, 2);
|
|
assert.deepEqual(rows[0].spec_id_list, [101, 201]);
|
|
assert.deepEqual(rows[1].spec_id_list, [102, 202]);
|
|
assert.equal(rows[0].multi_price, 9500);
|
|
assert.equal(rows[0].price, 10900);
|
|
assert.equal(rows[0].out_sku_sn, 'COMPANY-RED-80');
|
|
assert.equal(rows[1].quantity, 20);
|
|
assert.equal(rows[1].weight, 12_000);
|
|
});
|
|
|
|
test('dynamic category properties enforce required enum values', () => {
|
|
const rule = {
|
|
properties: [{
|
|
refPid: 310,
|
|
name: '品牌',
|
|
required: true,
|
|
chooseMaxNum: 1,
|
|
values: [{ vid: 8825, value: '卓禾' }],
|
|
}],
|
|
};
|
|
assert.throws(
|
|
() => validateGoodsProperties([], rule),
|
|
(error) => error.code === 'PDD_DRAFT_PROPERTY_REQUIRED'
|
|
);
|
|
assert.throws(
|
|
() => validateGoodsProperties([{ ref_pid: 310, vid: 9999, value: '无效' }], rule),
|
|
(error) => error.code === 'PDD_DRAFT_PROPERTY_INVALID'
|
|
);
|
|
assert.doesNotThrow(
|
|
() => validateGoodsProperties([{ ref_pid: 310, vid: 8825, value: '卓禾' }], rule)
|
|
);
|
|
});
|
|
|
|
test('draft response requires both goods ID and commit ID', () => {
|
|
assert.deepEqual(normalizeDraftResponse({
|
|
goods_update_response: {
|
|
goods_id: 989294315918,
|
|
goods_commit_id: 198258372338,
|
|
},
|
|
}), {
|
|
goodsId: '989294315918',
|
|
goodsCommitId: '198258372338',
|
|
});
|
|
assert.throws(
|
|
() => normalizeDraftResponse({ goods_update_response: { goods_id: 1 } }),
|
|
(error) => error.code === 'PDD_DRAFT_RESULT_UNKNOWN' && error.resultUnknown === true
|
|
);
|
|
});
|
|
|
|
test('1688 keeps the legacy server publisher available but uses the shared desktop queue', () => {
|
|
const serviceFile = path.join(__dirname, '../src/services/planningSelectionFissionService.js');
|
|
const source = fs.readFileSync(serviceFile, 'utf8');
|
|
assert.doesNotMatch(source, /if \(plan\.workflowProfile === ALIBABA_1688_PENDING_PROFILE\) \{\s*return saveAlibaba1688PddDrafts/);
|
|
assert.match(source, /async function saveAlibaba1688PddDrafts/);
|
|
assert.match(source, /const clientId = normalizeText\(input\.clientId/);
|
|
assert.match(source, /const supportedShopIds = new Set/);
|
|
assert.match(source, /publishMode: 'pdd_open_platform_draft'/);
|
|
});
|
|
|
|
test('complete publisher writes one draft commit and never calls submit or goods.add', async () => {
|
|
const calls = [];
|
|
let savedPayload;
|
|
const client = {
|
|
getAuthorizedCategories: async (parentCatId) => {
|
|
calls.push(['categories', parentCatId]);
|
|
return {
|
|
goods_auth_cats_get_response: {
|
|
goods_cats_list: Number(parentCatId) === 0
|
|
? [{ cat_id: 9324, cat_name: '住宅家具', leaf: false }]
|
|
: [{ cat_id: 10607, cat_name: '普通餐桌', leaf: true }],
|
|
},
|
|
};
|
|
},
|
|
getCategoryRule: async () => ({
|
|
cat_rule_get_response: {
|
|
goods_properties_rule: {
|
|
properties: [{
|
|
ref_pid: 310,
|
|
name: '品牌',
|
|
required: true,
|
|
values: [{ vid: 8825, value: '卓禾' }],
|
|
}],
|
|
},
|
|
},
|
|
}),
|
|
getCategorySpecs: async () => ({
|
|
goods_spec_get_response: {
|
|
goods_spec_list: [
|
|
{ parent_spec_id: 1215, parent_spec_name: '颜色' },
|
|
{ parent_spec_id: 1216, parent_spec_name: '尺寸' },
|
|
],
|
|
},
|
|
}),
|
|
getLogisticsTemplates: async () => ({
|
|
goods_logistics_template_get_response: {
|
|
logistics_template_list: [{
|
|
template_id: 303351846671360,
|
|
template_name: '内地包邮默认模板',
|
|
cost_type: 0,
|
|
}],
|
|
},
|
|
}),
|
|
getOrCreateSpecId: async (parentSpecId, specName) => {
|
|
calls.push(['spec', parentSpecId, specName]);
|
|
const ids = { '红色': 101, '蓝色': 102, '80cm': 201, '100cm': 202 };
|
|
return { goods_spec_id_get_response: { spec_id: ids[specName] } };
|
|
},
|
|
saveGoodsDraft: async (payload) => {
|
|
calls.push(['pdd.goods.edit.goods.commit']);
|
|
savedPayload = payload;
|
|
return {
|
|
goods_update_response: {
|
|
goods_id: 989294315918,
|
|
goods_commit_id: 198258372338,
|
|
},
|
|
};
|
|
},
|
|
};
|
|
const item = createTwoDimensionItem();
|
|
item.marketItemId = '1073252781818';
|
|
item.selectedProductTitle = '现代简约实木餐桌';
|
|
item.title = item.selectedProductTitle;
|
|
item.metadata.sourceRow.product.mainImages = ['https://img.example/main.jpg'];
|
|
item.metadata.sourceRow.product.detailImages = ['https://img.example/detail.jpg'];
|
|
const result = await publishPddGoodsDraft(
|
|
{ id: 9, schemeCode: 'FB-TEST' },
|
|
item,
|
|
{
|
|
catId: 10607,
|
|
categoryPath: [9324, 10607],
|
|
costTemplateId: 303351846671360,
|
|
goodsProperties: [{ refPid: 310, vid: 8825, value: '卓禾' }],
|
|
specMappings: [
|
|
{ sourceDimensionName: '颜色', parentSpecId: 1215 },
|
|
{ sourceDimensionName: '尺寸', parentSpecId: 1216 },
|
|
],
|
|
quantity: 20,
|
|
weight: 12_000,
|
|
twoPiecesDiscount: 95,
|
|
},
|
|
{ shopId: 'shop-1', shopName: '卓禾旗舰店' },
|
|
{
|
|
client,
|
|
uploadImage: async (url, kind) => `https://pdd.example/${kind}/${encodeURIComponent(url)}.jpg`,
|
|
}
|
|
);
|
|
|
|
assert.equal(result.goodsId, '989294315918');
|
|
assert.equal(result.goodsCommitId, '198258372338');
|
|
assert.equal(savedPayload.cat_id, 10607);
|
|
assert.equal(savedPayload.sku_list.length, 2);
|
|
assert.equal(savedPayload.carousel_gallery.length, 1);
|
|
assert.equal(savedPayload.detail_gallery.length, 1);
|
|
assert.deepEqual(calls.filter((row) => row[0] === 'pdd.goods.edit.goods.commit'), [
|
|
['pdd.goods.edit.goods.commit'],
|
|
]);
|
|
assert.equal(calls.some((row) => row[0] === 'pdd.goods.add'), false);
|
|
assert.equal(calls.some((row) => row[0] === 'pdd.goods.submit.goods.commit'), false);
|
|
});
|