1
0
Fork 0
mirror of https://github.com/kyverno/kyverno.git synced 2025-03-05 15:37:19 +00:00

fix: Kyverno cli apply duplicate result counts (#7945)

* removed repeated logic from kyverno_policies_types

Signed-off-by: hackeramitkumar <amit9116260192@gmail.com>

fixed unit tests

* fixed unit tests

Signed-off-by: hackeramitkumar <amit9116260192@gmail.com>

* updated common.go logic

Signed-off-by: hackeramitkumar <amit9116260192@gmail.com>

* remove skip response logic from common.go

Signed-off-by: hackeramitkumar <amit9116260192@gmail.com>

* remove skip response logic from common.go

Signed-off-by: hackeramitkumar <amit9116260192@gmail.com>

* fixed conflict

Signed-off-by: hackeramitkumar <amit9116260192@gmail.com>

---------

Signed-off-by: hackeramitkumar <amit9116260192@gmail.com>
Co-authored-by: shuting <shuting@nirmata.com>
This commit is contained in:
Amit kumar 2023-08-08 13:05:01 +05:30 committed by GitHub
parent bf21fbf673
commit 9e6ff00706
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 73 additions and 104 deletions

View file

@ -11,7 +11,6 @@ import (
"time"
"github.com/go-git/go-billy/v5/memfs"
"github.com/kyverno/kyverno/api/kyverno"
kyvernov1 "github.com/kyverno/kyverno/api/kyverno/v1"
"github.com/kyverno/kyverno/api/kyverno/v1beta1"
"github.com/kyverno/kyverno/cmd/cli/kubectl-kyverno/utils/color"
@ -403,52 +402,7 @@ func (c *ApplyCommandConfig) applyCommandHelper() (*common.ResultCounts, []*unst
if err != nil {
return &rc, resources, skipInvalidPolicies, responses, sanitizederror.NewWithError(fmt.Errorf("failed to apply policy %v on resource %v", policy.GetName(), resource.GetName()).Error(), err)
}
for _, response := range ers {
if !response.IsEmpty() {
for _, rule := range autogen.ComputeRules(response.Policy()) {
if rule.HasValidate() || rule.HasVerifyImageChecks() || rule.HasVerifyImages() {
ruleFoundInEngineResponse := false
for _, valResponseRule := range response.PolicyResponse.Rules {
if rule.Name == valResponseRule.Name() {
ruleFoundInEngineResponse = true
switch valResponseRule.Status() {
case engineapi.RuleStatusPass:
rc.Pass++
case engineapi.RuleStatusFail:
ann := policy.GetAnnotations()
if scored, ok := ann[kyverno.AnnotationPolicyScored]; ok && scored == "false" {
rc.Warn++
break
} else if applyPolicyConfig.AuditWarn && response.GetValidationFailureAction().Audit() {
rc.Warn++
} else {
rc.Fail++
}
case engineapi.RuleStatusError:
rc.Error++
case engineapi.RuleStatusWarn:
rc.Warn++
case engineapi.RuleStatusSkip:
rc.Skip++
}
continue
}
}
if !ruleFoundInEngineResponse {
rc.Skip++
response.PolicyResponse.Rules = append(response.PolicyResponse.Rules,
*engineapi.RuleSkip(
rule.Name,
engineapi.Validation,
rule.Validation.Message,
),
)
}
}
}
}
responses = append(responses, response)
}
responses = append(responses, processSkipEngineResponses(ers, applyPolicyConfig)...)
}
}
@ -522,3 +476,32 @@ func exit(rc *common.ResultCounts, warnExitCode int, warnNoPassed bool) {
osExit(warnExitCode)
}
}
func processSkipEngineResponses(responses []engineapi.EngineResponse, c common.ApplyPolicyConfig) []engineapi.EngineResponse {
var processedEngineResponses []engineapi.EngineResponse
for _, response := range responses {
if !response.IsEmpty() {
for _, rule := range autogen.ComputeRules(response.Policy()) {
if rule.HasValidate() || rule.HasVerifyImageChecks() || rule.HasVerifyImages() {
ruleFoundInEngineResponse := false
for _, valResponseRule := range response.PolicyResponse.Rules {
if rule.Name == valResponseRule.Name() {
ruleFoundInEngineResponse = true
}
}
if !ruleFoundInEngineResponse {
response.PolicyResponse.Rules = append(response.PolicyResponse.Rules,
*engineapi.RuleSkip(
rule.Name,
engineapi.Validation,
rule.Validation.Message,
),
)
}
}
}
}
processedEngineResponses = append(processedEngineResponses, response)
}
return processedEngineResponses
}

View file

@ -318,61 +318,6 @@ func GetVariable(
return variables, globalValMap, valuesMapResource, namespaceSelectorMap, subresources, nil
}
func ProcessValidateEngineResponse(policy kyvernov1.PolicyInterface, validateResponse engineapi.EngineResponse, resPath string, rc *ResultCounts, policyReport bool, auditWarn bool) {
printCount := 0
for _, policyRule := range autogen.ComputeRules(policy) {
ruleFoundInEngineResponse := false
if !policyRule.HasValidate() && !policyRule.HasVerifyImageChecks() && !policyRule.HasVerifyImages() {
continue
}
for i, valResponseRule := range validateResponse.PolicyResponse.Rules {
if policyRule.Name == valResponseRule.Name() {
ruleFoundInEngineResponse = true
switch valResponseRule.Status() {
case engineapi.RuleStatusPass:
rc.Pass++
case engineapi.RuleStatusFail:
auditWarning := false
ann := policy.GetAnnotations()
if scored, ok := ann[kyverno.AnnotationPolicyScored]; ok && scored == "false" {
rc.Warn++
break
} else if auditWarn && validateResponse.GetValidationFailureAction().Audit() {
rc.Warn++
auditWarning = true
} else {
rc.Fail++
}
if !policyReport {
if printCount < 1 {
if auditWarning {
fmt.Printf("\npolicy %s -> resource %s failed as audit warning: \n", policy.GetName(), resPath)
} else {
fmt.Printf("\npolicy %s -> resource %s failed: \n", policy.GetName(), resPath)
}
printCount++
}
fmt.Printf("%d. %s: %s \n", i+1, valResponseRule.Name(), valResponseRule.Message())
}
case engineapi.RuleStatusError:
fmt.Printf("\npolicy %s -> resource %s error: %s\n", policy.GetName(), resPath, valResponseRule.Message())
rc.Error++
case engineapi.RuleStatusWarn:
rc.Warn++
case engineapi.RuleStatusSkip:
rc.Skip++
}
continue
}
}
if !ruleFoundInEngineResponse {
rc.Skip++
}
}
}
// PrintMutatedOutput - function to print output in provided file or directory
func PrintMutatedOutput(mutateLogPath string, mutateLogPathIsDir bool, yaml string, fileName string) error {
var f *os.File
@ -932,3 +877,44 @@ func GetGitBranchOrPolicyPaths(gitBranch, repoURL string, policyPaths []string)
}
return gitBranch, gitPathToYamls
}
func processEngineResponses(responses []engineapi.EngineResponse, c ApplyPolicyConfig) {
for _, response := range responses {
if !response.IsEmpty() {
for _, rule := range autogen.ComputeRules(response.Policy()) {
if rule.HasValidate() || rule.HasVerifyImageChecks() || rule.HasVerifyImages() {
ruleFoundInEngineResponse := false
for _, valResponseRule := range response.PolicyResponse.Rules {
if rule.Name == valResponseRule.Name() {
ruleFoundInEngineResponse = true
switch valResponseRule.Status() {
case engineapi.RuleStatusPass:
c.Rc.Pass++
case engineapi.RuleStatusFail:
ann := c.Policy.GetAnnotations()
if scored, ok := ann[kyverno.AnnotationPolicyScored]; ok && scored == "false" {
c.Rc.Warn++
break
} else if c.AuditWarn && response.GetValidationFailureAction().Audit() {
c.Rc.Warn++
} else {
c.Rc.Fail++
}
case engineapi.RuleStatusError:
c.Rc.Error++
case engineapi.RuleStatusWarn:
c.Rc.Warn++
case engineapi.RuleStatusSkip:
c.Rc.Skip++
}
continue
}
}
if !ruleFoundInEngineResponse {
c.Rc.Skip++
}
}
}
}
}
}

View file

@ -172,7 +172,6 @@ OuterLoop:
if policyHasValidate {
validateResponse = eng.Validate(context.Background(), policyContext)
validateResponse = combineRuleResponses(validateResponse)
ProcessValidateEngineResponse(c.Policy, validateResponse, resPath, c.Rc, c.PolicyReport, c.AuditWarn)
}
if !validateResponse.IsEmpty() {
@ -183,7 +182,6 @@ OuterLoop:
if !verifyImageResponse.IsEmpty() {
verifyImageResponse = combineRuleResponses(verifyImageResponse)
engineResponses = append(engineResponses, verifyImageResponse)
ProcessValidateEngineResponse(c.Policy, verifyImageResponse, resPath, c.Rc, c.PolicyReport, c.AuditWarn)
}
var policyHasGenerate bool
@ -208,6 +206,8 @@ OuterLoop:
updateResultCounts(c.Policy, &generateResponse, resPath, c.Rc, c.AuditWarn)
}
processEngineResponses(engineResponses, c)
return engineResponses, nil
}