@@ -2,17 +2,18 @@ package skybiometry
2
2
3
3
import (
4
4
"context"
5
- regexp "github.com/wasilibs/go-re2"
5
+ "fmt"
6
+ "io"
6
7
"net/http"
7
- "net/url"
8
- "strings "
8
+
9
+ regexp "github.com/wasilibs/go-re2 "
9
10
10
11
"github.com/trufflesecurity/trufflehog/v3/pkg/common"
11
12
"github.com/trufflesecurity/trufflehog/v3/pkg/detectors"
12
13
"github.com/trufflesecurity/trufflehog/v3/pkg/pb/detectorspb"
13
14
)
14
15
15
- type Scanner struct {
16
+ type Scanner struct {
16
17
detectors.DefaultMultiPartCredentialProvider
17
18
}
18
19
@@ -37,43 +38,31 @@ func (s Scanner) Keywords() []string {
37
38
func (s Scanner ) FromData (ctx context.Context , verify bool , data []byte ) (results []detectors.Result , err error ) {
38
39
dataStr := string (data )
39
40
40
- matches := keyPat .FindAllStringSubmatch (dataStr , - 1 )
41
- secretMatches := secretPat .FindAllStringSubmatch (dataStr , - 1 )
41
+ uniqueKeyMatches , uniqueSecretMatches := make (map [string ]struct {}), make (map [string ]struct {})
42
42
43
- for _ , match := range matches {
44
- if len (match ) != 2 {
45
- continue
46
- }
47
- resMatch := strings .TrimSpace (match [1 ])
43
+ for _ , match := range keyPat .FindAllStringSubmatch (dataStr , - 1 ) {
44
+ uniqueKeyMatches [match [1 ]] = struct {}{}
45
+ }
46
+
47
+ for _ , match := range secretPat .FindAllStringSubmatch (dataStr , - 1 ) {
48
+ uniqueSecretMatches [match [1 ]] = struct {}{}
49
+ }
48
50
49
- for _ , secretMatch := range secretMatches {
50
- if len (secretMatch ) != 2 {
51
+ for key := range uniqueKeyMatches {
52
+ for secret := range uniqueSecretMatches {
53
+ if key == secret {
51
54
continue
52
55
}
53
- resSecretMatch := strings .TrimSpace (secretMatch [1 ])
54
56
55
57
s1 := detectors.Result {
56
58
DetectorType : detectorspb .DetectorType_SkyBiometry ,
57
- Raw : []byte (resSecretMatch ),
59
+ Raw : []byte (secret ),
58
60
}
59
61
60
62
if verify {
61
-
62
- payload := url.Values {}
63
- payload .Add ("api_key" , resMatch )
64
- payload .Add ("api_secret" , resSecretMatch )
65
-
66
- req , err := http .NewRequestWithContext (ctx , "GET" , "https://api.skybiometry.com/fc/account/authenticate?" + payload .Encode (), nil )
67
- if err != nil {
68
- continue
69
- }
70
- res , err := client .Do (req )
71
- if err == nil {
72
- defer res .Body .Close ()
73
- if res .StatusCode >= 200 && res .StatusCode < 300 {
74
- s1 .Verified = true
75
- }
76
- }
63
+ isVerified , verificationErr := verifySkyBiometery (ctx , client , key , secret )
64
+ s1 .Verified = isVerified
65
+ s1 .SetVerificationError (verificationErr )
77
66
}
78
67
79
68
results = append (results , s1 )
@@ -90,3 +79,31 @@ func (s Scanner) Type() detectorspb.DetectorType {
90
79
func (s Scanner ) Description () string {
91
80
return "SkyBiometry is a facial recognition service. SkyBiometry API keys can be used to access and utilize their facial recognition API."
92
81
}
82
+
83
+ func verifySkyBiometery (ctx context.Context , client * http.Client , apiKey , apiSecret string ) (bool , error ) {
84
+ apiURL := fmt .Sprintf ("https://api.skybiometry.com/fc/account/authenticate?api_key=%s&api_secret=%s" , apiKey , apiSecret )
85
+
86
+ req , err := http .NewRequestWithContext (ctx , "GET" , apiURL , nil )
87
+ if err != nil {
88
+ return false , err
89
+ }
90
+
91
+ resp , err := client .Do (req )
92
+ if err != nil {
93
+ return false , err
94
+ }
95
+
96
+ defer func () {
97
+ _ , _ = io .Copy (io .Discard , resp .Body )
98
+ _ = resp .Body .Close ()
99
+ }()
100
+
101
+ switch resp .StatusCode {
102
+ case http .StatusOK :
103
+ return true , nil
104
+ case http .StatusBadRequest , http .StatusUnauthorized :
105
+ return false , nil
106
+ default :
107
+ return false , fmt .Errorf ("unexpected status code: %d" , resp .StatusCode )
108
+ }
109
+ }
0 commit comments