Files
order_site/apps/backend/src/routes/admin/platform-config.js
T
2026-05-14 17:29:12 +08:00

621 lines
26 KiB
JavaScript

// @ts-check
import { Router } from 'express'
import {
appointAdminCloudtentaclesVirtualNumber,
backAdminCloudtentaclesVirtualNumber,
buyAdminCloudtentaclesSku,
fetchAdminCloudtentaclesVirtualNumberCode,
generateAdminCloudtentaclesLoginCode,
getAdminCloudtentaclesAsset,
getAdminCloudtentaclesBindUrl,
getAdminCloudtentaclesCategories,
getAdminNotificationConfig,
getAdminKuaishouCloudFulfillmentConfig,
getAdminKuaishouEticketSourceConfig,
getAdminCloudtentaclesKnapsack,
getAdminCloudtentaclesSourceConfig,
getAdminCloudtentaclesSkuList,
useAdminCloudtentaclesSku,
getAdminAgisoShopConfigs,
getAdminFulfillmentBindingConfigs,
getAdminNinetyoneOrders,
consumeAdminKuaishouEticket,
failAdminNinetyoneOrder,
listAdminCloudtentaclesVirtualNumbers,
lookupAdminFulfillmentBindingOrder,
queryAdminKuaishouEticketShopInfo,
queryAdminKuaishouEticketDetail,
retryAdminNinetyoneOrder,
runAdminCloudtentaclesFullFlow,
sendAdminCloudtentaclesSmsCode,
testAdminNotification,
testAdminCloudtentaclesLogin,
updateAdminKuaishouCloudFulfillmentConfig,
updateAdminKuaishouEticketSourceConfig,
updateAdminCloudtentaclesSourceConfig,
updateAdminNotificationConfig,
updateAdminAgisoShopConfigs,
updateAdminFulfillmentBindingConfigs,
verifyAdminCloudtentaclesLoginCode,
validateAdminCloudtentaclesSession,
} from '../../services/admin/platform-config/service.js'
import { createJsonHandler, requireAdminRoles } from './shared.js'
/** @typedef {import('../../types/admin-route-inputs.js').AdminAgisoShopConfigRouteBody} AdminAgisoShopConfigRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminFulfillmentBindingConfigRouteBody} AdminFulfillmentBindingConfigRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminFulfillmentBindingLookupRouteBody} AdminFulfillmentBindingLookupRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminEntityRouteParams} AdminEntityRouteParams */
/** @typedef {import('../../types/admin-route-inputs.js').AdminKuaishouEticketSourceConfigRouteBody} AdminKuaishouEticketSourceConfigRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminNotificationConfigRouteBody} AdminNotificationConfigRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminNotificationTestRouteBody} AdminNotificationTestRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminKuaishouEticketDetailQueryRouteBody} AdminKuaishouEticketDetailQueryRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminKuaishouEticketConsumeRouteBody} AdminKuaishouEticketConsumeRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminKuaishouEticketShopInfoRouteBody} AdminKuaishouEticketShopInfoRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminCloudtentaclesSourceConfigRouteBody} AdminCloudtentaclesSourceConfigRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminKuaishouCloudFulfillmentConfigRouteBody} AdminKuaishouCloudFulfillmentConfigRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminCloudtentaclesSendSmsCodeRouteBody} AdminCloudtentaclesSendSmsCodeRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminCloudtentaclesTestLoginRouteBody} AdminCloudtentaclesTestLoginRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminCloudtentaclesValidateSessionRouteBody} AdminCloudtentaclesValidateSessionRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminCloudtentaclesCatalogQueryRouteBody} AdminCloudtentaclesCatalogQueryRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminCloudtentaclesSkuBuyRouteBody} AdminCloudtentaclesSkuBuyRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminCloudtentaclesSkuUseRouteBody} AdminCloudtentaclesSkuUseRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminCloudtentaclesVirtualNumberRouteBody} AdminCloudtentaclesVirtualNumberRouteBody */
/** @typedef {import('../../types/admin-route-inputs.js').AdminCloudtentaclesFullFlowRouteBody} AdminCloudtentaclesFullFlowRouteBody */
/** @typedef {import('../../types/admin-write-models.js').AdminAgisoShopConfigSaveResponse} AdminAgisoShopConfigSaveResponse */
const router = Router()
router.use('/platform-config', requireAdminRoles(['admin']))
router.get('/platform-config/agiso-shops', createJsonHandler(
() => getAdminAgisoShopConfigs(),
{
successMessage: 'ok',
errorMessage: '读取 Agiso 店铺配置失败',
scope: '[admin/platform-config/agiso-shops]',
},
))
router.post('/platform-config/agiso-shops', createJsonHandler(
(req) => updateAdminAgisoShopConfigs(/** @type {AdminAgisoShopConfigRouteBody} */ (req.body)),
{
successMessage: 'Agiso 店铺配置已保存',
errorMessage: '保存 Agiso 店铺配置失败',
scope: '[admin/platform-config/agiso-shops]',
audit: (_req, data) => {
const result = /** @type {AdminAgisoShopConfigSaveResponse} */ (data)
return {
action: 'platform_shop_config_updated',
targetType: 'platform_config',
targetId: 'agiso_shops',
data: {
shopCount: result.shops.length,
filePath: result.filePath,
},
}
},
},
))
router.get('/platform-config/notifications', createJsonHandler(
() => getAdminNotificationConfig(),
{
successMessage: 'ok',
errorMessage: '读取内部通知配置失败',
scope: '[admin/platform-config/notifications]',
},
))
router.post('/platform-config/notifications', createJsonHandler(
(req) => updateAdminNotificationConfig(/** @type {AdminNotificationConfigRouteBody} */ (req.body)),
{
successMessage: '内部通知配置已保存',
errorMessage: '保存内部通知配置失败',
scope: '[admin/platform-config/notifications]',
audit: (_req, data) => {
const result = /** @type {{ filePath?: string, source?: { enabled?: boolean, channels?: { bark?: { recipients?: unknown[] } } } }} */ (data)
return {
action: 'platform_notification_config_updated',
targetType: 'platform_config',
targetId: 'notifications',
data: {
filePath: String(result.filePath || '').trim(),
enabled: Boolean(result.source?.enabled),
barkRecipientCount: Array.isArray(result.source?.channels?.bark?.recipients)
? result.source.channels.bark.recipients.length
: 0,
},
}
},
},
))
router.post('/platform-config/notifications/test', createJsonHandler(
(req) => testAdminNotification(/** @type {AdminNotificationTestRouteBody} */ (req.body)),
{
successMessage: '内部通知测试已执行',
errorMessage: '内部通知测试失败',
scope: '[admin/platform-config/notifications/test]',
audit: (_req, data) => {
const result = /** @type {{ successCount?: number, failedCount?: number, channel?: string }} */ (data)
return {
action: 'platform_notification_test_sent',
targetType: 'platform_config',
targetId: 'notifications',
data: {
channel: String(result.channel || '').trim(),
successCount: Number(result.successCount || 0),
failedCount: Number(result.failedCount || 0),
},
}
},
},
))
router.get('/platform-config/kuaishou-eticket-source', createJsonHandler(
() => getAdminKuaishouEticketSourceConfig(),
{
successMessage: 'ok',
errorMessage: '读取快手小店核销配置失败',
scope: '[admin/platform-config/kuaishou-eticket-source]',
},
))
router.post('/platform-config/kuaishou-eticket-source', createJsonHandler(
(req) => updateAdminKuaishouEticketSourceConfig(/** @type {AdminKuaishouEticketSourceConfigRouteBody} */ (req.body)),
{
successMessage: '快手小店核销配置已保存',
errorMessage: '保存快手小店核销配置失败',
scope: '[admin/platform-config/kuaishou-eticket-source]',
audit: (_req, data) => {
const result = /** @type {{ filePath?: string, source?: { enabled?: boolean, shops?: unknown[] } }} */ (data)
return {
action: 'platform_kuaishou_eticket_source_updated',
targetType: 'platform_config',
targetId: 'kuaishou_eticket_source',
data: {
filePath: String(result.filePath || '').trim(),
enabled: Boolean(result.source?.enabled),
shopCount: Array.isArray(result.source?.shops) ? result.source.shops.length : 0,
},
}
},
},
))
router.get('/platform-config/ninetyone/orders', createJsonHandler(
(req) => getAdminNinetyoneOrders(req.query),
{
successMessage: 'ok',
errorMessage: '读取 91卡券订单失败',
scope: '[admin/platform-config/ninetyone/orders]',
},
))
router.post('/platform-config/ninetyone/orders/:id/retry', createJsonHandler(
(req) => retryAdminNinetyoneOrder((/** @type {AdminEntityRouteParams} */ (req.params)).id),
{
successMessage: '91卡券订单已重试',
errorMessage: '重试 91卡券订单失败',
scope: '[admin/platform-config/ninetyone/orders/:id/retry]',
audit: (_req, data) => {
const result = /** @type {{ orderId?: number, orderNo?: string, taskCount?: number }} */ (data)
return {
action: 'platform_ninetyone_order_retried',
targetType: 'order',
targetId: String(result.orderId || '').trim(),
data: {
orderNo: String(result.orderNo || '').trim(),
taskCount: Number(result.taskCount || 0),
},
}
},
},
))
router.post('/platform-config/ninetyone/orders/:id/fail', createJsonHandler(
(req) => failAdminNinetyoneOrder(
(/** @type {AdminEntityRouteParams} */ (req.params)).id,
/** @type {{ reason?: string }} */ (req.body),
),
{
successMessage: '91卡券订单已标记失败',
errorMessage: '标记 91卡券订单失败',
scope: '[admin/platform-config/ninetyone/orders/:id/fail]',
audit: (req, data) => {
const result = /** @type {{ orderId?: number, orderNo?: string }} */ (data)
return {
action: 'platform_ninetyone_order_failed',
targetType: 'order',
targetId: String(result.orderId || '').trim(),
data: {
orderNo: String(result.orderNo || '').trim(),
reason: String((/** @type {{ reason?: string }} */ (req.body)).reason || '').trim(),
},
}
},
},
))
router.post('/platform-config/kuaishou-eticket/query-detail', createJsonHandler(
(req) => queryAdminKuaishouEticketDetail(/** @type {AdminKuaishouEticketDetailQueryRouteBody} */ (req.body)),
{
successMessage: '快手小店核销信息查询成功',
errorMessage: '查询快手小店核销信息失败',
scope: '[admin/platform-config/kuaishou-eticket/query-detail]',
audit: (req, data) => {
const body = /** @type {AdminKuaishouEticketDetailQueryRouteBody} */ (req.body)
const result = /** @type {{ eTicketId?: string, result?: number, ok?: boolean, alreadyConsumed?: boolean }} */ (data)
return {
action: 'platform_kuaishou_eticket_query_detail',
targetType: 'platform_config',
targetId: String(result.eTicketId || body.eTicketId || '').trim() || 'kuaishou_eticket',
data: {
result: Number(result.result || 0),
ok: Boolean(result.ok),
alreadyConsumed: Boolean(result.alreadyConsumed),
},
}
},
},
))
router.post('/platform-config/kuaishou-eticket/query-shop-info', createJsonHandler(
(req) => queryAdminKuaishouEticketShopInfo(/** @type {AdminKuaishouEticketShopInfoRouteBody} */ (req.body)),
{
successMessage: '快手小店店铺信息查询成功',
errorMessage: '查询快手小店店铺信息失败',
scope: '[admin/platform-config/kuaishou-eticket/query-shop-info]',
audit: (req, data) => {
const body = /** @type {AdminKuaishouEticketShopInfoRouteBody} */ (req.body)
const result = /** @type {{ shop?: { shopId?: string, kshopName?: string }, result?: number, ok?: boolean }} */ (data)
return {
action: 'platform_kuaishou_eticket_query_shop_info',
targetType: 'platform_config',
targetId: String(result.shop?.shopId || body.shopId || '').trim() || 'kuaishou_eticket_shop_info',
data: {
result: Number(result.result || 0),
ok: Boolean(result.ok),
kshopName: String(result.shop?.kshopName || '').trim(),
},
}
},
},
))
router.post('/platform-config/kuaishou-eticket/consume', createJsonHandler(
(req) => consumeAdminKuaishouEticket(/** @type {AdminKuaishouEticketConsumeRouteBody} */ (req.body)),
{
successMessage: '快手小店核销请求已执行',
errorMessage: '执行快手小店核销失败',
scope: '[admin/platform-config/kuaishou-eticket/consume]',
audit: (req, data) => {
const body = /** @type {AdminKuaishouEticketConsumeRouteBody} */ (req.body)
const result = /** @type {{ eTicketId?: string, result?: number, consumed?: boolean, alreadyConsumed?: boolean }} */ (data)
return {
action: 'platform_kuaishou_eticket_consume',
targetType: 'platform_config',
targetId: String(result.eTicketId || body.eTicketId || '').trim() || 'kuaishou_eticket',
data: {
result: Number(result.result || 0),
consumed: Boolean(result.consumed),
alreadyConsumed: Boolean(result.alreadyConsumed),
},
}
},
},
))
router.get('/platform-config/cloudtentacles-source', createJsonHandler(
() => getAdminCloudtentaclesSourceConfig(),
{
successMessage: 'ok',
errorMessage: '读取 cloudtentacles 履约平台配置失败',
scope: '[admin/platform-config/cloudtentacles-source]',
},
))
router.post('/platform-config/cloudtentacles-source', createJsonHandler(
(req) => updateAdminCloudtentaclesSourceConfig(/** @type {AdminCloudtentaclesSourceConfigRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 履约平台配置已保存',
errorMessage: '保存 cloudtentacles 履约平台配置失败',
scope: '[admin/platform-config/cloudtentacles-source]',
audit: (_req, data) => {
const result = /** @type {{ filePath?: string, source?: { username?: string, enabled?: boolean } }} */ (data)
return {
action: 'platform_cloudtentacles_source_updated',
targetType: 'platform_config',
targetId: 'cloudtentacles_source',
data: {
filePath: String(result.filePath || '').trim(),
username: String(result.source?.username || '').trim(),
enabled: Boolean(result.source?.enabled),
},
}
},
},
))
router.post('/platform-config/cloudtentacles/send-sms-code', createJsonHandler(
(req) => sendAdminCloudtentaclesSmsCode(/** @type {AdminCloudtentaclesSendSmsCodeRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 短信验证码已发送',
errorMessage: 'cloudtentacles 发送短信验证码失败',
scope: '[admin/platform-config/cloudtentacles/send-sms-code]',
audit: (req, data) => {
const body = /** @type {AdminCloudtentaclesSendSmsCodeRouteBody} */ (req.body)
const result = /** @type {{ username?: string, phoneMasked?: string, baseUrl?: string }} */ (data)
return {
action: 'platform_cloudtentacles_send_sms_code',
targetType: 'platform_config',
targetId: String(result.username || body.username || '').trim() || 'cloudtentacles',
data: {
baseUrl: result.baseUrl || String(body.baseUrl || '').trim(),
phoneMasked: result.phoneMasked || '',
},
}
},
},
))
router.post('/platform-config/cloudtentacles/test-login', createJsonHandler(
(req) => testAdminCloudtentaclesLogin(/** @type {AdminCloudtentaclesTestLoginRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 登录测试成功',
errorMessage: 'cloudtentacles 登录测试失败',
scope: '[admin/platform-config/cloudtentacles/test-login]',
audit: (req, data) => {
const body = /** @type {AdminCloudtentaclesTestLoginRouteBody} */ (req.body)
const result = /** @type {{ baseUrl?: string, username?: string, session?: { permissionCount?: number } }} */ (data)
return {
action: 'platform_cloudtentacles_test_login',
targetType: 'platform_config',
targetId: String(result.username || body.username || '').trim() || 'cloudtentacles',
data: {
baseUrl: result.baseUrl || String(body.baseUrl || '').trim(),
permissionCount: Number(result.session?.permissionCount || 0),
},
}
},
},
))
router.post('/platform-config/cloudtentacles/validate-session', createJsonHandler(
(req) => validateAdminCloudtentaclesSession(/** @type {AdminCloudtentaclesValidateSessionRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 会话校验成功',
errorMessage: 'cloudtentacles 会话校验失败',
scope: '[admin/platform-config/cloudtentacles/validate-session]',
audit: (_req, data) => {
const result = /** @type {{ baseUrl?: string, session?: { permissionCount?: number } }} */ (data)
return {
action: 'platform_cloudtentacles_validate_session',
targetType: 'platform_config',
targetId: 'cloudtentacles_session',
data: {
baseUrl: String(result.baseUrl || '').trim(),
permissionCount: Number(result.session?.permissionCount || 0),
},
}
},
},
))
router.post('/platform-config/cloudtentacles/asset', createJsonHandler(
(req) => getAdminCloudtentaclesAsset(/** @type {AdminCloudtentaclesCatalogQueryRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 余额查询成功',
errorMessage: 'cloudtentacles 余额查询失败',
scope: '[admin/platform-config/cloudtentacles/asset]',
},
))
router.post('/platform-config/cloudtentacles/categories', createJsonHandler(
(req) => getAdminCloudtentaclesCategories(/** @type {AdminCloudtentaclesCatalogQueryRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 分类查询成功',
errorMessage: 'cloudtentacles 分类查询失败',
scope: '[admin/platform-config/cloudtentacles/categories]',
},
))
router.post('/platform-config/cloudtentacles/sku/list', createJsonHandler(
(req) => getAdminCloudtentaclesSkuList(/** @type {AdminCloudtentaclesCatalogQueryRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles SKU 列表查询成功',
errorMessage: 'cloudtentacles SKU 列表查询失败',
scope: '[admin/platform-config/cloudtentacles/sku/list]',
},
))
router.post('/platform-config/cloudtentacles/sku/buy', createJsonHandler(
(req) => buyAdminCloudtentaclesSku(/** @type {AdminCloudtentaclesSkuBuyRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles SKU 购买成功',
errorMessage: 'cloudtentacles SKU 购买失败',
scope: '[admin/platform-config/cloudtentacles/sku/buy]',
},
))
router.post('/platform-config/cloudtentacles/sku/use', createJsonHandler(
(req) => useAdminCloudtentaclesSku(/** @type {AdminCloudtentaclesSkuUseRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 发货成功',
errorMessage: 'cloudtentacles 发货失败',
scope: '[admin/platform-config/cloudtentacles/sku/use]',
},
))
router.post('/platform-config/cloudtentacles/knapsack', createJsonHandler(
(req) => getAdminCloudtentaclesKnapsack(/** @type {AdminCloudtentaclesCatalogQueryRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 背包查询成功',
errorMessage: 'cloudtentacles 背包查询失败',
scope: '[admin/platform-config/cloudtentacles/knapsack]',
},
))
router.post('/platform-config/cloudtentacles/vn/list', createJsonHandler(
(req) => listAdminCloudtentaclesVirtualNumbers(/** @type {AdminCloudtentaclesVirtualNumberRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 虚拟号列表查询成功',
errorMessage: 'cloudtentacles 虚拟号列表查询失败',
scope: '[admin/platform-config/cloudtentacles/vn/list]',
},
))
router.post('/platform-config/cloudtentacles/vn/appoint', createJsonHandler(
(req) => appointAdminCloudtentaclesVirtualNumber(/** @type {AdminCloudtentaclesVirtualNumberRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 虚拟号申请成功',
errorMessage: 'cloudtentacles 虚拟号申请失败',
scope: '[admin/platform-config/cloudtentacles/vn/appoint]',
},
))
router.post('/platform-config/cloudtentacles/vn/generate-login-code', createJsonHandler(
(req) => generateAdminCloudtentaclesLoginCode(/** @type {AdminCloudtentaclesVirtualNumberRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 登录码生成成功',
errorMessage: 'cloudtentacles 登录码生成失败',
scope: '[admin/platform-config/cloudtentacles/vn/generate-login-code]',
},
))
router.post('/platform-config/cloudtentacles/vn/fetch-code', createJsonHandler(
(req) => fetchAdminCloudtentaclesVirtualNumberCode(/** @type {AdminCloudtentaclesVirtualNumberRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 验证码获取成功',
errorMessage: 'cloudtentacles 验证码获取失败',
scope: '[admin/platform-config/cloudtentacles/vn/fetch-code]',
},
))
router.post('/platform-config/cloudtentacles/vn/verify-code', createJsonHandler(
(req) => verifyAdminCloudtentaclesLoginCode(/** @type {AdminCloudtentaclesVirtualNumberRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 登录码校验成功',
errorMessage: 'cloudtentacles 登录码校验失败',
scope: '[admin/platform-config/cloudtentacles/vn/verify-code]',
},
))
router.post('/platform-config/cloudtentacles/vn/bind-url', createJsonHandler(
(req) => getAdminCloudtentaclesBindUrl(/** @type {AdminCloudtentaclesVirtualNumberRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 兑换链接获取成功',
errorMessage: 'cloudtentacles 兑换链接获取失败',
scope: '[admin/platform-config/cloudtentacles/vn/bind-url]',
},
))
router.post('/platform-config/cloudtentacles/vn/back', createJsonHandler(
(req) => backAdminCloudtentaclesVirtualNumber(/** @type {AdminCloudtentaclesVirtualNumberRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 号码退还成功',
errorMessage: 'cloudtentacles 号码退还失败',
scope: '[admin/platform-config/cloudtentacles/vn/back]',
},
))
router.post('/platform-config/cloudtentacles/debug/full-flow', createJsonHandler(
(req) => runAdminCloudtentaclesFullFlow(/** @type {AdminCloudtentaclesFullFlowRouteBody} */ (req.body)),
{
successMessage: 'cloudtentacles 完整调试流程执行成功',
errorMessage: 'cloudtentacles 完整调试流程执行失败',
scope: '[admin/platform-config/cloudtentacles/debug/full-flow]',
},
))
router.get('/platform-config/fulfillment-bindings', createJsonHandler(
() => getAdminFulfillmentBindingConfigs(),
{
successMessage: 'ok',
errorMessage: '读取履约配置失败',
scope: '[admin/platform-config/fulfillment-bindings]',
},
))
router.post('/platform-config/fulfillment-bindings/lookup-order', createJsonHandler(
(req) => lookupAdminFulfillmentBindingOrder(/** @type {AdminFulfillmentBindingLookupRouteBody} */ (req.body)),
{
successMessage: '订单商品查询成功',
errorMessage: '手动查询订单商品失败',
scope: '[admin/platform-config/fulfillment-bindings/lookup-order]',
audit: (req, data) => {
const result = /** @type {{ order?: { provider?: string, platform?: string, shopId?: string, platformOrderId?: string }, items?: unknown[] }} */ (data)
return {
action: 'platform_fulfillment_order_lookup',
targetType: 'platform_config',
targetId: [
result.order?.provider || 'unknown',
result.order?.platform || 'unknown',
result.order?.shopId || 'unknown',
result.order?.platformOrderId || 'unknown',
].join(':'),
data: {
itemCount: Array.isArray(result.items) ? result.items.length : 0,
shopId: result.order?.shopId || String((/** @type {AdminFulfillmentBindingLookupRouteBody} */ (req.body))?.shopId || '').trim(),
platformOrderId: result.order?.platformOrderId || String((/** @type {AdminFulfillmentBindingLookupRouteBody} */ (req.body))?.platformOrderId || '').trim(),
},
}
},
},
))
router.post('/platform-config/fulfillment-bindings', createJsonHandler(
(req) => updateAdminFulfillmentBindingConfigs(/** @type {AdminFulfillmentBindingConfigRouteBody} */ (req.body)),
{
successMessage: '履约配置已保存',
errorMessage: '保存履约配置失败',
scope: '[admin/platform-config/fulfillment-bindings]',
audit: (_req, data) => {
const result = /** @type {{ bindings?: unknown[], filePath?: string }} */ (data)
return {
action: 'platform_fulfillment_config_updated',
targetType: 'platform_config',
targetId: 'fulfillment_bindings',
data: {
bindingCount: Array.isArray(result.bindings) ? result.bindings.length : 0,
filePath: result.filePath || '',
},
}
},
},
))
router.get('/platform-config/kuaishou-cloud-fulfillment', createJsonHandler(
() => getAdminKuaishouCloudFulfillmentConfig(),
{
successMessage: 'ok',
errorMessage: '读取新履约配置失败',
scope: '[admin/platform-config/kuaishou-cloud-fulfillment]',
},
))
router.post('/platform-config/kuaishou-cloud-fulfillment', createJsonHandler(
(req) => updateAdminKuaishouCloudFulfillmentConfig(/** @type {AdminKuaishouCloudFulfillmentConfigRouteBody} */ (req.body)),
{
successMessage: '新履约配置已保存',
errorMessage: '保存新履约配置失败',
scope: '[admin/platform-config/kuaishou-cloud-fulfillment]',
audit: (_req, data) => {
const result = /** @type {{ filePath?: string, source?: { items?: unknown[] } }} */ (data)
return {
action: 'platform_kuaishou_cloud_fulfillment_updated',
targetType: 'platform_config',
targetId: 'kuaishou_cloud_fulfillment',
data: {
itemCount: Array.isArray(result.source?.items) ? result.source.items.length : 0,
filePath: String(result.filePath || '').trim(),
},
}
},
},
))
export default router