diff --git a/internal/agent/canvas/loop_subgraph.go b/internal/agent/canvas/loop_subgraph.go index 5b7eb1426..51ea1c9a3 100644 --- a/internal/agent/canvas/loop_subgraph.go +++ b/internal/agent/canvas/loop_subgraph.go @@ -37,6 +37,7 @@ package canvas import ( "context" "fmt" + "slices" "strings" "ragflow/internal/agent/workflowx" @@ -707,9 +708,9 @@ func evalDictOp(m map[string]any, op string, _ any) (bool, error) { func evalListOp(lst []any, op string, value any) (bool, error) { switch op { case "contains": - return listContains(lst, value), nil + return slices.Contains(lst, value), nil case "not contains": - return !listContains(lst, value), nil + return !slices.Contains(lst, value), nil case "is": return listEqual(lst, value), nil case "is not": @@ -722,15 +723,6 @@ func evalListOp(lst []any, op string, value any) (bool, error) { return false, fmt.Errorf("invalid operator: %s (list variable)", op) } -func listContains(lst []any, value any) bool { - for _, x := range lst { - if x == value { - return true - } - } - return false -} - func listEqual(lst []any, value any) bool { other, ok := value.([]any) if !ok { diff --git a/internal/agent/component/llm_test.go b/internal/agent/component/llm_test.go index d041f1986..b977b96ec 100644 --- a/internal/agent/component/llm_test.go +++ b/internal/agent/component/llm_test.go @@ -15,6 +15,7 @@ package component import ( "context" "errors" + "slices" "testing" "github.com/cloudwego/eino/schema" @@ -178,14 +179,7 @@ func TestLLM_Invoke_InvokerError(t *testing.T) { func TestLLM_Registered(t *testing.T) { names := RegisteredNames() - found := false - for _, n := range names { - if n == "llm" { - found = true - break - } - } - if !found { + if !slices.Contains(names, "llm") { t.Fatalf("LLM not registered; names=%v", names) } // And a factory round-trip. diff --git a/internal/agent/component/parallel_test.go b/internal/agent/component/parallel_test.go index 16cca46bf..31ec3e1d2 100644 --- a/internal/agent/component/parallel_test.go +++ b/internal/agent/component/parallel_test.go @@ -35,6 +35,7 @@ package component import ( "context" + "slices" "testing" ) @@ -45,14 +46,7 @@ import ( // assert their absence here. func TestParallel_Registered(t *testing.T) { names := RegisteredNames() - hasParallel := false - for _, n := range names { - if n == "parallel" { - hasParallel = true - break - } - } - if !hasParallel { + if !slices.Contains(names, "parallel") { t.Errorf("Parallel not registered; RegisteredNames=%v", names) } } diff --git a/internal/cli/filesystem/skill_hub/source/clawhub.go b/internal/cli/filesystem/skill_hub/source/clawhub.go index d62a74a21..d0b2f816f 100644 --- a/internal/cli/filesystem/skill_hub/source/clawhub.go +++ b/internal/cli/filesystem/skill_hub/source/clawhub.go @@ -25,6 +25,7 @@ import ( "net/http" "path/filepath" "regexp" + "slices" "sort" "strconv" "strings" @@ -905,24 +906,13 @@ func isSafePath(path string) bool { // Check for parent directory references parts := strings.Split(clean, string(filepath.Separator)) - for _, part := range parts { - if part == ".." { - return false - } - } - - return true + return !slices.Contains(parts, "..") } // isTextContent checks if content appears to be text (not binary) func isTextContent(data []byte) bool { // Check for null bytes (indicates binary) - for _, b := range data { - if b == 0 { - return false - } - } - return true + return !slices.Contains(data, 0) } func min(a, b int) int { diff --git a/internal/common/format.go b/internal/common/format.go index b8be5970d..fbd8dfcb2 100644 --- a/internal/common/format.go +++ b/internal/common/format.go @@ -20,6 +20,7 @@ import ( "encoding/base64" "fmt" "regexp" + "slices" "strconv" "strings" "time" @@ -40,12 +41,7 @@ func IsCompositeModelName(modelName string) bool { if len(parts) != 3 { return false } - for _, p := range parts { - if p == "" { - return false - } - } - return true + return !slices.Contains(parts, "") } func IsUUID(uuid string) bool { @@ -68,10 +64,8 @@ func ExtractCompositeName(modelName string) (string, string, string, error) { if len(parts) != 3 { return "", "", "", fmt.Errorf("invalid model name format") } - for _, p := range parts { - if p == "" { - return "", "", "", fmt.Errorf("invalid model name format") - } + if slices.Contains(parts, "") { + return "", "", "", fmt.Errorf("invalid model name format") } return parts[0], parts[1], parts[2], nil } diff --git a/internal/engine/infinity/chunk.go b/internal/engine/infinity/chunk.go index 6d6852e9c..efc3cbd52 100644 --- a/internal/engine/infinity/chunk.go +++ b/internal/engine/infinity/chunk.go @@ -2012,18 +2012,11 @@ func convertSelectFields(output []string, isSkillIndex ...bool) []string { // Add id and empty count if needed // For skill index, use skill_id instead of id - hasID := false idField := "id" if skillIndex { idField = "skill_id" } - for _, f := range result { - if f == idField { - hasID = true - break - } - } - if !hasID { + if !slices.Contains(result, idField) { result = append([]string{idField}, result...) } diff --git a/internal/harness/core/callback.go b/internal/harness/core/callback.go index 679082660..d9afc8e71 100644 --- a/internal/harness/core/callback.go +++ b/internal/harness/core/callback.go @@ -6,6 +6,7 @@ import ( "fmt" "io" "reflect" + "slices" ) // AgentCallbackInput is the input to the agent callback OnStart. @@ -102,14 +103,7 @@ func filterOptions(name string, opts []RunOption) []RunOption { tmp := &runOptions{} fn(tmp) if tmp.agentNames != nil { - match := false - for _, n := range tmp.agentNames { - if n == name { - match = true - break - } - } - if !match { + if !slices.Contains(tmp.agentNames, name) { continue } } @@ -152,14 +146,7 @@ func filterCallbackHandlersForNestedAgents(name string, opts []RunOption) []RunO tmp := &runOptions{} fn(tmp) if tmp.agentNames != nil { - match := false - for _, n := range tmp.agentNames { - if n == name { - match = true - break - } - } - if !match { + if !slices.Contains(tmp.agentNames, name) { continue } } diff --git a/internal/harness/events/store.go b/internal/harness/events/store.go index 0eba5c279..ead7549ef 100644 --- a/internal/harness/events/store.go +++ b/internal/harness/events/store.go @@ -2,6 +2,7 @@ package events import ( "context" + "slices" "time" ) @@ -60,14 +61,7 @@ func (f EventFilter) Matches(e *Event) bool { return false } if len(f.Types) > 0 { - matched := false - for _, t := range f.Types { - if e.Type == t { - matched = true - break - } - } - if !matched { + if !slices.Contains(f.Types, e.Type) { return false } } diff --git a/internal/harness/graph/graph/graph.go b/internal/harness/graph/graph/graph.go index e4052880b..6aefa8747 100644 --- a/internal/harness/graph/graph/graph.go +++ b/internal/harness/graph/graph/graph.go @@ -4,6 +4,7 @@ package graph import ( "context" "fmt" + "slices" "ragflow/internal/harness/graph/channels" "ragflow/internal/harness/graph/constants" @@ -158,14 +159,7 @@ func (g *stateGraph) AddEdge(from, to string) error { g.entryPoint = to } if to == constants.End { - found := false - for _, fp := range g.finishPoints { - if fp == from { - found = true - break - } - } - if !found { + if !slices.Contains(g.finishPoints, from) { g.finishPoints = append(g.finishPoints, from) } } diff --git a/internal/harness/graph/graph/message.go b/internal/harness/graph/graph/message.go index b8881893b..c51d32614 100644 --- a/internal/harness/graph/graph/message.go +++ b/internal/harness/graph/graph/message.go @@ -3,6 +3,7 @@ package graph import ( "context" "fmt" + "slices" "ragflow/internal/harness/graph/channels" "ragflow/internal/harness/graph/types" @@ -398,14 +399,7 @@ func (f *MessagesFilter) Filter(msgs []*Message) []*Message { for _, msg := range msgs { // Check role filter if len(f.roles) > 0 { - match := false - for _, role := range f.roles { - if msg.Role == role { - match = true - break - } - } - if !match { + if !slices.Contains(f.roles, msg.Role) { continue } } diff --git a/internal/harness/graph/pregel/write.go b/internal/harness/graph/pregel/write.go index cb278b5ca..8ef7295e1 100644 --- a/internal/harness/graph/pregel/write.go +++ b/internal/harness/graph/pregel/write.go @@ -3,6 +3,7 @@ package pregel import ( "context" "fmt" + "slices" "sync" "ragflow/internal/harness/graph/channels" @@ -331,10 +332,8 @@ func NewNonNullWriteValidator(whitelist ...string) *NonNullWriteValidator { } func (v *NonNullWriteValidator) Validate(entry *ChannelWriteEntry) error { - for _, channel := range v.whitelist { - if entry.Channel == channel { - return nil - } + if slices.Contains(v.whitelist, entry.Channel) { + return nil } if entry.Value == nil { diff --git a/internal/ingestion/compilation/extractor/dep_relation.go b/internal/ingestion/compilation/extractor/dep_relation.go index c0153305a..aacb9b8a9 100644 --- a/internal/ingestion/compilation/extractor/dep_relation.go +++ b/internal/ingestion/compilation/extractor/dep_relation.go @@ -4,7 +4,11 @@ package extractor -import "strings" +import ( + "slices" + "strings" +) + // Verb lemmatization — multi-language var verbLemma = map[string]string{ @@ -617,15 +621,15 @@ func extractCopula(text string, rootIdx int, tokens []DepToken, entityMap map[st var prepObj *Entity for _, c := range childrenOf(rootIdx, tokens) { - if !containsDep(c.Dep, cd.attrDeps) { + if !slices.Contains(cd.attrDeps, c.Dep) { continue } for _, cc := range childrenOf(c.Index, tokens) { - if !containsDep(cc.Dep, cd.prepDeps) { + if !slices.Contains(cd.prepDeps, cc.Dep) { continue } for _, gc := range childrenOf(cc.Index, tokens) { - if containsDep(gc.Dep, cd.objDeps) { + if slices.Contains(cd.objDeps, gc.Dep) { if ent := findEntityInSubtree(gc.Index, tokens, entityMap); ent != nil { prepObj = ent titleLemma = strings.ToLower(c.Text) @@ -678,15 +682,6 @@ func lookupVerb(verb, prep string) string { return depVerbRelations[verb] } -func containsDep(dep string, deps []string) bool { - for _, d := range deps { - if dep == d { - return true - } - } - return false -} - func childrenOf(idx int, tokens []DepToken) []DepToken { var kids []DepToken for _, t := range tokens { diff --git a/internal/service/nlp/term_weight_test.go b/internal/service/nlp/term_weight_test.go index a1efea53d..078e5b000 100644 --- a/internal/service/nlp/term_weight_test.go +++ b/internal/service/nlp/term_weight_test.go @@ -18,6 +18,7 @@ import ( "os" "path/filepath" "reflect" + "slices" "strings" "testing" ) @@ -713,14 +714,7 @@ func TestPretokenWithNumbers(t *testing.T) { t.Run("num=false filters single digits", func(t *testing.T) { result := d.Pretoken("5", false, true) // Single digit should be filtered when num=false - found := false - for _, r := range result { - if r == "5" { - found = true - break - } - } - if found { + if slices.Contains(result, "5") { t.Error("Single digit should be filtered when num=false") } }) diff --git a/internal/service/nlp/wordnet_test.go b/internal/service/nlp/wordnet_test.go index be4fc784f..5a88d7586 100644 --- a/internal/service/nlp/wordnet_test.go +++ b/internal/service/nlp/wordnet_test.go @@ -20,6 +20,7 @@ import ( "os" "path/filepath" "reflect" + "slices" "sort" "testing" ) @@ -122,14 +123,7 @@ func TestSynsets(t *testing.T) { names[i] = s.Name } for _, expectedName := range tt.checkNames { - found := false - for _, name := range names { - if name == expectedName { - found = true - break - } - } - if !found { + if !slices.Contains(names, expectedName) { t.Errorf("Synsets(%q, %q) did not contain expected synset %q, got %v", tt.lemma, tt.pos, expectedName, names) } diff --git a/internal/utility/ssrf.go b/internal/utility/ssrf.go index c837f981a..74a39c3d0 100644 --- a/internal/utility/ssrf.go +++ b/internal/utility/ssrf.go @@ -22,6 +22,7 @@ import ( "net" "net/http" "net/url" + "slices" "sort" "strings" "time" @@ -69,7 +70,7 @@ func AssertURLSafe(rawURL string) (hostname, resolvedIP string, err error) { } scheme := strings.ToLower(parsed.Scheme) - if !schemeAllowed(scheme) { + if !slices.Contains(AllowedURLSchemes, scheme) { sorted := append([]string(nil), AllowedURLSchemes...) sort.Strings(sorted) return "", "", fmt.Errorf("disallowed URL scheme: '%s'. Only %v are allowed", scheme, sorted) @@ -104,15 +105,6 @@ func AssertURLSafe(rawURL string) (hostname, resolvedIP string, err error) { return hostname, resolvedIP, nil } -func schemeAllowed(scheme string) bool { - for _, s := range AllowedURLSchemes { - if s == scheme { - return true - } - } - return false -} - // effectiveIP unwraps IPv4-mapped IPv6 addresses (e.g. ::ffff:127.0.0.1) so // the routability check sees the IPv4 form. Without this, an attacker could // bypass the guard with an IPv4-mapped IPv6 representation of a private host.