Skip to content

Commit

Permalink
feat: improve compilers package (#507)
Browse files Browse the repository at this point in the history
Signed-off-by: Charles-Edouard Brétéché <charles.edouard@nirmata.com>
  • Loading branch information
eddycharly authored Sep 21, 2024
1 parent fc7ad29 commit a7d5579
Show file tree
Hide file tree
Showing 15 changed files with 42 additions and 45 deletions.
5 changes: 2 additions & 3 deletions pkg/commands/jp/query/command.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import (

"github.com/jmespath-community/go-jmespath/pkg/parsing"
"github.com/kyverno/kyverno-json/pkg/command"
"github.com/kyverno/kyverno-json/pkg/core/templating"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
"github.com/spf13/cobra"
"sigs.k8s.io/yaml"
)
Expand Down Expand Up @@ -155,8 +155,7 @@ func loadInput(cmd *cobra.Command, file string) (any, error) {
}

func evaluate(input any, query string) (any, error) {
compiler := templating.DefaultCompiler
result, err := templating.Execute(query, input, nil, compiler.Jp)
result, err := compilers.Execute(query, input, nil, compilers.DefaultCompiler.Jp)
if err != nil {
if syntaxError, ok := err.(parsing.SyntaxError); ok {
return nil, fmt.Errorf("%s\n%s", syntaxError, syntaxError.HighlightLocation())
Expand Down
5 changes: 2 additions & 3 deletions pkg/commands/scan/options.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import (
"strings"

"github.com/kyverno/kyverno-json/pkg/apis/policy/v1alpha1"
"github.com/kyverno/kyverno-json/pkg/core/templating"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
jsonengine "github.com/kyverno/kyverno-json/pkg/json-engine"
"github.com/kyverno/kyverno-json/pkg/payload"
"github.com/kyverno/kyverno-json/pkg/policy"
Expand Down Expand Up @@ -76,9 +76,8 @@ func (c *options) run(cmd *cobra.Command, _ []string) error {
return errors.New("payload is `null`")
}
out.println("Pre processing ...")
compiler := templating.DefaultCompiler
for _, preprocessor := range c.preprocessors {
result, err := templating.Execute(preprocessor, payload, nil, compiler.Jp)
result, err := compilers.Execute(preprocessor, payload, nil, compilers.DefaultCompiler.Jp)
if err != nil {
return err
}
Expand Down
9 changes: 4 additions & 5 deletions pkg/core/assertion/assertion.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import (
"github.com/kyverno/kyverno-json/pkg/core/expression"
"github.com/kyverno/kyverno-json/pkg/core/matching"
"github.com/kyverno/kyverno-json/pkg/core/projection"
"github.com/kyverno/kyverno-json/pkg/core/templating"
reflectutils "github.com/kyverno/kyverno-json/pkg/utils/reflect"
"k8s.io/apimachinery/pkg/util/validation/field"
)
Expand All @@ -20,7 +19,7 @@ type Assertion interface {
Assert(*field.Path, any, binding.Bindings) (field.ErrorList, error)
}

func Parse(assertion any, compiler templating.Compiler) (node, error) {
func Parse(assertion any, compiler compilers.Compilers) (node, error) {
switch reflectutils.GetKind(assertion) {
case reflect.Slice:
return parseSlice(assertion, compiler)
Expand All @@ -41,7 +40,7 @@ func (n node) Assert(path *field.Path, value any, bindings binding.Bindings) (fi
// parseSlice is the assertion represented by a slice.
// it first compares the length of the analysed resource with the length of the descendants.
// if lengths match all descendants are evaluated with their corresponding items.
func parseSlice(assertion any, compiler templating.Compiler) (node, error) {
func parseSlice(assertion any, compiler compilers.Compilers) (node, error) {
var assertions []node
valueOf := reflect.ValueOf(assertion)
for i := 0; i < valueOf.Len(); i++ {
Expand Down Expand Up @@ -77,7 +76,7 @@ func parseSlice(assertion any, compiler templating.Compiler) (node, error) {

// parseMap is the assertion represented by a map.
// it is responsible for projecting the analysed resource and passing the result to the descendant
func parseMap(assertion any, compiler templating.Compiler) (node, error) {
func parseMap(assertion any, compiler compilers.Compilers) (node, error) {
assertions := map[any]struct {
projection.Projection
node
Expand Down Expand Up @@ -162,7 +161,7 @@ func parseMap(assertion any, compiler templating.Compiler) (node, error) {
// parseScalar is the assertion represented by a leaf.
// it receives a value and compares it with an expected value.
// the expected value can be the result of an expression.
func parseScalar(assertion any, compiler templating.Compiler) (node, error) {
func parseScalar(assertion any, compiler compilers.Compilers) (node, error) {
var project func(value any, bindings binding.Bindings) (any, error)
switch typed := assertion.(type) {
case string:
Expand Down
4 changes: 2 additions & 2 deletions pkg/core/assertion/assertion_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import (
"testing"

"github.com/jmespath-community/go-jmespath/pkg/binding"
"github.com/kyverno/kyverno-json/pkg/core/templating"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
tassert "github.com/stretchr/testify/assert"
"k8s.io/apimachinery/pkg/util/validation/field"
)
Expand Down Expand Up @@ -48,7 +48,7 @@ func TestAssert(t *testing.T) {
}}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
compiler := templating.DefaultCompiler
compiler := compilers.DefaultCompiler
parsed, err := Parse(tt.assertion, compiler)
tassert.NoError(t, err)
got, err := parsed.Assert(nil, tt.value, tt.bindings)
Expand Down
7 changes: 4 additions & 3 deletions pkg/core/compilers/cel/cel.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,12 @@ package cel
import (
"github.com/google/cel-go/cel"
"github.com/jmespath-community/go-jmespath/pkg/binding"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
)

type Program = func(any, binding.Bindings) (any, error)

type Compiler interface {
Compile(string) (compilers.Program, error)
Compile(string) (Program, error)
}

type compiler struct{}
Expand All @@ -16,7 +17,7 @@ func NewCompiler() *compiler {
return &compiler{}
}

func (c *compiler) Compile(statement string) (compilers.Program, error) {
func (c *compiler) Compile(statement string) (Program, error) {
env, err := DefaultEnv()
if err != nil {
return nil, err
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package templating
package compilers

import (
"sync"
Expand All @@ -10,17 +10,17 @@ import (
"k8s.io/apimachinery/pkg/util/validation/field"
)

var DefaultCompiler = Compiler{
var DefaultCompiler = Compilers{
Jp: jp.NewCompiler(),
Cel: cel.NewCompiler(),
}

type Compiler struct {
type Compilers struct {
Jp jp.Compiler
Cel cel.Compiler
}

func (c Compiler) NewBinding(path *field.Path, value any, bindings binding.Bindings, template any) binding.Binding {
func (c Compilers) NewBinding(path *field.Path, value any, bindings binding.Bindings, template any) binding.Binding {
return binding.NewDelegate(
sync.OnceValues(
func() (any, error) {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
package templating
package compilers

import (
"github.com/jmespath-community/go-jmespath/pkg/binding"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
)

func Execute(statement string, value any, bindings binding.Bindings, compiler compilers.Compiler) (any, error) {
func Execute(statement string, value any, bindings binding.Bindings, compiler Compiler) (any, error) {
program, err := compiler.Compile(statement)
if err != nil {
return nil, err
Expand Down
7 changes: 4 additions & 3 deletions pkg/core/compilers/jp/jp.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,12 @@ import (
"github.com/jmespath-community/go-jmespath/pkg/binding"
"github.com/jmespath-community/go-jmespath/pkg/interpreter"
"github.com/jmespath-community/go-jmespath/pkg/parsing"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
)

type Program = func(any, binding.Bindings) (any, error)

type Compiler interface {
Compile(string) (compilers.Program, error)
Compile(string) (Program, error)
Options() []Option
}

Expand All @@ -32,7 +33,7 @@ func (c *compiler) Options() []Option {
return c.options
}

func (c *compiler) Compile(statement string) (compilers.Program, error) {
func (c *compiler) Compile(statement string) (Program, error) {
parser := parsing.NewParser()
compiled, err := parser.Parse(statement)
if err != nil {
Expand Down
2 changes: 1 addition & 1 deletion pkg/core/compilers/program.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,4 @@ import (
"github.com/jmespath-community/go-jmespath/pkg/binding"
)

type Program func(any, binding.Bindings) (any, error)
type Program = func(any, binding.Bindings) (any, error)
3 changes: 1 addition & 2 deletions pkg/core/projection/projection.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@ import (
"github.com/jmespath-community/go-jmespath/pkg/binding"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
"github.com/kyverno/kyverno-json/pkg/core/expression"
"github.com/kyverno/kyverno-json/pkg/core/templating"
reflectutils "github.com/kyverno/kyverno-json/pkg/utils/reflect"
)

Expand All @@ -25,7 +24,7 @@ type Projection struct {
Handler
}

func Parse(in any, compiler templating.Compiler) (projection Projection) {
func Parse(in any, compiler compilers.Compilers) (projection Projection) {
switch typed := in.(type) {
case string:
// 1. if we have a string, parse the expression
Expand Down
4 changes: 2 additions & 2 deletions pkg/core/projection/projection_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import (
"testing"

"github.com/jmespath-community/go-jmespath/pkg/binding"
"github.com/kyverno/kyverno-json/pkg/core/templating"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
tassert "github.com/stretchr/testify/assert"
)

Expand Down Expand Up @@ -88,7 +88,7 @@ func TestProjection(t *testing.T) {
}}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
compiler := templating.DefaultCompiler
compiler := compilers.DefaultCompiler
proj := Parse(tt.key, compiler)
got, found, err := proj.Handler(tt.value, tt.bindings)
if tt.wantErr {
Expand Down
8 changes: 4 additions & 4 deletions pkg/json-engine/engine.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import (

jpbinding "github.com/jmespath-community/go-jmespath/pkg/binding"
"github.com/kyverno/kyverno-json/pkg/apis/policy/v1alpha1"
"github.com/kyverno/kyverno-json/pkg/core/templating"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
"github.com/kyverno/kyverno-json/pkg/engine"
"github.com/kyverno/kyverno-json/pkg/engine/builder"
"github.com/kyverno/kyverno-json/pkg/matching"
Expand Down Expand Up @@ -67,7 +67,7 @@ func New() engine.Engine[Request, Response] {
bindings jpbinding.Bindings
}
compiler := matching.Compiler{
Compiler: templating.DefaultCompiler,
Compilers: compilers.DefaultCompiler,
}
ruleEngine := builder.
Function(func(ctx context.Context, r ruleRequest) []RuleResponse {
Expand All @@ -80,7 +80,7 @@ func New() engine.Engine[Request, Response] {
}
identifier := ""
if r.rule.Identifier != "" {
result, err := templating.Execute(r.rule.Identifier, r.resource, bindings, compiler.Compiler.Jp)
result, err := compilers.Execute(r.rule.Identifier, r.resource, bindings, compiler.Jp)
if err != nil {
identifier = fmt.Sprintf("(error: %s)", err)
} else {
Expand Down Expand Up @@ -119,7 +119,7 @@ func New() engine.Engine[Request, Response] {
}
var feedback map[string]Feedback
for _, f := range r.rule.Feedback {
result, err := templating.Execute(f.Value, r.resource, bindings, compiler.Compiler.Jp)
result, err := compilers.Execute(f.Value, r.resource, bindings, compiler.Jp)
if feedback == nil {
feedback = map[string]Feedback{}
}
Expand Down
12 changes: 6 additions & 6 deletions pkg/matching/compiler.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,11 @@ import (
"github.com/cespare/xxhash/v2"
"github.com/elastic/go-freelru"
"github.com/kyverno/kyverno-json/pkg/core/assertion"
"github.com/kyverno/kyverno-json/pkg/core/templating"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
)

type Compiler struct {
templating.Compiler
compilers.Compilers
*freelru.SyncedLRU[string, func() (assertion.Assertion, error)]
}

Expand All @@ -19,9 +19,9 @@ func hashStringXXHASH(s string) uint32 {
return uint32(sum) //nolint:gosec
}

func NewCompiler(compiler templating.Compiler, cacheSize uint32) Compiler {
func NewCompiler(compiler compilers.Compilers, cacheSize uint32) Compiler {
out := Compiler{
Compiler: compiler,
Compilers: compiler,
}
if cache, err := freelru.NewSynced[string, func() (assertion.Assertion, error)](cacheSize, hashStringXXHASH); err == nil {
out.SyncedLRU = cache
Expand All @@ -31,12 +31,12 @@ func NewCompiler(compiler templating.Compiler, cacheSize uint32) Compiler {

func (c Compiler) CompileAssertion(hash string, value any) (assertion.Assertion, error) {
if c.SyncedLRU == nil {
return assertion.Parse(value, c.Compiler)
return assertion.Parse(value, c.Compilers)
}
entry, _ := c.SyncedLRU.Get(hash)
if entry == nil {
entry = sync.OnceValues(func() (assertion.Assertion, error) {
return assertion.Parse(value, c.Compiler)
return assertion.Parse(value, c.Compilers)
})
c.SyncedLRU.Add(hash, entry)
}
Expand Down
4 changes: 2 additions & 2 deletions pkg/server/playground/handler.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import (

"github.com/gin-gonic/gin"
"github.com/kyverno/kyverno-json/pkg/apis/policy/v1alpha1"
"github.com/kyverno/kyverno-json/pkg/core/templating"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
jsonengine "github.com/kyverno/kyverno-json/pkg/json-engine"
"github.com/kyverno/kyverno-json/pkg/server/model"
"github.com/loopfz/gadgeto/tonic"
Expand All @@ -34,7 +34,7 @@ func newHandler() (gin.HandlerFunc, error) {
}
// apply pre processors
for _, preprocessor := range in.Preprocessors {
result, err := templating.Execute(preprocessor, payload, nil, templating.DefaultCompiler.Jp)
result, err := compilers.Execute(preprocessor, payload, nil, compilers.DefaultCompiler.Jp)
if err != nil {
return nil, fmt.Errorf("failed to execute prepocessor (%s) - %w", preprocessor, err)
}
Expand Down
4 changes: 2 additions & 2 deletions pkg/server/scan/handler.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import (

"github.com/gin-gonic/gin"
"github.com/kyverno/kyverno-json/pkg/apis/policy/v1alpha1"
"github.com/kyverno/kyverno-json/pkg/core/templating"
"github.com/kyverno/kyverno-json/pkg/core/compilers"
jsonengine "github.com/kyverno/kyverno-json/pkg/json-engine"
"github.com/kyverno/kyverno-json/pkg/server/model"
"github.com/loopfz/gadgeto/tonic"
Expand All @@ -26,7 +26,7 @@ func newHandler(policyProvider PolicyProvider) (gin.HandlerFunc, error) {
payload := in.Payload
// apply pre processors
for _, preprocessor := range in.Preprocessors {
result, err := templating.Execute(preprocessor, payload, nil, templating.DefaultCompiler.Jp)
result, err := compilers.Execute(preprocessor, payload, nil, compilers.DefaultCompiler.Jp)
if err != nil {
return nil, fmt.Errorf("failed to execute prepocessor (%s) - %w", preprocessor, err)
}
Expand Down

0 comments on commit a7d5579

Please sign in to comment.