Skip to content

Commit

Permalink
Merge branch 'dev' of https://github.com/jfrog/jfrog-cli-core into re…
Browse files Browse the repository at this point in the history
…factor_print_table
  • Loading branch information
EyalDelarea committed Sep 26, 2023
2 parents 4b2b2e9 + 0414290 commit 2a121de
Show file tree
Hide file tree
Showing 9 changed files with 1,251 additions and 220 deletions.
90 changes: 90 additions & 0 deletions xray/commands/audit/jas/common_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
package jas

import (
"testing"

"github.com/jfrog/jfrog-cli-core/v2/xray/utils"
"github.com/owenrumney/go-sarif/v2/sarif"
"github.com/stretchr/testify/assert"
)

func TestExcludeSuppressResults(t *testing.T) {
tests := []struct {
name string
sarifResults []*sarif.Result
expectedOutput []*sarif.Result
}{
{
sarifResults: []*sarif.Result{
utils.CreateResultWithOneLocation("", 0, 0, 0, 0, "snippet1", "ruleId1", "level1"),
utils.CreateResultWithOneLocation("", 0, 0, 0, 0, "snippet2", "ruleId2", "level2"),
},
expectedOutput: []*sarif.Result{
utils.CreateResultWithOneLocation("", 0, 0, 0, 0, "snippet1", "ruleId1", "level1"),
utils.CreateResultWithOneLocation("", 0, 0, 0, 0, "snippet2", "ruleId2", "level2"),
},
},
{
sarifResults: []*sarif.Result{
utils.CreateResultWithOneLocation("", 0, 0, 0, 0, "snippet1", "ruleId1", "level1").WithSuppression([]*sarif.Suppression{sarif.NewSuppression("")}),
utils.CreateResultWithOneLocation("", 0, 0, 0, 0, "snippet2", "ruleId2", "level2"),
},
expectedOutput: []*sarif.Result{
utils.CreateResultWithOneLocation("", 0, 0, 0, 0, "snippet2", "ruleId2", "level2"),
},
},
{
sarifResults: []*sarif.Result{
utils.CreateResultWithOneLocation("", 0, 0, 0, 0, "snippet1", "ruleId1", "level1").WithSuppression([]*sarif.Suppression{sarif.NewSuppression("")}),
utils.CreateResultWithOneLocation("", 0, 0, 0, 0, "snippet2", "ruleId2", "level2").WithSuppression([]*sarif.Suppression{sarif.NewSuppression("")}),
},
expectedOutput: []*sarif.Result{},
},
}

for _, test := range tests {
assert.Equal(t, test.expectedOutput, excludeSuppressResults(test.sarifResults))
}
}

func TestAddScoreToRunRules(t *testing.T) {

tests := []struct {
name string
sarifRun *sarif.Run
expectedOutput []*sarif.ReportingDescriptor
}{
{
sarifRun: utils.CreateRunWithDummyResults(
utils.CreateResultWithOneLocation("file1", 0, 0, 0, 0, "snippet", "rule1", "info"),
utils.CreateResultWithOneLocation("file2", 0, 0, 0, 0, "snippet", "rule1", "info"),
utils.CreateResultWithOneLocation("file", 0, 0, 0, 0, "snippet", "rule2", "warning"),
),
expectedOutput: []*sarif.ReportingDescriptor{
sarif.NewRule("rule1").WithProperties(sarif.Properties{"security-severity": "6.9"}),
sarif.NewRule("rule2").WithProperties(sarif.Properties{"security-severity": "6.9"}),
},
},
{
sarifRun: utils.CreateRunWithDummyResults(
utils.CreateResultWithOneLocation("file", 0, 0, 0, 0, "snippet", "rule1", "none"),
utils.CreateResultWithOneLocation("file", 0, 0, 0, 0, "snippet", "rule2", "note"),
utils.CreateResultWithOneLocation("file", 0, 0, 0, 0, "snippet", "rule3", "info"),
utils.CreateResultWithOneLocation("file", 0, 0, 0, 0, "snippet", "rule4", "warning"),
utils.CreateResultWithOneLocation("file", 0, 0, 0, 0, "snippet", "rule5", "error"),
),
expectedOutput: []*sarif.ReportingDescriptor{
sarif.NewRule("rule1").WithProperties(sarif.Properties{"security-severity": "0.0"}),
sarif.NewRule("rule2").WithProperties(sarif.Properties{"security-severity": "3.9"}),
sarif.NewRule("rule3").WithProperties(sarif.Properties{"security-severity": "6.9"}),
sarif.NewRule("rule4").WithProperties(sarif.Properties{"security-severity": "6.9"}),
sarif.NewRule("rule5").WithProperties(sarif.Properties{"security-severity": "8.9"}),
},
},
}

for _, test := range tests {
addScoreToRunRules(test.sarifRun)
assert.Equal(t, test.expectedOutput, test.sarifRun.Tool.Driver.Rules)
}
}
34 changes: 20 additions & 14 deletions xray/commands/audit/jas/sast/sastscanner.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
package sast

import (
"fmt"

"github.com/jfrog/jfrog-cli-core/v2/xray/commands/audit/jas"
"github.com/jfrog/jfrog-cli-core/v2/xray/utils"
"github.com/jfrog/jfrog-client-go/utils/log"
Expand Down Expand Up @@ -47,7 +49,8 @@ func (ssm *SastScanManager) Run(wd string) (err error) {
if err != nil {
return
}
ssm.sastScannerResults = append(ssm.sastScannerResults, groupResultsByLocation(workingDirRuns)...)
groupResultsByLocation(workingDirRuns)
ssm.sastScannerResults = append(ssm.sastScannerResults, workingDirRuns...)
return
}

Expand All @@ -58,7 +61,7 @@ func (ssm *SastScanManager) runAnalyzerManager(wd string) error {
// In the Sast scanner, there can be multiple results with the same location.
// The only difference is that their CodeFlow values are different.
// We combine those under the same result location value
func groupResultsByLocation(sarifRuns []*sarif.Run) []*sarif.Run {
func groupResultsByLocation(sarifRuns []*sarif.Run) {
for _, sastRun := range sarifRuns {
locationToResult := map[string]*sarif.Result{}
for _, sastResult := range sastRun.Results {
Expand All @@ -71,25 +74,28 @@ func groupResultsByLocation(sarifRuns []*sarif.Run) []*sarif.Run {
}
sastRun.Results = maps.Values(locationToResult)
}
return sarifRuns
}

// In Sast there is only one location for each result
func getResultFileName(result *sarif.Result) string {
if len(result.Locations) > 0 {
return utils.GetLocationFileName(result.Locations[0])
func getResultLocationStr(result *sarif.Result) string {
if len(result.Locations) == 0 {
return ""
}
return ""
location := result.Locations[0]
return fmt.Sprintf("%s%d%d%d%d",
utils.GetLocationFileName(location),
utils.GetLocationStartLine(location),
utils.GetLocationStartColumn(location),
utils.GetLocationEndLine(location),
utils.GetLocationEndColumn(location))
}

// In Sast there is only one location for each result
func getResultStartLocationInFile(result *sarif.Result) string {
if len(result.Locations) > 0 {
return utils.GetStartLocationInFile(result.Locations[0])
func getResultRuleId(result *sarif.Result) string {
if result.RuleID == nil {
return ""
}
return ""
return *result.RuleID
}

func getResultId(result *sarif.Result) string {
return getResultFileName(result) + getResultStartLocationInFile(result) + utils.GetResultSeverity(result) + utils.GetResultMsgText(result)
return getResultRuleId(result) + utils.GetResultSeverity(result) + utils.GetResultMsgText(result) + getResultLocationStr(result)
}
92 changes: 90 additions & 2 deletions xray/commands/audit/jas/sast/sastscanner_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@ import (
"testing"

"github.com/jfrog/jfrog-cli-core/v2/xray/commands/audit/jas"
"github.com/jfrog/jfrog-cli-core/v2/xray/utils"
"github.com/owenrumney/go-sarif/v2/sarif"

"github.com/stretchr/testify/assert"
)
Expand Down Expand Up @@ -40,7 +42,7 @@ func TestSastParseResults_EmptyResults(t *testing.T) {
if assert.NoError(t, err) && assert.NotNil(t, sastScanManager.sastScannerResults) {
assert.Len(t, sastScanManager.sastScannerResults, 1)
assert.Empty(t, sastScanManager.sastScannerResults[0].Results)
sastScanManager.sastScannerResults = groupResultsByLocation(sastScanManager.sastScannerResults)
groupResultsByLocation(sastScanManager.sastScannerResults)
assert.Len(t, sastScanManager.sastScannerResults, 1)
assert.Empty(t, sastScanManager.sastScannerResults[0].Results)
}
Expand All @@ -61,8 +63,94 @@ func TestSastParseResults_ResultsContainIacViolations(t *testing.T) {
if assert.NoError(t, err) && assert.NotNil(t, sastScanManager.sastScannerResults) {
assert.Len(t, sastScanManager.sastScannerResults, 1)
assert.NotEmpty(t, sastScanManager.sastScannerResults[0].Results)
sastScanManager.sastScannerResults = groupResultsByLocation(sastScanManager.sastScannerResults)
groupResultsByLocation(sastScanManager.sastScannerResults)
// File has 4 results, 2 of them at the same location different codeFlow
assert.Len(t, sastScanManager.sastScannerResults[0].Results, 3)
}
}

func TestGroupResultsByLocation(t *testing.T) {
tests := []struct {
run *sarif.Run
expectedOutput *sarif.Run
}{
{
run: utils.CreateRunWithDummyResults(),
expectedOutput: utils.CreateRunWithDummyResults(),
},
{
// No similar groups at all
run: utils.CreateRunWithDummyResults(
utils.CreateResultWithOneLocation("file", 1, 2, 3, 4, "snippet", "rule1", "info"),
utils.CreateResultWithOneLocation("file", 1, 2, 3, 4, "snippet", "rule1", "note"),
utils.CreateResultWithOneLocation("file", 5, 6, 7, 8, "snippet", "rule1", "info"),
utils.CreateResultWithOneLocation("file2", 1, 2, 3, 4, "snippet", "rule1", "info").WithCodeFlows([]*sarif.CodeFlow{
utils.CreateCodeFlow(utils.CreateThreadFlow(
utils.CreateLocation("other", 0, 0, 0, 0, "other-snippet"),
utils.CreateLocation("file2", 1, 2, 3, 4, "snippet"),
)),
}),
utils.CreateResultWithOneLocation("file2", 1, 2, 3, 4, "snippet", "rule2", "info").WithCodeFlows([]*sarif.CodeFlow{
utils.CreateCodeFlow(utils.CreateThreadFlow(
utils.CreateLocation("other2", 1, 1, 1, 1, "other-snippet2"),
utils.CreateLocation("file2", 1, 2, 3, 4, "snippet"),
)),
}),
),
expectedOutput: utils.CreateRunWithDummyResults(
utils.CreateResultWithOneLocation("file", 1, 2, 3, 4, "snippet", "rule1", "info"),
utils.CreateResultWithOneLocation("file", 1, 2, 3, 4, "snippet", "rule1", "note"),
utils.CreateResultWithOneLocation("file", 5, 6, 7, 8, "snippet", "rule1", "info"),
utils.CreateResultWithOneLocation("file2", 1, 2, 3, 4, "snippet", "rule1", "info").WithCodeFlows([]*sarif.CodeFlow{
utils.CreateCodeFlow(utils.CreateThreadFlow(
utils.CreateLocation("other", 0, 0, 0, 0, "other-snippet"),
utils.CreateLocation("file2", 1, 2, 3, 4, "snippet"),
)),
}),
utils.CreateResultWithOneLocation("file2", 1, 2, 3, 4, "snippet", "rule2", "info").WithCodeFlows([]*sarif.CodeFlow{
utils.CreateCodeFlow(utils.CreateThreadFlow(
utils.CreateLocation("other2", 1, 1, 1, 1, "other-snippet2"),
utils.CreateLocation("file2", 1, 2, 3, 4, "snippet"),
)),
}),
),
},
{
// With similar groups
run: utils.CreateRunWithDummyResults(
utils.CreateResultWithOneLocation("file", 1, 2, 3, 4, "snippet", "rule1", "info").WithCodeFlows([]*sarif.CodeFlow{
utils.CreateCodeFlow(utils.CreateThreadFlow(
utils.CreateLocation("other", 0, 0, 0, 0, "other-snippet"),
utils.CreateLocation("file", 1, 2, 3, 4, "snippet"),
)),
}),
utils.CreateResultWithOneLocation("file", 1, 2, 3, 4, "snippet", "rule1", "info").WithCodeFlows([]*sarif.CodeFlow{
utils.CreateCodeFlow(utils.CreateThreadFlow(
utils.CreateLocation("other2", 1, 1, 1, 1, "other-snippet"),
utils.CreateLocation("file", 1, 2, 3, 4, "snippet"),
)),
}),
utils.CreateResultWithOneLocation("file", 5, 6, 7, 8, "snippet", "rule1", "info"),
utils.CreateResultWithOneLocation("file", 1, 2, 3, 4, "snippet", "rule1", "info"),
),
expectedOutput: utils.CreateRunWithDummyResults(
utils.CreateResultWithOneLocation("file", 1, 2, 3, 4, "snippet", "rule1", "info").WithCodeFlows([]*sarif.CodeFlow{
utils.CreateCodeFlow(utils.CreateThreadFlow(
utils.CreateLocation("other", 0, 0, 0, 0, "other-snippet"),
utils.CreateLocation("file", 1, 2, 3, 4, "snippet"),
)),
utils.CreateCodeFlow(utils.CreateThreadFlow(
utils.CreateLocation("other2", 1, 1, 1, 1, "other-snippet"),
utils.CreateLocation("file", 1, 2, 3, 4, "snippet"),
)),
}),
utils.CreateResultWithOneLocation("file", 5, 6, 7, 8, "snippet", "rule1", "info"),
),
},
}

for _, test := range tests {
groupResultsByLocation([]*sarif.Run{test.run})
assert.ElementsMatch(t, test.expectedOutput.Results, test.run.Results)
}
}
3 changes: 1 addition & 2 deletions xray/commands/audit/jas/secrets/secretsscanner.go
Original file line number Diff line number Diff line change
Expand Up @@ -105,8 +105,7 @@ func processSecretScanRuns(sarifRuns []*sarif.Run) []*sarif.Run {
// Hide discovered secrets value
for _, secretResult := range secretRun.Results {
for _, location := range secretResult.Locations {
secret := utils.GetLocationSnippetPointer(location)
utils.SetLocationSnippet(location, maskSecret(*secret))
utils.SetLocationSnippet(location, maskSecret(utils.GetLocationSnippet(location)))
}
}
}
Expand Down
Loading

0 comments on commit 2a121de

Please sign in to comment.