Open christopherhein opened 6 years ago
hey @christopherhein ! What do you mean with
This should be a cluster-wide resource, as well when they use a standard policy name it should use aws as the account id in the arn.
Does it mean that the IAM Role Resource should be created in a shared namespace instead of the same namespace where the application is running? We are currently creating AWS resources using other tools and we are considering moving into this operator. Our current setup creates an IAM Role for every single application. This IAM Role contains the IAM Policies required by the application, like access to the application's S3 bucket, application's KMS keys and so on. Thanks!
The idea here is in AWS IAM Roles and Policies are treated at the global namespace meaning they are shared across regions, in Kubernetes and AWS we have the concept of namespaces but then we also have cluster wide components like cluster-roles
this is delineated in the CRD using the scope
attribute with the Operator right now the code generator doesn't support changing from Namespaced
to Cluster
but it should be an easy addition. That's what that is referring to. The Roles will be in the global namespace and then your application would reference them using something like kube2iam
We'd need to reference other AWS resources created by this operator like S3 buckets, in the Policies that would be attached to the IAM Role for the application. If we want to programatically create this policies, maybe we should label the AWS resources created in the Kubernetes API with the application name, try to filter using the label and take the output
field from those resources to use them in the Policy, right?
That wasn't my initial thought, how I'd originally envisioned and started prototyping this was using #58 for the policies, treating them more like we treat ClusterRoles
and Bindings
it makes it more declarative and easier to track changes, everything is self-documented for a specific policy, you can change that policy without having to reapply a pod manifest, and also from an implementation reduces the amount of custom work that needs to be done.
So if you check out the example:
apiVersion: operator.aws/v1alpha1
kind: IAMRole
metadata:
name: aws-operator
spec:
policies:
- aws-operator
- AdministratorAccess
the keys under spec.policies
is a list of strings and those strings (besides the whitelisted names, which are defaults in your AWS account) those would reference a named policy that would be built from another CRD in #58.
Note: with #58, I'm still very WIP about how those would be defined and modeled given how the standard IAM policies are encoded in
json
.
I see. But do you think this would make sense?
apiVersion: operator.aws/v1alpha1
kind: IAMRole
metadata:
name: my-awesome-app
spec:
policies:
- my-awesome-app-kms
- my-awesome-app-s3
This role would be used by my-awesome-app
to access its own s3 bucket and to encrypt/decrypt using its own KMS key. This way, only my-awesome-app
is allowed to use these resources, and every application has their own AWS resources and policies that allow access to them.
Normally, we don't share AWS resources like databases, S3 buckets or KMS keys between applications. That's why we'd like to limit the access to the application.
I would love more feedback on this but I don't think the solution outlined precludes what you are saying actually. It just models the resources similar to the way the AWS IAM is modeled being a global service… if you make a policy or role it's accessible to region A and region B.
The way it is structured in that sample manifest allows you to use of all policies including the standard policies in every AWS Account, (the whitelist) from within the role and they get backed up to individual policies outside of the role. This enables but doesn't force other roles to use that same policy. An example of this could be two applications that need write capability to an SQS queue, you could write the policy once and reference it in the two separate roles one for each application.
What we lose by structuring it this way is inline policies, is this a deal breaker? Given that the operator is creating and managing those resources for you, you likely won't need to do anything in the console to make this happen.
To give a more clear example if you had a role/policy that needed write access to SQS
and you could write a single file that looked like this:
---
apiVersion: service-operator.aws/v1alpha1
kind: IAMPolicy
metadata:
name: foo-app-sqs-policy
spec:
sqs:
write:
- SendMessage
resource:
- arn:aws:sqs:*:123456789012:foo-app
---
apiVersion: service-operator.aws/v1alpha1
kind: IAMRole
metadata:
name: foo-app-role
spec:
policies:
- foo-app-sqs-policy
Then if later in development you need to mutate the role and give it read-only S3 access you can simply mutate the spec.policies
list and add AmazonS3ReadOnlyAccess
being a whitelisted policy.
Doesn't that help? Concerns?
I like the separation of concerns with kind: IAMPolicy
and kind: IAMRole
Hello @christopherhein ! Any updates about creating IAM resources with aws-service-operator? I would like to try it.
Hey @Avolynsk I don't as of now. I've been working on the build out of #153 which will encompass it but it's still a bit out. Is this something you need ASAP?
Yeah, managing IAM resources is a hot issue for me at the moment.
Hey @christopherhein, any movement on the code gen part of this project? I'm pretty interesting getting the IAM into the operator and would like to help if needed. I'm a noob to operators and Go but happy to give it a shot if you're open to it.
Let me know where it's at and where I can help, if at all.
This will allow you to model an IAM role for your applications. These will reference policy names either via the name in IAM from defaults or using the IAM Policy resource in #58.
This should be a cluster-wide resource, as well when they use a standard policy name it should use
aws
as the account id in the arn.whitelisted policy names