Skip to content

Commit

Permalink
Merge pull request #94 from kubescape/silence
Browse files Browse the repository at this point in the history
add presave processor to deduplicate profile info
  • Loading branch information
matthyx authored Feb 5, 2024
2 parents 54e72de + 4a89322 commit a4538df
Show file tree
Hide file tree
Showing 8 changed files with 620 additions and 48 deletions.
27 changes: 27 additions & 0 deletions pkg/apis/softwarecomposition/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ package softwarecomposition

import (
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"strings"
)

// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
Expand Down Expand Up @@ -314,11 +315,37 @@ type ExecCalls struct {
Envs []string
}

const sep = "␟"

func (e ExecCalls) String() string {
s := strings.Builder{}
s.WriteString(e.Path)
for _, arg := range e.Args {
s.WriteString(sep)
s.WriteString(arg)
}
for _, env := range e.Envs {
s.WriteString(sep)
s.WriteString(env)
}
return s.String()
}

type OpenCalls struct {
Path string
Flags []string
}

func (e OpenCalls) String() string {
s := strings.Builder{}
s.WriteString(e.Path)
for _, arg := range e.Flags {
s.WriteString(sep)
s.WriteString(arg)
}
return s.String()
}

type ApplicationProfileStatus struct {
}

Expand Down
77 changes: 77 additions & 0 deletions pkg/apis/softwarecomposition/types_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -268,3 +268,80 @@ func Test_SeveritySummaryAdd(t *testing.T) {
}

}

func TestExecCalls_String(t *testing.T) {
tests := []struct {
name string
e ExecCalls
want string
}{
{
name: "Empty",
e: ExecCalls{},
want: "",
},
{
name: "Path only",
e: ExecCalls{
Path: "ls",
},
want: "ls",
},
{
name: "Path and args",
e: ExecCalls{
Path: "ls",
Args: []string{"-l", "-a"},
},
want: "ls␟-l␟-a",
},
{
name: "Path and args and env",
e: ExecCalls{
Path: "ls",
Args: []string{"-l", "-a"},
Envs: []string{"HOME=/home/user", "USER=user"},
},
want: "ls␟-l␟-a␟HOME=/home/user␟USER=user",
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
assert.Equalf(t, tt.want, tt.e.String(), "String()")
})
}
}

func TestOpenCalls_String(t *testing.T) {
tests := []struct {
name string
o OpenCalls
want string
}{
{
name: "Empty",
o: OpenCalls{},
want: "",
},
{
name: "Path only",
o: OpenCalls{
Path: "/etc/passwd",
},
want: "/etc/passwd",
},
{
name: "Path and flags",
o: OpenCalls{
Path: "/etc/passwd",
Flags: []string{"O_RDONLY"},
},
want: "/etc/passwd␟O_RDONLY",
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
assert.Equalf(t, tt.want, tt.o.String(), "String()")
})
}
}
3 changes: 2 additions & 1 deletion pkg/apiserver/apiserver.go
Original file line number Diff line number Diff line change
Expand Up @@ -149,6 +149,7 @@ func (c completedConfig) New() (*WardleServer, error) {

storageImpl := file.NewStorageImpl(osFs, file.DefaultStorageRoot)

applicationProfileStorageImpl := file.NewStorageImplWithCollector(osFs, file.DefaultStorageRoot, &file.ApplicationProfileProcessor{})
configScanStorageImpl := file.NewConfigurationScanSummaryStorage(&storageImpl)
vulnerabilitySummaryStorage := file.NewVulnerabilitySummaryStorage(&storageImpl)
generatedNetworkPolicyStorage := file.NewGeneratedNetworkPolicyStorage(&storageImpl)
Expand All @@ -168,7 +169,7 @@ func (c completedConfig) New() (*WardleServer, error) {
v1beta1storage["configurationscansummaries"] = sbomregistry.RESTInPeace(configurationscansummary.NewREST(Scheme, configScanStorageImpl, c.GenericConfig.RESTOptionsGetter))
v1beta1storage["vulnerabilitysummaries"] = sbomregistry.RESTInPeace(vsumstorage.NewREST(Scheme, vulnerabilitySummaryStorage, c.GenericConfig.RESTOptionsGetter))

v1beta1storage["applicationprofiles"] = sbomregistry.RESTInPeace(applicationprofile.NewREST(Scheme, storageImpl, c.GenericConfig.RESTOptionsGetter))
v1beta1storage["applicationprofiles"] = sbomregistry.RESTInPeace(applicationprofile.NewREST(Scheme, applicationProfileStorageImpl, c.GenericConfig.RESTOptionsGetter))
v1beta1storage["applicationprofilesummaries"] = sbomregistry.RESTInPeace(applicationprofilesummary.NewREST(Scheme, storageImpl, c.GenericConfig.RESTOptionsGetter))
v1beta1storage["applicationactivities"] = sbomregistry.RESTInPeace(applicationactivity.NewREST(Scheme, storageImpl, c.GenericConfig.RESTOptionsGetter))

Expand Down
64 changes: 64 additions & 0 deletions pkg/registry/file/processor.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
package file

import (
"fmt"
sets "github.com/deckarep/golang-set/v2"
"github.com/kubescape/storage/pkg/apis/softwarecomposition"
"k8s.io/apimachinery/pkg/runtime"
)

type Processor interface {
PreSave(object runtime.Object) error
}

type DefaultProcessor struct {
}

var _ Processor = (*DefaultProcessor)(nil)

func (d DefaultProcessor) PreSave(_ runtime.Object) error {
return nil
}

type ApplicationProfileProcessor struct {
}

var _ Processor = (*ApplicationProfileProcessor)(nil)

func (a ApplicationProfileProcessor) PreSave(object runtime.Object) error {
profile, ok := object.(*softwarecomposition.ApplicationProfile)
if !ok {
return fmt.Errorf("given object is not an ApplicationProfile")
}
for i, container := range profile.Spec.Containers {
profile.Spec.Containers[i] = deflate(container)
}
return nil
}

func deflate(container softwarecomposition.ApplicationProfileContainer) softwarecomposition.ApplicationProfileContainer {
return softwarecomposition.ApplicationProfileContainer{
Name: container.Name,
Capabilities: sets.NewThreadUnsafeSet(container.Capabilities...).ToSlice(),
Execs: deflateStringer(container.Execs),
Opens: deflateStringer(container.Opens),
Syscalls: sets.NewThreadUnsafeSet(container.Syscalls...).ToSlice(),
}
}

type Stringer interface {
String() string
}

func deflateStringer[T Stringer](in []T) []T {
var out []T
set := sets.NewThreadUnsafeSet[string]()
for _, item := range in {
if set.Contains(item.String()) {
continue
}
set.Add(item.String())
out = append(out, item)
}
return out
}
Loading

0 comments on commit a4538df

Please sign in to comment.