在开发微服务应用时,我们经常需要处理复杂的业务流程。传统的方式容易导致代码嵌套过深、逻辑分散。为此,我们开发了 chainlet,一个轻量级的链式调用框架。
为什么需要 chainlet?
传统方式的问题
// 传统方式 - 嵌套过深
async function processOrder(order: Order) {
const validated = await validateOrder(order);
if (!validated.success) {
throw new Error('Invalid order');
}
const inventory = await checkInventory(validated.data);
if (!inventory.available) {
throw { type: 'out_of_stock', items: inventory.missing };
}
const payment = await processPayment(validated.data);
if (!payment.success) {
throw { type: 'payment_failed', reason: payment.error };
}
return await confirmOrder(validated.data, payment);
}chainlet 的优势
// chainlet 方式 - 清晰的流水线
const pipeline = chain()
.use(validateOrder)
.use(checkInventory)
.use(processPayment)
.use(confirmOrder)
.handle(ValidationError, handleInvalidOrder)
.handle(InventoryError, handleOutOfStock)
.handle(PaymentError, { retry: 3, fallback: handlePaymentFailed });
const result = await pipeline.execute(order);核心概念
Chain
链式调用的核心容器,按顺序执行中间件。
Middleware
中间件处理输入数据,可以:
- 验证和转换数据
- 调用外部服务
- 决定是否继续执行
Handler
错误处理器,捕获和处理特定类型的错误。
高级用法
条件执行
chain()
.use(checkUserStatus)
.when(user => user.isPremium, premiumPipeline)
.otherwise(freePipeline);并行执行
chain()
.parallel([
fetchUserProfile,
fetchUserOrders,
fetchUserNotifications
])
.use(combineUserData);重试机制
chain()
.use(unstableExternalService, {
retry: 3,
backoff: 'exponential',
maxDelay: 5000
});实际应用场景
支付流程
const paymentPipeline = chain()
.use(verifyPaymentMethod)
.use(calculateAmount)
.use(processPayment)
.use(recordTransaction)
.use(sendConfirmation);数据导入
const importPipeline = chain()
.use(parseCSVFile)
.use(validateData)
.batch(100, saveToDatabase)
.use(generateReport);总结
chainlet 让复杂业务流程变得:
- 可读性强:像阅读故事一样理解业务流程
- 易于测试:每个中间件可以独立测试
- 灵活扩展:轻松添加或移除处理步骤
安装 chainlet:
npm install @rpamis/chainlet希望 chainlet 能帮助大家更好地组织代码!