Skip to content
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

Partial support for User resource, e2e test #32

Merged
merged 1 commit into from
Jun 11, 2021

Conversation

echen-98
Copy link
Contributor

@echen-98 echen-98 commented Jun 4, 2021

Issue #, if available:

Description of changes:

Summary of the generator config/custom code:

  • add terminal codes
  • add additional Status fields for AccessString state-keeping which are only modified upon creation or modification of the User (needed because the ElastiCache API returns an expanded AccessString different than the one specified)
  • "custom modify" code only handles requeues (no actual modification done)
  • remove differences from Delta which are not meaningful
  • only populate update payload with fields that have actual differences between desired/latest (via ignoring most field paths in default modify payload and using a post_build_request hook)
  • post_set_output hook handles synced condition
  • e2e CRUD test

Working on this has revealed the need for a couple small improvements in common repos (see below) which could significantly simplify the code. So although we need some more custom code (e.g. secrets support for Passwords field among other things) this feels like a good stopping point until those get resolved.

aws-controllers-k8s/community#806
aws-controllers-k8s/community#808

By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license.

@RedbackThomson
Copy link
Contributor

/ok-to-test
/test elasticache-kind-e2e
/test elasticache-unit-test

@ack-bot ack-bot added the ok-to-test Indicates a non-member PR verified by an org member that is safe to test. label Jun 4, 2021
Comment on lines 33 to 35
// Passwords used for this user. You can create up to two passwords for each
// user.
Passwords []*string `json:"passwords,omitempty"`
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This needs to be of *ackv1alpha1.SecretKeyReference type.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please refer next comment for details:

This needs to be array of K8s Secret type.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As discussed on this PR and offline, we will temporarily disable the passwords field for this PR, and I will follow up soon with another PR making use of aws-controllers-k8s/code-generator#87 to support this

Comment on lines 48 to 53
passwords:
description: Passwords used for this user. You can create up to two
passwords for each user.
items:
type: string
type: array
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This needs to be array of K8s Secret type.
Please refer replication group yaml authToken field for reference.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@kumargauravsharma see the PR description... @echen-98 identified this as being a problem.

Since Passwords is a slice of string and *ackv1alpha1.SecretKeyReference refers to a single secret key, not multiple things, we have a mismatch here.

If you mark User.spec.passwords as is_secret, you will essentially need to write custom code for handling all of User's newCreateBuildRequest and setOutput code points. This custom code will need to translate between a single string value stored in the SecretKeyReference and the multiple strings needed in the Passwords field of the CreateUserInput shape... You will need to deal with the whole "up to two passwords" constraint manually in custom code and have the user place the passwords in a comma-delimited string in the SecretKeyReference storage.

Alternately, you could set the User.spec.passwords and User.spec.noPasswordRequired fields as is_ignored in the generator config and set noPasswordRequired to always be true in the CreateUserInput shape...

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jaypipes Thanks for pointing that out. I was initially considering something closer to the latter option and leaving support for the passwords field for later. As a result I wasn't aware of this additional challenge.

At the same time the passwords are an important part of the User APIs, so I'll look into it further

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jaypipes thanks for your inputs.
My comment was to have it as array (slice) of K8s Secret type.
Thus the generated Spec code would have this property as:

Passwords []*ackv1alpha1.SecretKeyReference `json:"passwords,omitempty"`

and the corresponding crd would look like:

         passwords:
             description: Passwords used for this user. You can create up to two passwords for each user.
             type: array
             items:
                properties:
                  key:
                    description: Key is the key within the secret
                    type: string
                  name:
                    description: Name is unique within a namespace to reference a
                      secret resource.
                    type: string
                  namespace:
                    description: Namespace defines the space within which the secret
                      name must be unique.
                    type: string
                required:
                - key
                type: object

With this, there is no need to store multiple password strings into single K8s secret field.
Rather, each password in slice will have its corresponding K8s secret field for value.

Copy link
Contributor

@kumargauravsharma kumargauravsharma Jun 9, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We considered not to exclude password fields from spec.
However, to not block this PR for this change, temporarily we can remove this field from the spec if at the moment, its not feasible to have

Passwords []*ackv1alpha1.SecretKeyReference `json:"passwords,omitempty"`

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@kumargauravsharma sounds good, I will follow up with another revision and then keep the support for the passwords field as a follow-up.

I'll probably also rename the PR and commit to say "partial support" to convey this.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

PR: aws-controllers-k8s/code-generator#87 adds support for K8s Secret for slice types.

Comment on lines +157 to +161
CreateUser:
set_output_custom_method_name: CustomCreateUserSetOutput
ModifyUser:
custom_implementation: CustomModifyUser
set_output_custom_method_name: CustomModifyUserSetOutput
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These can be removed and required logic can be added to hooks configuration that is already specified for these methods in this PR.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We need to do 2 things after receiving an API response:

  1. set the synced condition based on the User's status.status
  2. update the state-keeping status fields of LastRequestedAccessString and ExpandedAccessString, but only upon successful create and modify calls. The logic to handle the access string depends on LastRequestedAccessString to not be changed upon describe calls.

It's certainly possible to move the first item to the custom hooks, but then we would need two separate hook functions:

  1. One that gets called from create and modify, that does both the items above.
  2. One that gets called from read, that does only the second item above.

I think this approach might make first hook a bit too convoluted in terms of combining two tasks into one. Further, since it would be called from both sdkCreate and sdkUpdate, but the API response types are different, we would need to pass in both resp.Status and resp.AccessString as separate arguments.

I chose the initial approach since the task accomplished by the hook and the task accomplished by the set_output functions are separated and well-defined, but if I'm missing a simpler way to do this please let me know.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks for the details @echen-98
lets keep it as for now

Comment on lines 39 to 40
//TODO: this field requires the use of k8s secrets
if delta.DifferentAt("Passwords") && r.ko.Spec.Passwords != nil {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please update the code for this TODO.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As discussed above, will remove password-related code and keep it for the next PR

Copy link
Contributor

@jaypipes jaypipes left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is definitely going to be a tricky one due to the odd shape of the Elasticache CreateUser APIs...

Comment on lines 48 to 53
passwords:
description: Passwords used for this user. You can create up to two
passwords for each user.
items:
type: string
type: array
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@kumargauravsharma see the PR description... @echen-98 identified this as being a problem.

Since Passwords is a slice of string and *ackv1alpha1.SecretKeyReference refers to a single secret key, not multiple things, we have a mismatch here.

If you mark User.spec.passwords as is_secret, you will essentially need to write custom code for handling all of User's newCreateBuildRequest and setOutput code points. This custom code will need to translate between a single string value stored in the SecretKeyReference and the multiple strings needed in the Passwords field of the CreateUserInput shape... You will need to deal with the whole "up to two passwords" constraint manually in custom code and have the user place the passwords in a comma-delimited string in the SecretKeyReference storage.

Alternately, you could set the User.spec.passwords and User.spec.noPasswordRequired fields as is_ignored in the generator config and set noPasswordRequired to always be true in the CreateUserInput shape...

@echen-98
Copy link
Contributor Author

/test elasticache-kind-e2e

@echen-98
Copy link
Contributor Author

/retest

1 similar comment
@echen-98
Copy link
Contributor Author

/retest

@echen-98 echen-98 changed the title Initial support for User resource, e2e test Partial support for User resource, e2e test Jun 10, 2021
@ack-bot
Copy link
Collaborator

ack-bot commented Jun 10, 2021

@echen-98: The following test failed, say /retest to rerun all failed tests:

Test name Commit Details Rerun command
elasticache-kind-e2e b4e76c3 link /test elasticache-kind-e2e

Full PR test history. Your PR dashboard.

Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository. I understand the commands that are listed here.

@echen-98
Copy link
Contributor Author

e2e test job is now running properly. Some tests are failing but the one associated with this PR is passing:

 [gw1] [ 14%] SKIPPED tests/test_replicationgroup_largecluster.py::TestReplicationGroupLargeCluster::test_rg_largecluster 
[gw0] [ 28%] ERROR tests/test_replicationgroup.py::TestReplicationGroup::test_rg_input_coverage 
tests/test_replicationgroup.py::TestReplicationGroup::test_rg_cmd_fromsnapshot 
[gw2] [ 42%] PASSED tests/test_user.py::TestUser::test_CRUD 
[gw3] [ 57%] PASSED tests/test_snapshot.py::TestSnapshot::test_snapshot_kms 
[gw0] [ 71%] FAILED tests/test_replicationgroup.py::TestReplicationGroup::test_rg_cmd_fromsnapshot 
tests/test_replicationgroup.py::TestReplicationGroup::test_rg_cmd_update 
[gw0] [ 85%] PASSED tests/test_replicationgroup.py::TestReplicationGroup::test_rg_cmd_update 
tests/test_replicationgroup.py::TestReplicationGroup::test_rg_auth_token 
[gw0] [100%] ERROR tests/test_replicationgroup.py::TestReplicationGroup::test_rg_auth_token 
[gw0] [100%] ERROR tests/test_replicationgroup.py::TestReplicationGroup::test_rg_auth_token 

I will investigate the test failures and address them in another PR if needed

@ack-bot
Copy link
Collaborator

ack-bot commented Jun 11, 2021

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: echen-98, kumargauravsharma

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Needs approval from an approver in each of these files:
  • OWNERS [echen-98,kumargauravsharma]

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
approved ok-to-test Indicates a non-member PR verified by an org member that is safe to test.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants