mirror of
https://github.com/MHSanaei/3x-ui.git
synced 2026-11-02 19:25:05 +03:00
fix(sub): resolve legacy socket fallback fronts on PostgreSQL too
The socket-front lookup filtered and extracted settings.fallbacks with SQLite's json_valid, JSON_TYPE and json_extract, which PostgreSQL does not have, so on PostgreSQL the statement failed and a legacy @socket child never got its front's address and security in its links. The lookup now selects the inbounds whose settings mention fallbacks and parses them in Go, which works on both databases and still skips an inbound whose settings do not decode.
This commit is contained in:
@@ -2048,8 +2048,10 @@ func TestSub_LegacyFallbackMasterLookedUpOncePerRequest(t *testing.T) {
|
||||
|
||||
scans := 0
|
||||
count := func(tx *gorm.DB) {
|
||||
if strings.Contains(tx.Statement.SQL.String(), "$.fallbacks") {
|
||||
scans++
|
||||
for _, v := range tx.Statement.Vars {
|
||||
if v == "%fallbacks%" {
|
||||
scans++
|
||||
}
|
||||
}
|
||||
}
|
||||
_ = db.Callback().Query().After("gorm:query").Register("test:count_front_scans", count)
|
||||
|
||||
+10
-8
@@ -3607,20 +3607,22 @@ func (s *SubService) socketFront(key socketFrontKey) *model.Inbound {
|
||||
Listen string
|
||||
Port int
|
||||
StreamSettings string
|
||||
Fallbacks string
|
||||
Settings string
|
||||
}
|
||||
// json_valid keeps one inbound with unreadable settings from failing the
|
||||
// whole statement and hiding every front.
|
||||
// Parsed here, not with SQL JSON functions, so the lookup works on PostgreSQL too and one
|
||||
// inbound with unreadable settings cannot hide every front.
|
||||
if err := database.GetDB().Model(model.Inbound{}).
|
||||
Select("node_id, listen, port, stream_settings, json_extract(settings, '$.fallbacks') AS fallbacks").
|
||||
Where("CASE WHEN json_valid(settings) THEN JSON_TYPE(settings, '$.fallbacks') END = 'array'").
|
||||
Select("node_id, listen, port, stream_settings, settings").
|
||||
Where("settings LIKE ?", "%fallbacks%").
|
||||
Order("id ASC").Scan(&fronts).Error; err != nil {
|
||||
return nil
|
||||
}
|
||||
for _, front := range fronts {
|
||||
var fallbacks []any
|
||||
_ = json.Unmarshal([]byte(front.Fallbacks), &fallbacks)
|
||||
for _, fallback := range fallbacks {
|
||||
var parsed struct {
|
||||
Fallbacks []any `json:"fallbacks"`
|
||||
}
|
||||
_ = json.Unmarshal([]byte(front.Settings), &parsed)
|
||||
for _, fallback := range parsed.Fallbacks {
|
||||
rule, _ := fallback.(map[string]any)
|
||||
dest, _ := rule["dest"].(string)
|
||||
k := socketFrontKey{node: nodeKeyOf(front.NodeID), dest: dest}
|
||||
|
||||
Reference in New Issue
Block a user