trustbase-seller-backend 0.7.8 → 0.7.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -175,9 +175,22 @@ function isTunnelBuyerRequest(req, clientIP) {
175
175
  return TUNNEL_BUYER_PATHS.some(p => paths.some(x => x === p || x.startsWith(p + '/')));
176
176
  }
177
177
 
178
+ function getRateLimitClientIP(req, socketIP) {
179
+ const isLoopback = socketIP === '127.0.0.1' || socketIP === '::1' || /^127\./.test(socketIP);
180
+ // 2026-10-18 fix: 公网经隧道时, socket 对端恒为 127.0.0.1,
181
+ // 若直接用 socketIP 做限流桶 key, 全体公网买家会共享一个桶。
182
+ // 只在"回环 + 隧道头"时采信 XFF 第一个非空 IP, 否则回退 socketIP。
183
+ if (isLoopback && String(req.headers['x-tb-tunnel'] || '') === '1') {
184
+ const first = String(req.headers['x-forwarded-for'] || '').split(',')[0].trim();
185
+ if (first) return first;
186
+ }
187
+ return socketIP;
188
+ }
189
+
178
190
  function requireAPIKey(skipLAN = true, exemptPaths = []) { return (req, res, next) => {
179
- // 获取客户端 IP
180
- const clientIP = (req.ip || req.connection.remoteAddress || '').replace('::ffff:', '');
191
+ // 获取 socket 对端 IP (用于隧道回环判定) 与限流桶 IP (用于限流)
192
+ const socketIP = (req.ip || req.connection.remoteAddress || '').replace('::ffff:', '');
193
+ const clientIP = getRateLimitClientIP(req, socketIP);
181
194
  // 1. 检查 IP 黑名单
182
195
  if ((0, intrusion_detection_1.isIPBlacklisted)(clientIP)) {
183
196
  return res.status(403).json({
@@ -211,7 +224,7 @@ function requireAPIKey(skipLAN = true, exemptPaths = []) { return (req, res,
211
224
  // 而商户机默认 REQUIRE_API_KEY_FOR_LAN=1 → 回环也不放行 → 买家拿到 401, 公网店店等于不可用。
212
225
  // 口径收窄到三者同时成立: ① 来源是回环(只有本机进程能发这个头) ② 带 X-TB-Tunnel 头(隧道客户端转发时加)
213
226
  // ③ 命中买家面路径(商品/订单读)。管理面 API 一律仍要密钥。
214
- if (isTunnelBuyerRequest(req, clientIP)) {
227
+ if (isTunnelBuyerRequest(req, socketIP)) {
215
228
  return next();
216
229
  }
217
230
  // 跳过局域网(开发模式)
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "trustbase-seller-backend",
3
- "version": "0.7.8",
3
+ "version": "0.7.9",
4
4
  "description": "TrustBase Seller Backend (merchant edition) — 商品上链/订单/支付/质押 write API for TrustBase 保障链生态. 单卖家自托管形态: 签名 key 即卖家身份, 私钥不出门.",
5
5
  "main": "run-unified.js",
6
6
  "bin": {