Refactored detection logic to include ports and a confidence score
This commit is contained in:
227
protocol/match_test.go
Normal file
227
protocol/match_test.go
Normal file
@@ -0,0 +1,227 @@
|
||||
package protocol
|
||||
|
||||
import (
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestMatch(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string
|
||||
magic string
|
||||
input []byte
|
||||
expected bool
|
||||
}{
|
||||
// Basic escaping tests
|
||||
{
|
||||
name: "escape star",
|
||||
magic: "\\*",
|
||||
input: []byte("*"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "escape star no match",
|
||||
magic: "\\*",
|
||||
input: []byte("a"),
|
||||
expected: false,
|
||||
},
|
||||
{
|
||||
name: "escape star with longer input",
|
||||
magic: "\\*",
|
||||
input: []byte("*extra"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "escape question mark",
|
||||
magic: "\\?",
|
||||
input: []byte("?"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "escape question mark no match",
|
||||
magic: "\\?",
|
||||
input: []byte("a"),
|
||||
expected: false,
|
||||
},
|
||||
{
|
||||
name: "escape backslash",
|
||||
magic: "\\\\",
|
||||
input: []byte("\\"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "escape backslash no match",
|
||||
magic: "\\\\",
|
||||
input: []byte("a"),
|
||||
expected: false,
|
||||
},
|
||||
{
|
||||
name: "escape backslash with longer input",
|
||||
magic: "\\\\",
|
||||
input: []byte("\\extra"),
|
||||
expected: true,
|
||||
},
|
||||
|
||||
// Multiple escaped characters
|
||||
{
|
||||
name: "multiple escaped characters",
|
||||
magic: "\\*\\?\\\\",
|
||||
input: []byte("*?\\"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "multiple escaped characters with longer input",
|
||||
magic: "\\*\\?\\\\",
|
||||
input: []byte("*?\\extra"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "mixed escaped characters",
|
||||
magic: "a\\*b\\?c\\\\d",
|
||||
input: []byte("a*b?c\\d"),
|
||||
expected: true,
|
||||
},
|
||||
|
||||
// Escaping combined with wildcards
|
||||
{
|
||||
name: "star then escaped star",
|
||||
magic: "*\\*",
|
||||
input: []byte("anything*"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "star then escaped star must end with star",
|
||||
magic: "*\\*",
|
||||
input: []byte("anything"),
|
||||
expected: false,
|
||||
},
|
||||
{
|
||||
name: "star then escaped question",
|
||||
magic: "*\\?",
|
||||
input: []byte("hello?"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "question then escaped star",
|
||||
magic: "?\\*",
|
||||
input: []byte("a*"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "question then escaped star wrong second char",
|
||||
magic: "?\\*",
|
||||
input: []byte("aa"),
|
||||
expected: false,
|
||||
},
|
||||
{
|
||||
name: "wildcards between escaped characters",
|
||||
magic: "*\\\\*",
|
||||
input: []byte("path\\to\\file"),
|
||||
expected: true,
|
||||
},
|
||||
|
||||
// Real-world escaping scenarios
|
||||
{
|
||||
name: "file pattern with literal star",
|
||||
magic: "file\\*.txt",
|
||||
input: []byte("file*.txt"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "file pattern with literal star no match",
|
||||
magic: "file\\*.txt",
|
||||
input: []byte("filex.txt"),
|
||||
expected: false,
|
||||
},
|
||||
{
|
||||
name: "pattern with literal question",
|
||||
magic: "what\\?*",
|
||||
input: []byte("what? is this"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "pattern with literal question must have question",
|
||||
magic: "what\\?*",
|
||||
input: []byte("what is this"),
|
||||
expected: false,
|
||||
},
|
||||
{
|
||||
name: "database like pattern",
|
||||
magic: "table_\\*_\\?",
|
||||
input: []byte("table_*_?"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "database like pattern with longer input",
|
||||
magic: "table_\\*_\\?",
|
||||
input: []byte("table_*_?backup"),
|
||||
expected: true,
|
||||
},
|
||||
|
||||
// Edge cases with escaping
|
||||
{
|
||||
name: "backslash at end of magic",
|
||||
magic: "test\\",
|
||||
input: []byte("test\\"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "backslash at end of magic no match",
|
||||
magic: "test\\",
|
||||
input: []byte("test"),
|
||||
expected: false,
|
||||
},
|
||||
{
|
||||
name: "only backslash",
|
||||
magic: "\\",
|
||||
input: []byte("\\"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "consecutive backslashes",
|
||||
magic: "\\\\\\\\",
|
||||
input: []byte("\\\\"),
|
||||
expected: true,
|
||||
},
|
||||
|
||||
// Mixed scenarios with both escaping and wildcards
|
||||
{
|
||||
name: "escaped wildcards in middle",
|
||||
magic: "a*\\?b*\\*c",
|
||||
input: []byte("aanything?banything*c"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "escaped wildcards pattern",
|
||||
magic: "select * from \\*",
|
||||
input: []byte("select * from *"),
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
name: "escaped wildcards pattern with longer input",
|
||||
magic: "select * from *\\*",
|
||||
input: []byte("select name from users*"),
|
||||
expected: true,
|
||||
},
|
||||
}
|
||||
|
||||
for _, test := range tests {
|
||||
t.Run(test.name, func(t *testing.T) {
|
||||
result := Match(test.magic, test.input)
|
||||
if result != test.expected {
|
||||
t.Errorf("Match(%q, %q) = %v, want %v",
|
||||
test.magic, string(test.input), result, test.expected)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
// Benchmark test with escaping
|
||||
func BenchmarkMatch(b *testing.B) {
|
||||
magic := "file\\*\\?*\\\\*.txt"
|
||||
input := []byte("file*?name\\backup.txt")
|
||||
|
||||
b.ResetTimer()
|
||||
for b.Loop() {
|
||||
Match(magic, input)
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user