Skip to content

Commit c7d7e66

Browse files
Merge branch 'main' into fix/ins-291
2 parents 6394f7a + ddb9583 commit c7d7e66

File tree

4 files changed

+124
-52
lines changed

4 files changed

+124
-52
lines changed

pkg/detectors/http.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ func NewDetectorTransport(T http.RoundTripper) http.RoundTripper {
9494
}
9595

9696
func isLocalIP(ip net.IP) bool {
97-
if ip.IsLoopback() || ip.IsLinkLocalUnicast() || ip.IsLinkLocalMulticast() || ip.IsPrivate() {
97+
if ip.IsLoopback() || ip.IsLinkLocalUnicast() || ip.IsLinkLocalMulticast() || ip.IsPrivate() || ip.IsUnspecified() {
9898
return true
9999
}
100100

pkg/detectors/http_test.go

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,30 @@ func TestWithNoLocalIP(t *testing.T) {
2222
assert.ErrorIs(t, err, ErrNoLocalIP)
2323
})
2424

25+
t.Run("Prevents dialing wildcard IP", func(t *testing.T) {
26+
client := &http.Client{}
27+
WithNoLocalIP()(client)
28+
29+
transport, ok := client.Transport.(*http.Transport)
30+
assert.True(t, ok, "Expected transport to be *http.Transport")
31+
32+
_, err := transport.DialContext(context.Background(), "tcp", "0.0.0.0:8080")
33+
assert.Error(t, err)
34+
assert.ErrorIs(t, err, ErrNoLocalIP)
35+
})
36+
37+
t.Run("Prevents dialing IPv6 wildcard IP", func(t *testing.T) {
38+
client := &http.Client{}
39+
WithNoLocalIP()(client)
40+
41+
transport, ok := client.Transport.(*http.Transport)
42+
assert.True(t, ok, "Expected transport to be *http.Transport")
43+
44+
_, err := transport.DialContext(context.Background(), "tcp", "[::]:8080")
45+
assert.Error(t, err)
46+
assert.ErrorIs(t, err, ErrNoLocalIP)
47+
})
48+
2549
t.Run("Allows dialing non-local host", func(t *testing.T) {
2650
client := &http.Client{}
2751
WithNoLocalIP()(client)
@@ -81,6 +105,8 @@ func TestIsLocalIP(t *testing.T) {
81105
{"Loopback IPv6", net.ParseIP("::1"), true},
82106
{"Private IPv4", net.ParseIP("192.168.1.1"), true},
83107
{"Private IPv6", net.ParseIP("fd00::1"), true},
108+
{"Unspecified IPv4", net.ParseIP("0.0.0.0"), true},
109+
{"Unspecified IPv6", net.ParseIP("::"), true},
84110
{"Public IPv4", net.ParseIP("8.8.8.8"), false},
85111
{"Public IPv6", net.ParseIP("2001:4860:4860::8888"), false},
86112
}

pkg/detectors/tableau/tableau.go

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,9 @@ func (s Scanner) FromData(ctx context.Context, verify bool, data []byte) (result
9797
result.Verified = isVerified
9898
maps.Copy(result.ExtraData, extraData)
9999
result.SetVerificationError(verificationErr, tokenName, tokenSecret, endpoint)
100+
if isVerified {
101+
result.AnalysisInfo = map[string]string{"tokenName": tokenName, "patSecret": tokenSecret, "endpoint": endpoint}
102+
}
100103
}
101104
results = append(results, result)
102105
}

pkg/detectors/tableau/tableau_integration_test.go

Lines changed: 94 additions & 51 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,11 @@ func TestTableau_FromChunk(t *testing.T) {
6969
"verification_status": "valid",
7070
"auth_token_received": "true",
7171
},
72+
AnalysisInfo: map[string]string{
73+
"endpoint": tableauURL,
74+
"patSecret": tokenSecret,
75+
"tokenName": tokenName,
76+
},
7277
},
7378
},
7479
wantErr: false,
@@ -174,57 +179,6 @@ func TestTableau_FromChunk(t *testing.T) {
174179
want: nil, // Should not find due to invalid secret format
175180
wantErr: false,
176181
},
177-
{
178-
name: "found multiple, mixed verification results with URLs",
179-
s: Scanner{},
180-
args: args{
181-
ctx: context.Background(),
182-
data: []byte(fmt.Sprintf(`
183-
name1 = '%s'
184-
name2 = '%s'
185-
secret = '%s'
186-
secret2 = '%s'
187-
server1 = '%s'
188-
server2 = '%s'
189-
`, tokenName, inactiveTokenName, tokenSecret, inactiveTokenSecret, tableauURL, invalidURL)),
190-
verify: true,
191-
},
192-
want: []detectors.Result{
193-
{
194-
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
195-
Verified: true, // tokenName + tokenSecret + valid URL
196-
},
197-
{
198-
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
199-
Verified: false, // tokenName + tokenSecret + invalid URL
200-
},
201-
{
202-
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
203-
Verified: false, // tokenName + inactiveTokenSecret + valid URL
204-
},
205-
{
206-
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
207-
Verified: false, // tokenName + inactiveTokenSecret + invalid URL
208-
},
209-
{
210-
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
211-
Verified: false, // inactiveTokenName + tokenSecret + valid URL
212-
},
213-
{
214-
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
215-
Verified: false, // inactiveTokenName + tokenSecret + invalid URL
216-
},
217-
{
218-
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
219-
Verified: false, // inactiveTokenName + inactiveTokenSecret + valid URL
220-
},
221-
{
222-
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
223-
Verified: false, // inactiveTokenName + inactiveTokenSecret + invalid URL
224-
},
225-
},
226-
wantErr: false,
227-
},
228182
}
229183

230184
for _, tt := range tests {
@@ -264,3 +218,92 @@ func TestTableau_FromChunk(t *testing.T) {
264218
})
265219
}
266220
}
221+
222+
func TestTableau_FromChunk_MultipleMixedVerificationResults(t *testing.T) {
223+
ctx, cancel := context.WithTimeout(context.Background(), time.Second*5)
224+
defer cancel()
225+
226+
testSecrets, err := common.GetSecret(ctx, "trufflehog-testing", "detectors6")
227+
if err != nil {
228+
t.Fatalf("could not get test secrets from GCP: %s", err)
229+
}
230+
231+
tokenName := testSecrets.MustGetField("TABLEAU_TOKEN_NAME")
232+
tokenSecret := testSecrets.MustGetField("TABLEAU_TOKEN_SECRET")
233+
inactiveTokenName := testSecrets.MustGetField("TABLEAU_INACTIVE_TOKEN_NAME")
234+
inactiveTokenSecret := testSecrets.MustGetField("TABLEAU_INACTIVE_TOKEN_SECRET")
235+
tableauURL := testSecrets.MustGetField("TABLEAU_VALID_POD_NAME")
236+
invalidURL := testSecrets.MustGetField("TABLEAU_INVALID_POD_NAME")
237+
238+
scanner := Scanner{}
239+
scanner.UseFoundEndpoints(true)
240+
241+
data := []byte(fmt.Sprintf(`
242+
name1 = '%s'
243+
name2 = '%s'
244+
secret = '%s'
245+
secret2 = '%s'
246+
server1 = '%s'
247+
server2 = '%s'
248+
`, tokenName, inactiveTokenName, tokenSecret, inactiveTokenSecret, tableauURL, invalidURL))
249+
250+
want := []detectors.Result{
251+
{
252+
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
253+
Verified: true, // tokenName + tokenSecret + valid URL
254+
},
255+
{
256+
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
257+
Verified: false, // tokenName + tokenSecret + invalid URL
258+
},
259+
{
260+
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
261+
Verified: false, // tokenName + inactiveTokenSecret + valid URL
262+
},
263+
{
264+
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
265+
Verified: false, // tokenName + inactiveTokenSecret + invalid URL
266+
},
267+
{
268+
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
269+
Verified: false, // inactiveTokenName + tokenSecret + valid URL
270+
},
271+
{
272+
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
273+
Verified: false, // inactiveTokenName + tokenSecret + invalid URL
274+
},
275+
{
276+
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
277+
Verified: false, // inactiveTokenName + inactiveTokenSecret + valid URL
278+
},
279+
{
280+
DetectorType: detectorspb.DetectorType_TableauPersonalAccessToken,
281+
Verified: false, // inactiveTokenName + inactiveTokenSecret + invalid URL
282+
},
283+
}
284+
285+
got, err := scanner.FromData(context.Background(), true, data)
286+
if err != nil {
287+
t.Fatalf("Tableau.FromData() unexpected error: %v", err)
288+
}
289+
290+
if len(got) != len(want) {
291+
t.Errorf("Tableau.FromData() got %d results, want %d", len(got), len(want))
292+
}
293+
for i := range got {
294+
if len(got[i].Raw) == 0 {
295+
t.Fatalf("no raw secret present: \n %+v", got[i])
296+
}
297+
if (got[i].VerificationError() != nil) != false {
298+
t.Errorf("Tableau.FromData() verificationError = %v, wantVerificationErr %v", got[i].VerificationError(), false)
299+
}
300+
}
301+
ignoreOpts := []cmp.Option{
302+
cmpopts.IgnoreFields(detectors.Result{}, "Raw", "RawV2", "verificationError", "ExtraData", "AnalysisInfo"),
303+
cmpopts.IgnoreUnexported(detectors.Result{}),
304+
}
305+
306+
if diff := cmp.Diff(got, want, ignoreOpts...); diff != "" {
307+
t.Errorf("Tableau.FromData() diff: (-got +want)\n%s", diff)
308+
}
309+
}

0 commit comments

Comments
 (0)