-
Notifications
You must be signed in to change notification settings - Fork 87
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[KEP-0009] feat: add expression based assertions #576
Open
kumar-mallikarjuna
wants to merge
31
commits into
kudobuilder:main
Choose a base branch
from
kumar-mallikarjuna:KEP-0009
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from all commits
Commits
Show all changes
31 commits
Select commit
Hold shift + click to select a range
bd77825
[KEP-0009] feat: add expression based assertions
kumar-mallikarjuna 68c60e3
chore: rename Id->Ref and make linter happy
kumar-mallikarjuna 9a94a6b
chore: add validation for resourceRefs
kumar-mallikarjuna 38819ef
chore: make assertion syntax consistent with the KEP
kumar-mallikarjuna 3a6b02e
refactor: rename Validate method for `TestResourceRef`
kumar-mallikarjuna bd362f2
chore: pre-build environment and program for expressions
kumar-mallikarjuna 14ad7a8
chore: make linter happy and initialize Programs only if assertions a…
kumar-mallikarjuna 6df2e32
chore: incorporate review comments
kumar-mallikarjuna aa6cb65
chore: move RunAssertExpressions() to pkg/expressions
kumar-mallikarjuna 832bf9e
refactor: move CEL program loading to a dedicated function
kumar-mallikarjuna e32b53e
refactor: move program-loading to Step out of LoadPrograms()
kumar-mallikarjuna 3223ada
chore: add tests for `TestResourceRef`
kumar-mallikarjuna f08a27e
fix: correct evaluation for `assertAll`
kumar-mallikarjuna 7cb27fc
chore: add integration tests for expressions
kumar-mallikarjuna 3fcf018
chore: make linter happy
kumar-mallikarjuna c6c3e8a
chore: incorporate review comments
kumar-mallikarjuna 51e3deb
fix: change array reference for all-asserts
kumar-mallikarjuna 32330e9
chore: change signature for `CheckAssertExpressions()`
kumar-mallikarjuna 5e252f5
chore: use envtest in `expression_integration_test.go`
kumar-mallikarjuna 56c1779
fix: remove redundant definitions for integration test tools
kumar-mallikarjuna 2c58b63
chore: use testenv in expression_integration_test.go
kumar-mallikarjuna aa2fa55
fix: run target expressions test within a Kuttl owned ephemeral names…
kumar-mallikarjuna 9e77060
chore: remove redundant file and update go.mod
kumar-mallikarjuna f824fb9
chore: incorporate review comments
kumar-mallikarjuna 965b7eb
chore: update error messages
kumar-mallikarjuna 5173e6c
chore: update error message
kumar-mallikarjuna 4f358b0
chore: incorporate review comments
kumar-mallikarjuna 60b818d
fix: update context creation
kumar-mallikarjuna dd85a98
chore: aggregate test steps into one
kumar-mallikarjuna d510656
chore: remove debug statements
kumar-mallikarjuna 7c164ba
chore(tests): remove prefixes for expression integration test steps
kumar-mallikarjuna File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,65 @@ | ||
package v1beta1 | ||
|
||
import ( | ||
"errors" | ||
"fmt" | ||
"strings" | ||
|
||
"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured" | ||
"k8s.io/apimachinery/pkg/runtime/schema" | ||
"k8s.io/apimachinery/pkg/types" | ||
) | ||
|
||
var ( | ||
errAPIVersionInvalid = errors.New("apiVersion not of the format (<group>/)<version>") | ||
errKindNotSpecified = errors.New("kind not specified") | ||
errNameNotSpecified = errors.New("name not specified") | ||
errRefNotSpecified = errors.New("ref not specified") | ||
) | ||
|
||
func (t *TestResourceRef) BuildResourceReference() (namespacedName types.NamespacedName, referencedResource *unstructured.Unstructured) { | ||
referencedResource = &unstructured.Unstructured{} | ||
apiVersionSplit := strings.Split(t.APIVersion, "/") | ||
gvk := schema.GroupVersionKind{ | ||
Version: apiVersionSplit[len(apiVersionSplit)-1], | ||
Kind: t.Kind, | ||
} | ||
if len(apiVersionSplit) > 1 { | ||
gvk.Group = apiVersionSplit[0] | ||
} | ||
referencedResource.SetGroupVersionKind(gvk) | ||
|
||
namespacedName = types.NamespacedName{ | ||
Namespace: t.Namespace, | ||
Name: t.Name, | ||
} | ||
|
||
return | ||
} | ||
|
||
func (t *TestResourceRef) Validate() error { | ||
apiVersionSplit := strings.Split(t.APIVersion, "/") | ||
switch { | ||
case t.APIVersion == "" || len(apiVersionSplit) > 2: | ||
return errAPIVersionInvalid | ||
case t.Kind == "": | ||
return errKindNotSpecified | ||
case t.Name == "": | ||
return errNameNotSpecified | ||
case t.Ref == "": | ||
return errRefNotSpecified | ||
} | ||
|
||
return nil | ||
} | ||
|
||
func (t *TestResourceRef) String() string { | ||
return fmt.Sprintf( | ||
"apiVersion=%v, kind=%v, namespace=%v, name=%v, ref=%v", | ||
t.APIVersion, | ||
t.Kind, | ||
t.Namespace, | ||
t.Name, | ||
t.Ref, | ||
) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,181 @@ | ||
package v1beta1 | ||
|
||
import ( | ||
"reflect" | ||
"testing" | ||
|
||
"github.com/stretchr/testify/assert" | ||
"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured" | ||
"k8s.io/apimachinery/pkg/runtime/schema" | ||
"k8s.io/apimachinery/pkg/types" | ||
) | ||
|
||
func TestValidate(t *testing.T) { | ||
testCases := []struct { | ||
name string | ||
testResourceRef TestResourceRef | ||
errored bool | ||
expectedError error | ||
}{ | ||
{ | ||
name: "apiVersion is not specified", | ||
testResourceRef: TestResourceRef{ | ||
Kind: "Pod", | ||
Namespace: "test", | ||
Name: "test-pod", | ||
Ref: "testPod", | ||
}, | ||
errored: true, | ||
expectedError: errAPIVersionInvalid, | ||
}, | ||
{ | ||
name: "apiVersion is invalid", | ||
testResourceRef: TestResourceRef{ | ||
APIVersion: "x/y/z", | ||
Kind: "Pod", | ||
Namespace: "test", | ||
Name: "test-pod", | ||
Ref: "testPod", | ||
}, | ||
errored: true, | ||
expectedError: errAPIVersionInvalid, | ||
}, | ||
{ | ||
name: "apiVersion is valid and group is vacuous", | ||
testResourceRef: TestResourceRef{ | ||
APIVersion: "v1", | ||
Kind: "Pod", | ||
Namespace: "test", | ||
Name: "test-pod", | ||
Ref: "testPod", | ||
}, | ||
errored: false, | ||
}, | ||
{ | ||
name: "apiVersion has both group name and version", | ||
testResourceRef: TestResourceRef{ | ||
APIVersion: "apps/v1", | ||
Kind: "Deployment", | ||
Namespace: "test", | ||
Name: "test-deployment", | ||
Ref: "testDeployment", | ||
}, | ||
errored: false, | ||
}, | ||
{ | ||
name: "kind is not specified", | ||
testResourceRef: TestResourceRef{ | ||
APIVersion: "apps/v1", | ||
Namespace: "test", | ||
Name: "test-deployment", | ||
Ref: "testDeployment", | ||
}, | ||
errored: true, | ||
expectedError: errKindNotSpecified, | ||
}, | ||
{ | ||
name: "name is not specified", | ||
testResourceRef: TestResourceRef{ | ||
APIVersion: "apps/v1", | ||
Kind: "Deployment", | ||
Namespace: "test", | ||
Ref: "testDeployment", | ||
}, | ||
errored: true, | ||
expectedError: errNameNotSpecified, | ||
}, | ||
{ | ||
name: "ref is not specified", | ||
testResourceRef: TestResourceRef{ | ||
APIVersion: "apps/v1", | ||
Kind: "Deployment", | ||
Namespace: "test", | ||
Name: "test-deployment", | ||
}, | ||
errored: true, | ||
expectedError: errRefNotSpecified, | ||
}, | ||
{ | ||
name: "all attributes are present and valid", | ||
testResourceRef: TestResourceRef{ | ||
APIVersion: "apps/v1", | ||
Kind: "Deployment", | ||
Namespace: "test", | ||
Name: "test-deployment", | ||
Ref: "testDeployment", | ||
}, | ||
errored: false, | ||
}, | ||
} | ||
|
||
for _, tc := range testCases { | ||
t.Run(tc.name, func(t *testing.T) { | ||
err := tc.testResourceRef.Validate() | ||
if !tc.errored { | ||
assert.NoError(t, err) | ||
} else { | ||
assert.ErrorIs(t, err, tc.expectedError) | ||
} | ||
}) | ||
} | ||
} | ||
|
||
func TestBuildResourceReference(t *testing.T) { | ||
buildObject := func(gvk schema.GroupVersionKind) *unstructured.Unstructured { | ||
obj := &unstructured.Unstructured{} | ||
obj.SetGroupVersionKind(gvk) | ||
return obj | ||
} | ||
|
||
testCases := []struct { | ||
name string | ||
testResourceRef TestResourceRef | ||
namespacedName types.NamespacedName | ||
resourceReference *unstructured.Unstructured | ||
}{ | ||
{ | ||
name: "group name is vacuous", | ||
testResourceRef: TestResourceRef{ | ||
APIVersion: "v1", | ||
Kind: "Pod", | ||
Namespace: "test", | ||
Name: "test-pod", | ||
Ref: "testPod", | ||
}, | ||
namespacedName: types.NamespacedName{ | ||
Namespace: "test", | ||
Name: "test-pod", | ||
}, | ||
resourceReference: buildObject(schema.GroupVersionKind{Group: "", Version: "v1", Kind: "Pod"}), | ||
}, | ||
{ | ||
name: "group name is present", | ||
testResourceRef: TestResourceRef{ | ||
APIVersion: "apps/v1", | ||
Kind: "Deployment", | ||
Namespace: "test", | ||
Name: "test-deployment", | ||
Ref: "testDeployment", | ||
}, | ||
namespacedName: types.NamespacedName{ | ||
Namespace: "test", | ||
Name: "test-deployment", | ||
}, | ||
resourceReference: buildObject(schema.GroupVersionKind{Group: "apps", Version: "v1", Kind: "Deployment"}), | ||
}, | ||
} | ||
|
||
for _, tc := range testCases { | ||
t.Run(tc.name, func(t *testing.T) { | ||
namspacedName, referencedResource := tc.testResourceRef.BuildResourceReference() | ||
assert.Equal(t, tc.namespacedName, namspacedName) | ||
assert.True( | ||
t, | ||
reflect.DeepEqual(tc.resourceReference, referencedResource), | ||
"constructed unstructured reference does not match, expected '%s', got '%s'", | ||
tc.resourceReference, | ||
referencedResource, | ||
) | ||
}) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You should consider two
TestResourceRef
with the same id an error.