mirror of
https://github.com/kyverno/kyverno.git
synced 2025-03-28 10:28:36 +00:00
update status v1
This commit is contained in:
parent
bcad9ada2d
commit
3f876e6f46
3 changed files with 72 additions and 25 deletions
|
@ -1,6 +1,8 @@
|
|||
package v1alpha1
|
||||
|
||||
import (
|
||||
"time"
|
||||
|
||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||
)
|
||||
|
||||
|
@ -89,7 +91,15 @@ type CloneFrom struct {
|
|||
|
||||
//PolicyStatus provides status for violations
|
||||
type PolicyStatus struct {
|
||||
Violations int `json:"violations"`
|
||||
ViolationCount int `json:"violationCount"`
|
||||
// Count of rules that were applied
|
||||
RulesAppliedCount int `json:"rulesAppliedCount"`
|
||||
// Count of resources for whom update/create api requests were blocked as the resoruce did not satisfy the policy rules
|
||||
ResourcesBlockedCount int `json:"resourcesBlockedCount"`
|
||||
// average time required to process the policy Mutation rules on a resource
|
||||
AvgExecutionTimeMutation time.Duration `json:"averageMutationExecutionTime"`
|
||||
// average time required to process the policy Validation rules on a resource
|
||||
AvgExecutionTimeValidation time.Duration `json:"averageValidationExecutionTime"`
|
||||
}
|
||||
|
||||
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
|
||||
|
|
|
@ -119,7 +119,7 @@ func NewPolicyController(kyvernoClient *kyvernoclient.Clientset, client *client.
|
|||
pc.rm = NewResourceManager(30)
|
||||
|
||||
// aggregator
|
||||
pc.statusAggregator = NewPolicyStatAggregator(kyvernoClient, pInformer.Lister())
|
||||
pc.statusAggregator = NewPolicyStatAggregator(kyvernoClient, pInformer)
|
||||
|
||||
return &pc, nil
|
||||
}
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package policy
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"reflect"
|
||||
"sync"
|
||||
"time"
|
||||
|
@ -8,48 +9,55 @@ import (
|
|||
"github.com/golang/glog"
|
||||
kyverno "github.com/nirmata/kyverno/pkg/api/kyverno/v1alpha1"
|
||||
kyvernoclient "github.com/nirmata/kyverno/pkg/client/clientset/versioned"
|
||||
kyvernoinformer "github.com/nirmata/kyverno/pkg/client/informers/externalversions/kyverno/v1alpha1"
|
||||
kyvernolister "github.com/nirmata/kyverno/pkg/client/listers/kyverno/v1alpha1"
|
||||
utilruntime "k8s.io/apimachinery/pkg/util/runtime"
|
||||
"k8s.io/apimachinery/pkg/util/wait"
|
||||
"k8s.io/client-go/tools/cache"
|
||||
)
|
||||
|
||||
type PolicyStatus struct {
|
||||
// average time required to process the policy rules on a resource
|
||||
avgExecutionTime time.Duration
|
||||
// Count of rules that were applied succesfully
|
||||
rulesAppliedCount int
|
||||
// Count of resources for whom update/create api requests were blocked as the resoruce did not satisfy the policy rules
|
||||
resourcesBlockedCount int
|
||||
// Count of the resource for whom the mutation rules were applied succesfully
|
||||
resourcesMutatedCount int
|
||||
}
|
||||
// type PolicyStatus struct {
|
||||
// // average time required to process the policy rules on a resource
|
||||
// avgExecutionTime time.Duration
|
||||
// // Count of rules that were applied succesfully
|
||||
// rulesAppliedCount int
|
||||
// // Count of resources for whom update/create api requests were blocked as the resoruce did not satisfy the policy rules
|
||||
// resourcesBlockedCount int
|
||||
// // Count of the resource for whom the mutation rules were applied succesfully
|
||||
// resourcesMutatedCount int
|
||||
// }
|
||||
|
||||
//PolicyStatusAggregator stores information abt aggregation
|
||||
type PolicyStatusAggregator struct {
|
||||
// time since we start aggregating the stats
|
||||
startTime time.Time
|
||||
// channel to recieve stats
|
||||
ch chan PolicyStat
|
||||
// update polict status
|
||||
// update policy status
|
||||
psControl PStatusControlInterface
|
||||
// pLister can list/get policy from the shared informer's store
|
||||
pLister kyvernolister.PolicyLister
|
||||
// pListerSynced returns true if the Policy store has been synced at least once
|
||||
pListerSynced cache.InformerSynced
|
||||
// UpdateViolationCount and SendStat can update same policy status
|
||||
// we need to sync the updates using policyName
|
||||
policyUpdateData sync.Map
|
||||
}
|
||||
|
||||
//NewPolicyStatAggregator returns a new policy status
|
||||
func NewPolicyStatAggregator(client *kyvernoclient.Clientset, pLister kyvernolister.PolicyLister) *PolicyStatusAggregator {
|
||||
func NewPolicyStatAggregator(client *kyvernoclient.Clientset, pInformer kyvernoinformer.PolicyInformer) *PolicyStatusAggregator {
|
||||
psa := PolicyStatusAggregator{
|
||||
startTime: time.Now(),
|
||||
ch: make(chan PolicyStat),
|
||||
}
|
||||
psa.pLister = pLister
|
||||
psa.pLister = pInformer.Lister()
|
||||
psa.pListerSynced = pInformer.Informer().HasSynced
|
||||
psa.psControl = PSControl{Client: client}
|
||||
//TODO: add WaitGroup
|
||||
return &psa
|
||||
}
|
||||
|
||||
//Run begins aggregator
|
||||
func (psa *PolicyStatusAggregator) Run(workers int, stopCh <-chan struct{}) {
|
||||
defer utilruntime.HandleCrash()
|
||||
glog.V(4).Info("Started aggregator for policy status stats")
|
||||
|
@ -69,7 +77,7 @@ func (psa *PolicyStatusAggregator) aggregate() {
|
|||
for r := range psa.ch {
|
||||
glog.V(4).Infof("recieved policy stats %v", r)
|
||||
if err := psa.updateStats(r); err != nil {
|
||||
glog.Info("Failed to update stats for policy %s: %v", r.PolicyName, err)
|
||||
glog.Infof("Failed to update stats for policy %s: %v", r.PolicyName, err)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -77,32 +85,59 @@ func (psa *PolicyStatusAggregator) aggregate() {
|
|||
|
||||
func (psa *PolicyStatusAggregator) updateStats(stats PolicyStat) error {
|
||||
func() {
|
||||
glog.V(4).Infof("lock updates for policy name %s", stats.PolicyName)
|
||||
glog.V(4).Infof("lock updates for policy %s", stats.PolicyName)
|
||||
// Lock the update for policy
|
||||
psa.policyUpdateData.Store(stats.PolicyName, struct{}{})
|
||||
}()
|
||||
defer func() {
|
||||
glog.V(4).Infof("Unlock updates for policy name %s", stats.PolicyName)
|
||||
glog.V(4).Infof("Unlock updates for policy %s", stats.PolicyName)
|
||||
psa.policyUpdateData.Delete(stats.PolicyName)
|
||||
}()
|
||||
|
||||
// //wait for cache sync
|
||||
// if !cache.WaitForCacheSync(nil, psa.pListerSynced) {
|
||||
// glog.Infof("unable to sync cache for policy informer")
|
||||
// return nil
|
||||
// }
|
||||
// get policy
|
||||
policy, err := psa.pLister.Get(stats.PolicyName)
|
||||
if err != nil {
|
||||
glog.V(4).Infof("failed to get policy %s. Unable to update violation count: %v", stats.PolicyName, err)
|
||||
return err
|
||||
}
|
||||
newpolicy := policy
|
||||
fmt.Println(newpolicy.ResourceVersion)
|
||||
newpolicy.Status = kyverno.PolicyStatus{}
|
||||
glog.V(4).Infof("updating stats for policy %s", policy.Name)
|
||||
// update the statistics
|
||||
// policy.Status
|
||||
|
||||
return nil
|
||||
// rules applied count
|
||||
newpolicy.Status.RulesAppliedCount = newpolicy.Status.RulesAppliedCount + stats.RulesAppliedCount
|
||||
// resource blocked count
|
||||
if stats.ResourceBlocked {
|
||||
policy.Status.ResourcesBlockedCount++
|
||||
}
|
||||
var zeroDuration time.Duration
|
||||
if newpolicy.Status.AvgExecutionTimeMutation != zeroDuration {
|
||||
// avg execution time for mutation rules
|
||||
newpolicy.Status.AvgExecutionTimeMutation = (newpolicy.Status.AvgExecutionTimeMutation + stats.MutationExecutionTime) / 2
|
||||
} else {
|
||||
newpolicy.Status.AvgExecutionTimeMutation = stats.MutationExecutionTime
|
||||
}
|
||||
if policy.Status.AvgExecutionTimeValidation != zeroDuration {
|
||||
// avg execution time for validation rules
|
||||
newpolicy.Status.AvgExecutionTimeValidation = (newpolicy.Status.AvgExecutionTimeValidation + stats.ValidationExecutionTime) / 2
|
||||
} else {
|
||||
newpolicy.Status.AvgExecutionTimeValidation = stats.ValidationExecutionTime
|
||||
}
|
||||
return psa.psControl.UpdatePolicyStatus(newpolicy)
|
||||
}
|
||||
|
||||
//PolicyStatusInterface provides methods to modify policyStatus
|
||||
type PolicyStatusInterface interface {
|
||||
SendStat(stat PolicyStat)
|
||||
UpdateViolationCount(policyName string, pvList []*kyverno.PolicyViolation) error
|
||||
}
|
||||
|
||||
//PolicyStat stored stats for policy
|
||||
type PolicyStat struct {
|
||||
PolicyName string
|
||||
MutationExecutionTime time.Duration
|
||||
|
@ -121,12 +156,12 @@ func (psa *PolicyStatusAggregator) SendStat(stat PolicyStat) {
|
|||
//UpdateViolationCount updates the active violation count
|
||||
func (psa *PolicyStatusAggregator) UpdateViolationCount(policyName string, pvList []*kyverno.PolicyViolation) error {
|
||||
func() {
|
||||
glog.V(4).Infof("lock updates for policy name %s", policyName)
|
||||
glog.V(4).Infof("lock updates for policy %s", policyName)
|
||||
// Lock the update for policy
|
||||
psa.policyUpdateData.Store(policyName, struct{}{})
|
||||
}()
|
||||
defer func() {
|
||||
glog.V(4).Infof("Unlock updates for policy name %s", policyName)
|
||||
glog.V(4).Infof("Unlock updates for policy %s", policyName)
|
||||
psa.policyUpdateData.Delete(policyName)
|
||||
}()
|
||||
// get policy
|
||||
|
@ -139,6 +174,7 @@ func (psa *PolicyStatusAggregator) UpdateViolationCount(policyName string, pvLis
|
|||
newStatus := calculateStatus(pvList)
|
||||
if reflect.DeepEqual(newStatus, policy.Status) {
|
||||
// no update to status
|
||||
glog.V(4).Infof("no changes in policy violation count for policy %s", policy.Name)
|
||||
return nil
|
||||
}
|
||||
// update status
|
||||
|
@ -151,7 +187,7 @@ func (psa *PolicyStatusAggregator) UpdateViolationCount(policyName string, pvLis
|
|||
func calculateStatus(pvList []*kyverno.PolicyViolation) kyverno.PolicyStatus {
|
||||
violationCount := len(pvList)
|
||||
status := kyverno.PolicyStatus{
|
||||
Violations: violationCount,
|
||||
ViolationCount: violationCount,
|
||||
}
|
||||
return status
|
||||
}
|
||||
|
@ -166,6 +202,7 @@ type PStatusControlInterface interface {
|
|||
UpdatePolicyStatus(newPolicy *kyverno.Policy) error
|
||||
}
|
||||
|
||||
//PSControl allows update for policy status
|
||||
type PSControl struct {
|
||||
Client kyvernoclient.Interface
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue