adding yaml input

This commit is contained in:
dwertent
2021-08-26 12:11:04 +03:00
parent 6414be3c6f
commit 8f4ac5dd87
6 changed files with 169 additions and 25 deletions

1
go.mod
View File

@@ -23,6 +23,7 @@ require (
github.com/satori/go.uuid v1.2.0
golang.org/x/oauth2 v0.0.0-20210810183815-faf39c7919d5
gopkg.in/square/go-jose.v2 v2.6.0 // indirect
gopkg.in/yaml.v2 v2.4.0
k8s.io/api v0.22.0
k8s.io/apimachinery v0.22.0
k8s.io/client-go v0.22.0

Binary file not shown.

View File

@@ -0,0 +1,114 @@
package policyhandler
import (
"bytes"
"encoding/json"
"fmt"
"io/ioutil"
"kube-escape/cautils"
"path/filepath"
"gopkg.in/yaml.v2"
)
var (
YAML_PREFIX = []string{".yaml", ".yml"}
JSON_PREFIX = []string{".json"}
)
// // build resources map
// k8sResourcesMap := setResourceMap(frameworks)
func loadFiles(filePaths []string) {
for i := range filePaths {
loadFile(filePaths[i])
}
}
func loadFile(filePath string) (interface{}, error) {
var obj interface{}
var err error
if isYaml(filePath) {
obj, err = loadYamlFile(filePath)
} else if isJson(filePath) {
obj, err = loadJsonFile(filePath)
} else {
return nil, fmt.Errorf("Unknown file format")
}
if err != nil {
return obj, err
}
if _, ok := obj.([]interface{}); ok {
return obj, nil
}
return []interface{}{obj}, nil
}
func listFiles(patterns []string) ([]string, []error) {
files := []string{}
errs := []error{}
for i := range patterns {
f, err := filepath.Glob(patterns[i])
if err != nil {
errs = append(errs, err)
} else {
files = append(files, f...)
}
}
return files, errs
}
func loadYamlFile(filePath string) (interface{}, error) {
yamlFile, err := ioutil.ReadFile(filePath)
if err != nil {
return nil, err
}
r := bytes.NewReader(yamlFile)
dec := yaml.NewDecoder(r)
var t interface{}
yamlObjs := []interface{}{}
for dec.Decode(&t) == nil {
var yamlObj interface{}
if err := yaml.Unmarshal(yamlFile, &yamlObj); err != nil {
return yamlObj, err
}
yamlObjs = append(yamlObjs, t)
}
return convertYamlToJson(yamlObjs), nil
}
func loadJsonFile(filePath string) (interface{}, error) {
var jsonObj interface{}
jsonFile, err := ioutil.ReadFile(filePath)
if err != nil {
return jsonObj, err
}
if err = json.Unmarshal(jsonFile, &jsonObj); err != nil {
return jsonObj, err
}
return jsonObj, nil
}
func convertYamlToJson(i interface{}) interface{} {
switch x := i.(type) {
case map[interface{}]interface{}:
m2 := map[string]interface{}{}
for k, v := range x {
m2[k.(string)] = convertYamlToJson(v)
}
return m2
case []interface{}:
for i, v := range x {
x[i] = convertYamlToJson(v)
}
}
return i
}
func isYaml(filePath string) bool {
return cautils.StringInSlice(YAML_PREFIX, filepath.Ext(filePath)) != cautils.ValueNotFound
}
func isJson(filePath string) bool {
return cautils.StringInSlice(YAML_PREFIX, filepath.Ext(filePath)) != cautils.ValueNotFound
}

View File

@@ -0,0 +1,8 @@
package policyhandler
import "testing"
func TestLoadFiles(t *testing.T) {
loadFiles([]string{})
}

View File

@@ -1,15 +1,12 @@
package policyhandler
import (
"flag"
"fmt"
"kube-escape/cautils"
"kube-escape/cautils/k8sinterface"
"kube-escape/cautils/opapolicy"
"github.com/golang/glog"
)
// PolicyHandler -
@@ -28,40 +25,26 @@ func NewPolicyHandler(processPolicy *chan *cautils.OPASessionObj, k8s *k8sinterf
}
func (policyHandler *PolicyHandler) HandleNotificationRequest(notification *opapolicy.PolicyNotification) error {
glog.Infof("Processing notification. reportID: %s", notification.ReportID)
opaSessionObj := cautils.NewOPASessionObj(nil, nil)
// validate notification
// TODO
// get policies
glog.Infof(fmt.Sprintf("Getting %d policies from backend. reportID: %s", len(notification.Rules), notification.ReportID))
cautils.ProgressTextDisplay("Downloading framework definitions")
frameworks, err := policyHandler.GetPoliciesFromBackend(notification)
frameworks, err := policyHandler.getPolicies(notification)
if err != nil {
return err
}
if len(frameworks) == 0 {
err := fmt.Errorf("Could not download any policies, please check previous logs")
return err
return fmt.Errorf("empty list of frameworks")
}
opaSessionObj.Frameworks = frameworks
cautils.SuccessTextDisplay("Downloaded framework")
// store policies as configmaps
// TODO
// get k8s resources
cautils.ProgressTextDisplay("Accessing Kubernetes objects")
glog.Infof(fmt.Sprintf("Getting kubernetes objects. reportID: %s", notification.ReportID))
excludedNamespaces := ""
if flag.Arg(3) == "--exclude-namespaces" {
excludedNamespaces = flag.Arg(4)
k8sResources, err := policyHandler.getResources(notification, opaSessionObj)
if err != nil {
return err
}
k8sResources, err := policyHandler.getK8sResources(frameworks, &notification.Designators, excludedNamespaces)
if err != nil || len(*k8sResources) == 0 {
glog.Error(err)
} else {
cautils.SuccessTextDisplay("Accessed successfully to Kubernetes objects, lets start!!!")
if k8sResources == nil || len(*k8sResources) == 0 {
return fmt.Errorf("empty list of resources")
}
opaSessionObj.K8SResources = k8sResources
@@ -69,3 +52,37 @@ func (policyHandler *PolicyHandler) HandleNotificationRequest(notification *opap
*policyHandler.processPolicy <- opaSessionObj
return nil
}
func (policyHandler *PolicyHandler) getPolicies(notification *opapolicy.PolicyNotification) ([]opapolicy.Framework, error) {
cautils.ProgressTextDisplay("Downloading framework definitions")
// TODO - support load policies from local file
frameworks, err := policyHandler.GetPoliciesFromBackend(notification)
if err != nil {
return frameworks, err
}
if len(frameworks) == 0 {
err := fmt.Errorf("could not download any policies, please check previous logs")
return frameworks, err
}
cautils.SuccessTextDisplay("Downloaded framework")
return frameworks, nil
}
func (policyHandler *PolicyHandler) getResources(notification *opapolicy.PolicyNotification, opaSessionObj *cautils.OPASessionObj) (*cautils.K8SResources, error) {
var k8sResources *cautils.K8SResources
var err error
paths := []string{}
if len(paths) > 0 {
//
} else {
excludedNamespaces := ""
k8sResources, err = policyHandler.getK8sResources(opaSessionObj.Frameworks, &notification.Designators, excludedNamespaces)
}
return k8sResources, err
}

View File

@@ -20,6 +20,9 @@ import (
const SelectAllResources = "*"
func (policyHandler *PolicyHandler) getK8sResources(frameworks []opapolicy.Framework, designator *armotypes.PortalDesignator, excludedNamespaces string) (*cautils.K8SResources, error) {
// get k8s resources
cautils.ProgressTextDisplay("Accessing Kubernetes objects")
// build resources map
k8sResourcesMap := setResourceMap(frameworks)
@@ -31,6 +34,7 @@ func (policyHandler *PolicyHandler) getK8sResources(frameworks []opapolicy.Frame
return k8sResourcesMap, err
}
cautils.SuccessTextDisplay("Accessed successfully to Kubernetes objects, lets start!!!")
return k8sResourcesMap, nil
}
@@ -66,7 +70,7 @@ func (policyHandler *PolicyHandler) pullSingleResource(resource *schema.GroupVer
listOptions.FieldSelector += "metadata.namespace!=" + excludedNamespace + ","
}
}
if labels != nil && len(labels) > 0 {
if len(labels) > 0 {
set := k8slabels.Set(labels)
listOptions.LabelSelector = set.AsSelector().String()
}