diff --git a/pkg/engine/generation.go b/pkg/engine/generation.go index b90311822e..9578d39674 100644 --- a/pkg/engine/generation.go +++ b/pkg/engine/generation.go @@ -18,19 +18,20 @@ import ( ) //Generate apply generation rules on a resource -func Generate(client *client.Client, policy kyverno.Policy, ns unstructured.Unstructured) []info.RuleInfo { +func Generate(client *client.Client, policy kyverno.Policy, ns unstructured.Unstructured) EngineResponse { + var response EngineResponse var executionTime time.Duration - var rulesAppliedCount int startTime := time.Now() glog.V(4).Infof("started applying generation rules of policy %q (%v)", policy.Name, startTime) defer func() { executionTime = time.Since(startTime) - glog.V(4).Infof("Finished applying generation rules policy %q (%v)", policy.Name, executionTime) - glog.V(4).Infof("Generation Rules appplied succesfully count %q for policy %q", rulesAppliedCount, policy.Name) + response.ExecutionTime = time.Since(startTime) + glog.V(4).Infof("Finished applying generation rules policy %q (%v)", policy.Name, response.ExecutionTime) + glog.V(4).Infof("Mutation Rules appplied succesfully count %q for policy %q", response.RulesAppliedCount, policy.Name) }() succesfulRuleCount := func() { // rules applied succesfully count - rulesAppliedCount++ + response.RulesAppliedCount++ } ris := []info.RuleInfo{} @@ -52,7 +53,8 @@ func Generate(client *client.Client, policy kyverno.Policy, ns unstructured.Unst } ris = append(ris, ri) } - return ris + response.RuleInfos = ris + return response } func applyRuleGenerator(client *client.Client, ns unstructured.Unstructured, gen kyverno.Generation, policyCreationTime metav1.Time) error { diff --git a/pkg/engine/mutation.go b/pkg/engine/mutation.go index 7cade297b1..88ae7d7644 100644 --- a/pkg/engine/mutation.go +++ b/pkg/engine/mutation.go @@ -13,22 +13,23 @@ import ( // Mutate performs mutation. Overlay first and then mutation patches func Mutate(policy kyverno.Policy, resource unstructured.Unstructured) EngineResponse { + var response EngineResponse var allPatches, rulePatches [][]byte var err error var errs []error ris := []info.RuleInfo{} var executionTime time.Duration - var rulesAppliedCount int startTime := time.Now() glog.V(4).Infof("started applying mutation rules of policy %q (%v)", policy.Name, startTime) defer func() { executionTime = time.Since(startTime) - glog.V(4).Infof("Finished applying mutation rules policy %q (%v)", policy.Name, executionTime) - glog.V(4).Infof("Mutation Rules appplied succesfully count %q for policy %q", rulesAppliedCount, policy.Name) + response.ExecutionTime = time.Since(startTime) + glog.V(4).Infof("Finished applying mutation rules policy %q (%v)", policy.Name, response.ExecutionTime) + glog.V(4).Infof("Mutation Rules appplied succesfully count %q for policy %q", response.RulesAppliedCount, policy.Name) }() succesfulRuleCount := func() { // rules applied succesfully count - rulesAppliedCount++ + response.RulesAppliedCount++ } patchedDocument, err := resource.MarshalJSON() @@ -38,7 +39,8 @@ func Mutate(policy kyverno.Policy, resource unstructured.Unstructured) EngineRes if err != nil { glog.V(4).Infof("unable to marshal resource : %v", err) - return EngineResponse{PatchedResource: resource} + response.PatchedResource = resource + return response } for _, rule := range policy.Spec.Rules { @@ -114,12 +116,12 @@ func Mutate(policy kyverno.Policy, resource unstructured.Unstructured) EngineRes patchedResource, err := ConvertToUnstructured(patchedDocument) if err != nil { glog.Errorf("Failed to convert patched resource to unstructuredtype, err%v\n:", err) - return EngineResponse{PatchedResource: resource} + response.PatchedResource = resource + return response } - return EngineResponse{ - Patches: allPatches, - PatchedResource: *patchedResource, - RuleInfos: ris, - } + response.Patches = allPatches + response.PatchedResource = *patchedResource + response.RuleInfos = ris + return response } diff --git a/pkg/engine/utils.go b/pkg/engine/utils.go index 9096a74869..ff2f3f9745 100644 --- a/pkg/engine/utils.go +++ b/pkg/engine/utils.go @@ -5,6 +5,7 @@ import ( "fmt" "strconv" "strings" + "time" "github.com/golang/glog" @@ -18,10 +19,20 @@ import ( "k8s.io/apimachinery/pkg/labels" ) +//EngineResponse provides the response to the application of a policy rule set on a resource type EngineResponse struct { Patches [][]byte PatchedResource unstructured.Unstructured RuleInfos []info.RuleInfo + EngineStats +} + +//EngineStats stores in the statistics for a single application of resource +type EngineStats struct { + // average time required to process the policy rules on a resource + ExecutionTime time.Duration + // Count of rules that were applied succesfully + RulesAppliedCount int } // //ListResourcesThatApplyToPolicy returns list of resources that are filtered by policy rules diff --git a/pkg/engine/validation.go b/pkg/engine/validation.go index 42d917f998..9dcaca2ae1 100644 --- a/pkg/engine/validation.go +++ b/pkg/engine/validation.go @@ -19,29 +19,32 @@ import ( // Validate handles validating admission request // Checks the target resources for rules defined in the policy func Validate(policy kyverno.Policy, resource unstructured.Unstructured) EngineResponse { + var response EngineResponse var executionTime time.Duration - var rulesAppliedCount int startTime := time.Now() glog.V(4).Infof("started applying validation rules of policy %q (%v)", policy.Name, startTime) defer func() { executionTime = time.Since(startTime) - glog.V(4).Infof("Finished applying validation rules policy %q (%v)", policy.Name, executionTime) - glog.V(4).Infof("Validation Rules appplied succesfully count %q for policy %q", rulesAppliedCount, policy.Name) + response.ExecutionTime = time.Since(startTime) + glog.V(4).Infof("Finished applying mutation rules policy %q (%v)", policy.Name, response.ExecutionTime) + glog.V(4).Infof("Mutation Rules appplied succesfully count %q for policy %q", response.RulesAppliedCount, policy.Name) }() succesfulRuleCount := func() { // rules applied succesfully count - rulesAppliedCount++ + response.RulesAppliedCount++ } resourceRaw, err := resource.MarshalJSON() if err != nil { glog.V(4).Infof("Skip processing validating rule, unable to marshal resource : %v\n", err) - return EngineResponse{PatchedResource: resource} + response.PatchedResource = resource + return response } var resourceInt interface{} if err := json.Unmarshal(resourceRaw, &resourceInt); err != nil { glog.V(4).Infof("unable to unmarshal resource : %v\n", err) - return EngineResponse{PatchedResource: resource} + response.PatchedResource = resource + return response } var ruleInfos []info.RuleInfo @@ -73,8 +76,8 @@ func Validate(policy kyverno.Policy, resource unstructured.Unstructured) EngineR } ruleInfos = append(ruleInfos, ruleInfo) } - - return EngineResponse{RuleInfos: ruleInfos} + response.RuleInfos = ruleInfos + return response } // validateResourceWithPattern is a start of element-by-element validation process diff --git a/pkg/namespace/generation.go b/pkg/namespace/generation.go index 18a6a2908d..ca715e20ce 100644 --- a/pkg/namespace/generation.go +++ b/pkg/namespace/generation.go @@ -148,8 +148,8 @@ func applyPolicy(client *client.Client, resource unstructured.Unstructured, poli glog.V(4).Infof("Finished applying %s on resource %s/%s/%s (%v)", policy.Name, resource.GetKind(), resource.GetNamespace(), resource.GetName(), time.Since(startTime)) }() policyInfo := info.NewPolicyInfo(policy.Name, resource.GetKind(), resource.GetName(), resource.GetNamespace(), policy.Spec.ValidationFailureAction) - ruleInfos := engine.Generate(client, policy, resource) - policyInfo.AddRuleInfos(ruleInfos) + engineResponse := engine.Generate(client, policy, resource) + policyInfo.AddRuleInfos(engineResponse.RuleInfos) return policyInfo }