比方说,我正在创建一个PWA(渐进式Web应用程序),用户可以在其中添加产品。 这些产品的价格从0.01欧元到1.00欧元不等。 我正在使用Stripe付款。 Stripe Order对象不支持动态价格,即时传递,没有任何引用(外键类型)。 要接受订单,Stripe需要引用SKU。 就我而言,此SKU将是产品的价格变化。 这意味着,要涵盖所有变体,我需要100个SKU,从1(0.01 EUR)到100(1,00 EUR)。 因此,对于在Stripe中创建的每个产品,我需要在Stripe中创建100个SKU。
我尝试插入200个产品的测试数据集,这意味着(200个产品+(200 x 100 SKU))= 20200个请求。 我从Stripe收到一个令人惊讶的“超出请求速率限制”错误。 不到创建记录的一半...:(
“超出请求速率限制”是问题的核心。
现在,插入过程如下(x 200):
我需要解决此Stripe API速率限制错误的解决方案。 我有几种解决方案:
能够在给定的时间内增加Stripe rate API限制。 不确定是否可以。
能够使用不同的Stripe键,然后将其旋转,以执行管理工作,例如在Stripe中插入多个产品/ SKU。 最终在生产中,能够以编程方式为每个用户创建1个Stripe键,因此每个用户都有自己的限制。 不确定是否可以。
在javascript中减慢插入过程。 不知道该怎么执行。 此外,云函数的JavaScript预算/限制为60秒。所以我不能耽误太多。
使用发布/订阅(?)或Firestore触发器进行延迟工作 例如,在Firestore中有一个整数,表示每个函数调用都会递增,并且同一函数会监听写入内容以重新递增其编号等,等等,等等,直到第100个SKU的编号等于100。该解决方案将按条带化顺序写入100个SKU。 不确定这样做是否真的会减慢工作速度,使其不会超出API速率限制。另外,这样的解决方案将花费很多钱:仅针对一种产品,进行100多次Firestore写入,以及执行100多次函数调用来执行这些写入,这意味着对200种产品而言为20000 + / 20000 +。那太贵了。
在用户付款时执行即时插入。 付款请求API调用后,服务器端算法可能如下所示:
Create order in Stripe
If error 'No such sku...' catched {
For each SKU { // Ideally filter here SKUs to create (only those in error)
If price not between 1 and 100 {
continue // Bad price, not legit
}
Create SKU in Stripe
If error 'Already exists' {
continue // no creation needed for that SKU
}
If error 'No such product...' catched {
If productId does not exists in Firestore {
continue // Bad productId, not legit
}
Create product in Stripe
}
Create SKU in Stripe
}
}
Create order in Stripe
最后一个解决方案可以完成这项工作。 但是,这可能会给用户执行付款带来一些延迟,这可能会增加压力。另外,它可能会增加营业时间内的Stripe呼叫。同时进行的多次购买可能会导致Stripe API速率限制错误,尤其是在配备精良的购物车中(例如,购物车中平均有30种产品,因此在最坏的情况下,付款期间有30+个HTTPS调用,乘以1000个用户= 30000个调用= >条带错误)。对于给定产品,该问题可能会随着时间的推移而减少,因为一旦创建了SKU,便会确定地创建它。尽管如此,由于会有新产品出现,所以每天创建时SKU为零的产品仍然存在问题。
您怎么看? 您还有其他想法吗?
答案 0 :(得分:0)
解决方案3和解决方案5进行一些调整后效果最佳。
解决方案3:您可以使用async模块的forEachLimit或队列来限制对Stripe的并发请求数。
解决方案5:即时插入也是一个不错的选择,因为它不会同时在Stripe服务器上增加太多负载。关于您在工作时间内会遇到相同错误的担忧,这是非常罕见的情况,因为Stripe API的构建可以很好地执行。但是,如果您对此仍然有疑问,可以做一个在非工作时间添加SKU的背景流程,它将继续为您创建SKU,而不会遇到Stripe API速率限制错误。
解决方案6(修改后的解决方案5):只需及时插入,但每当在购物车中输入产品时,都会向您的服务器创建一个额外的API请求,然后该产品将检查Stripe中是否存在SKU,如果没有,则创建它在购物车付款发生之前在后台进行。
答案 1 :(得分:0)
具有相同的想法(JIT),但将SKU创建从付款时间转移到了产品选择时间。每次选择产品时,请尝试在Stripe中创建产品及其当前的SKU(价格变化)。这样,Stripe调用应该在时间上更加分散。也许它会以更多的API调用结束,因为我们选择产品的次数比我们支付的次数还多,因为用户可以选择和取消选择产品,所以他们在旅途中选择的产品可能比购物车中最终支付的总和更多?
相同的想法(JIT),但SKU缓存在Algolia或Firebase中,因此我可以执行“此SKU是否存在?”调用而无需查询Stripe,如果在create调用之前执行了存在性测试(我们不会盲目调用Stripe.skus.create()),这将减少Stripe调用。缺点是,Firebase和Algolia暴露在前端,因此SKU和价格也将存在,这是潜在的威胁来源,因此必须使用服务器专用的唯一索引。