sync: 同步生产版 v1.0.4 并脱敏

This commit is contained in:
MiFaZhan
2026-10-29 15:03:39 +08:00
parent fed9459244
commit 2d045591b7
32 changed files with 695 additions and 80 deletions
@@ -1,15 +1,80 @@
package upstreamimpl
import (
"context"
"encoding/json"
"net/http"
"time"
"fmt"
"git.5iot.com/iotlcm-public/iotlcm-upstream-proxy/internal/model"
"github.com/gogf/gf/v2/frame/g"
"strings"
"git.5iot.com/iotlcm-public/iotlcm-upstream-proxy/internal/model"
"github.com/gogf/gf/v2/errors/gerror"
"github.com/gogf/gf/v2/net/gclient"
)
const (
// gatewayBatchTimeoutConfigKey 限制单次批量转发的最长等待,防止上游异常时无限占用连接。
gatewayBatchTimeoutConfigKey = "gateway.batchTimeout"
// defaultGatewayBatchTimeout 覆盖 100 张卡按单卡 10 秒预算的最坏耗时,并留有余量。
defaultGatewayBatchTimeout = 20 * time.Minute
// defaultDataServiceTimeout 是数据开停转发的独立预算。
defaultDataServiceTimeout = 210 * time.Second
)
// configureGatewayTimeout 让响应头等待与整次请求使用同一预算,避免默认30秒提前中断。
// upstream-chan 对批量操作按卡串行调用运营商接口,耗时随卡数线性增长;
// 因此批量请求不能沿用 gclient 默认的 30 秒响应头超时,否则请求仍在办理就会被判为失败。
func configureGatewayTimeout(ctx context.Context, client *gclient.Client, path string, count int, perCard time.Duration) {
if path == "/sim/change/sim-apn" || path == "/sim/query/sim-apn-capability" {
client.SetContentType("application/json")
}
applyGatewayTimeout(client, path, count, perCard,
configDuration(ctx, "gateway.dataServiceTimeout", defaultDataServiceTimeout),
configDuration(ctx, gatewayBatchTimeoutConfigKey, defaultGatewayBatchTimeout))
}
// applyGatewayTimeout 计算并应用单次转发预算:整次请求与响应头等待必须一致,
// 否则响应头超时会在业务仍在办理时提前中断请求。
func applyGatewayTimeout(client *gclient.Client, path string, count int, perCard, dataServiceTimeout, batchTimeout time.Duration) {
if count < 1 {
count = 1
}
if perCard <= 0 {
perCard = 10 * time.Second
}
timeout := perCard * time.Duration(count)
if path == "/sim/change/sim-apn" {
timeout = dataServiceTimeout
if timeout <= 0 {
timeout = defaultDataServiceTimeout
}
} else if batchTimeout > 0 && timeout > batchTimeout {
timeout = batchTimeout
}
client.SetTimeout(timeout)
if transport, ok := client.Transport.(*http.Transport); ok {
transport.ResponseHeaderTimeout = timeout
}
}
// configDuration 读取时长配置,兼容写成 "20m" 字符串或秒数整数两种形式。
func configDuration(ctx context.Context, key string, fallback time.Duration) time.Duration {
value := g.Cfg().MustGet(ctx, key)
if value == nil || value.IsNil() {
return fallback
}
if duration := value.Duration(); duration >= time.Second {
return duration
}
if seconds := value.Int(); seconds > 0 {
return time.Duration(seconds) * time.Second
}
return fallback
}
func readGatewayResponse(response *gclient.Response) (model.SimBaseResJson, error) {
defer response.Close()
body := response.ReadAll()