mirror of
https://github.com/trufflesecurity/trufflehog.git
synced 2024-11-10 07:04:24 +00:00
[analyze] Improve SquareUp analyzer and Implemented test (#3231)
* square analyzer fix assign team members to unbounded resources - unit test for square analyzer * refactoring --------- Co-authored-by: Abdul Basit <abasit@folio3.com>
This commit is contained in:
parent
5d7e6fc2fa
commit
c449129d75
3 changed files with 127 additions and 6 deletions
1
pkg/analyzer/analyzers/square/expected_output.json
Normal file
1
pkg/analyzer/analyzers/square/expected_output.json
Normal file
File diff suppressed because one or more lines are too long
|
@ -41,23 +41,43 @@ func secretInfoToAnalyzerResult(info *SecretInfo) *analyzers.AnalyzerResult {
|
|||
return nil
|
||||
}
|
||||
result := analyzers.AnalyzerResult{
|
||||
AnalyzerType: analyzerpb.AnalyzerType_Square,
|
||||
AnalyzerType: analyzerpb.AnalyzerType_Square,
|
||||
UnboundedResources: []analyzers.Resource{},
|
||||
Metadata: map[string]any{
|
||||
"team_members": info.Team.TeamMembers,
|
||||
"expires_at": info.Permissions.ExpiresAt,
|
||||
"client_id": info.Permissions.ClientID,
|
||||
"merchant_id": info.Permissions.MerchantID,
|
||||
"expires_at": info.Permissions.ExpiresAt,
|
||||
"client_id": info.Permissions.ClientID,
|
||||
"merchant_id": info.Permissions.MerchantID,
|
||||
},
|
||||
}
|
||||
|
||||
bindings, unboundedResources := getBindingsAndUnboundedResources(info.Permissions.Scopes)
|
||||
|
||||
result.Bindings = bindings
|
||||
result.UnboundedResources = unboundedResources
|
||||
result.UnboundedResources = append(result.UnboundedResources, unboundedResources...)
|
||||
result.UnboundedResources = append(result.UnboundedResources, getTeamMembersResources(info.Team)...)
|
||||
|
||||
return &result
|
||||
}
|
||||
|
||||
// Convert given list of team members into resources
|
||||
func getTeamMembersResources(team TeamJSON) []analyzers.Resource {
|
||||
teamMembersResources := make([]analyzers.Resource, len(team.TeamMembers))
|
||||
|
||||
for idx, teamMember := range team.TeamMembers {
|
||||
teamMembersResources[idx] = analyzers.Resource{
|
||||
Name: teamMember.FirstName + " " + teamMember.LastName,
|
||||
FullyQualifiedName: teamMember.Email,
|
||||
Type: "team_member",
|
||||
Metadata: map[string]any{
|
||||
"is_owner": teamMember.IsOwner,
|
||||
"created_at": teamMember.CreatedAt,
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
return teamMembersResources
|
||||
}
|
||||
|
||||
// Build a list of Bindings and UnboundedResources by referencing the category permissions list and
|
||||
// checking with the given scopes
|
||||
func getBindingsAndUnboundedResources(scopes []string) ([]analyzers.Binding, []analyzers.Resource) {
|
||||
|
|
100
pkg/analyzer/analyzers/square/square_test.go
Normal file
100
pkg/analyzer/analyzers/square/square_test.go
Normal file
|
@ -0,0 +1,100 @@
|
|||
package square
|
||||
|
||||
import (
|
||||
_ "embed"
|
||||
"encoding/json"
|
||||
"sort"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/trufflesecurity/trufflehog/v3/pkg/analyzer/analyzers"
|
||||
"github.com/trufflesecurity/trufflehog/v3/pkg/analyzer/config"
|
||||
"github.com/trufflesecurity/trufflehog/v3/pkg/common"
|
||||
"github.com/trufflesecurity/trufflehog/v3/pkg/context"
|
||||
)
|
||||
|
||||
//go:embed expected_output.json
|
||||
var expectedOutput []byte
|
||||
|
||||
func TestAnalyzer_Analyze(t *testing.T) {
|
||||
ctx, cancel := context.WithTimeout(context.Background(), time.Second*5)
|
||||
defer cancel()
|
||||
testSecrets, err := common.GetSecret(ctx, "trufflehog-testing", "detectors2")
|
||||
if err != nil {
|
||||
t.Fatalf("could not get test secrets from GCP: %s", err)
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
key string
|
||||
want []byte // JSON string
|
||||
wantErr bool
|
||||
}{
|
||||
{
|
||||
name: "valid Square key",
|
||||
key: testSecrets.MustGetField("SQUARE_SECRET"),
|
||||
want: expectedOutput,
|
||||
wantErr: false,
|
||||
},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
a := Analyzer{Cfg: &config.Config{}}
|
||||
got, err := a.Analyze(ctx, map[string]string{"key": tt.key})
|
||||
if (err != nil) != tt.wantErr {
|
||||
t.Errorf("Analyzer.Analyze() error = %v, wantErr %v", err, tt.wantErr)
|
||||
return
|
||||
}
|
||||
|
||||
// Bindings need to be in the same order to be comparable
|
||||
sortBindings(got.Bindings)
|
||||
|
||||
// Marshal the actual result to JSON
|
||||
gotJSON, err := json.Marshal(got)
|
||||
if err != nil {
|
||||
t.Fatalf("could not marshal got to JSON: %s", err)
|
||||
}
|
||||
|
||||
// Parse the expected JSON string
|
||||
var wantObj analyzers.AnalyzerResult
|
||||
if err := json.Unmarshal(tt.want, &wantObj); err != nil {
|
||||
t.Fatalf("could not unmarshal want JSON string: %s", err)
|
||||
}
|
||||
|
||||
// // Bindings need to be in the same order to be comparable
|
||||
sortBindings(wantObj.Bindings)
|
||||
|
||||
// Marshal the expected result to JSON (to normalize)
|
||||
wantJSON, err := json.Marshal(wantObj)
|
||||
if err != nil {
|
||||
t.Fatalf("could not marshal want to JSON: %s", err)
|
||||
}
|
||||
|
||||
// // Compare the JSON strings
|
||||
if string(gotJSON) != string(wantJSON) {
|
||||
// Pretty-print both JSON strings for easier comparison
|
||||
var gotIndented, wantIndented []byte
|
||||
gotIndented, err = json.MarshalIndent(got, "", " ")
|
||||
if err != nil {
|
||||
t.Fatalf("could not marshal got to indented JSON: %s", err)
|
||||
}
|
||||
wantIndented, err = json.MarshalIndent(wantObj, "", " ")
|
||||
if err != nil {
|
||||
t.Fatalf("could not marshal want to indented JSON: %s", err)
|
||||
}
|
||||
t.Errorf("Analyzer.Analyze() = %s, want %s", gotIndented, wantIndented)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
// Helper function to sort bindings
|
||||
func sortBindings(bindings []analyzers.Binding) {
|
||||
sort.SliceStable(bindings, func(i, j int) bool {
|
||||
if bindings[i].Resource.Name == bindings[j].Resource.Name {
|
||||
return bindings[i].Permission.Value < bindings[j].Permission.Value
|
||||
}
|
||||
return bindings[i].Resource.Name < bindings[j].Resource.Name
|
||||
})
|
||||
}
|
Loading…
Reference in a new issue