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

Authorization HTTPFilter #532

Closed
wants to merge 2 commits into from
Closed

Conversation

jmprusi
Copy link

@jmprusi jmprusi commented Jan 19, 2021

What type of PR is this?
/kind design

What this PR does / why we need it:
This PR shows a possible new Filter design, called RequestAuthorization, that would be used to authorize incoming HTTP requests with an external authorization component.

Design doc: Pluggable Access Control for HTTPRoute

Which issue(s) this PR fixes:
Fixes #114

Does this PR introduce a user-facing change?:

Adds a new HTTPFilter: "RequestAuthorization", that allows users to authorize incoming HTTP request with an external authorization service.

@k8s-ci-robot k8s-ci-robot added do-not-merge/work-in-progress Indicates that a PR should not merge because it is a work in progress. kind/design Categorizes issue or PR as related to design. cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. labels Jan 19, 2021
@k8s-ci-robot
Copy link
Contributor

Welcome @jmprusi!

It looks like this is your first PR to kubernetes-sigs/service-apis 🎉. Please refer to our pull request process documentation to help your PR have a smooth ride to approval.

You will be prompted by a bot to use commands during the review process. Do not be afraid to follow the prompts! It is okay to experiment. Here is the bot commands documentation.

You can also check if kubernetes-sigs/service-apis has its own contribution guidelines.

You may want to refer to our testing guide if you run into trouble with your tests not passing.

If you are having difficulty getting your pull request seen, please follow the recommended escalation practices. Also, for tips and tricks in the contribution process you may want to read the Kubernetes contributor cheat sheet. We want to make sure your contribution gets all the attention it needs!

Thank you, and welcome to Kubernetes. 😃

@k8s-ci-robot
Copy link
Contributor

Hi @jmprusi. Thanks for your PR.

I'm waiting for a kubernetes-sigs member to verify that this patch is reasonable to test. If it is, they should reply with /ok-to-test on its own line. Until that is done, I will not automatically test new commits in this PR, but the usual testing commands by org members will still work. Regular contributors should join the org to skip this step.

Once the patch is verified, the new status will be reflected by the ok-to-test label.

I understand the commands that are listed here.

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.

@k8s-ci-robot k8s-ci-robot added the size/M Denotes a PR that changes 30-99 lines, ignoring generated files. label Jan 19, 2021
apis/v1alpha1/httproute_types.go Outdated Show resolved Hide resolved
// It is expected for the authorization server to implement the Envoy ExtAuthz HTTP protocol:
// https://www.envoyproxy.io/docs/envoy/latest/api-v3/service/auth/v3/external_auth.proto
//
URL string `json:"url"`
Copy link
Contributor

Choose a reason for hiding this comment

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

How does configuration of how to reach this URl work? For example, if we need authentication, TLS, etc.

if it were a k8s service it would be "easy" since existing APIs defined here like BackendPolicy would apply. For a generic URL, I am not sure its easy.

Copy link
Author

Choose a reason for hiding this comment

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

Yes, that's a good point. Thinking out loud, perhaps splitting the URL into a service reference and a type or protocol field to define the type of authorization (grpc/HTTP) could work?

Copy link
Contributor

Choose a reason for hiding this comment

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

That could potentially work, I think some sort of reference is probably more consistent with the rest of the API as well. FWIW we recently went through lots of debate with https://docs.google.com/document/d/1V4mCQCw7mlGp0zSQQXYoBdbKMDnkPOjeyUb85U07iSI/ about this exact topic in Istio.

Copy link
Author

Choose a reason for hiding this comment

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

Thanks, @howardjohn! I will review that document and try to find a better API design.

Copy link
Contributor

Choose a reason for hiding this comment

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

Just getting to review this one now, Contour added an ExtensionService to cover the "service reference" part of this (see https://projectcontour.io/docs/v1.12.0/config/api/#projectcontour.io/v1alpha1.ExtensionService), and then an AuthorizationServer struct that holds the ExtensionService reference. (https://projectcontour.io/docs/v1.12.0/config/api/#projectcontour.io/v1.AuthorizationServer). Both the ExtensionService and AuthorizationServer have places to put config.

I'm not suggesting doing the same thing, but I think the idea of a service reference and a type or protocol field would be great.

Copy link
Author

Choose a reason for hiding this comment

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

@youngnick It already has a protocol field, but for the service reference, we can follow the example of the other filters and replace URL with:

ServiceName *string `json:"serviceName,omitempty"`
BackendRef *LocalObjectReference `json:"backendRef,omitempty"`
Port *PortNumber `json:"port,omitempty"`

Or add a new structure that allows us to cross the namespace boundary, with additional information on how to connect to the external service, like for example a TLS client certificate to use.

apis/v1alpha1/httproute_types.go Outdated Show resolved Hide resolved
@robscott
Copy link
Member

Thanks for the work on this @jmprusi! Based on our conversation yesterday at the community meeting, it seems like there's broad support for an approach like this if we can make it portable. Ideally this filter should be usable with more than Envoy ExtAuthz. It seems like external auth is generally configured with the same approximate concepts:

  • Protocol
  • URL
  • Timeout
  • FailureMode

That seems rather similar to what is already proposed here. I'm hesitant about specifying which underlying approach an implementation of this API should take, but if we can avoid that, I think this has the potential to be a valuable and portable filter.

@jmprusi jmprusi force-pushed the auth_filter branch 2 times, most recently from c356917 to 8bcfc88 Compare February 10, 2021 18:18
@jmprusi
Copy link
Author

jmprusi commented Feb 10, 2021

Thanks for the work on this @jmprusi! Based on our conversation yesterday at the community meeting, it seems like there's broad support for an approach like this if we can make it portable. Ideally this filter should be usable with more than Envoy ExtAuthz. It seems like external auth is generally configured with the same approximate concepts:

  • Protocol
  • URL
  • Timeout
  • FailureMode

That seems rather similar to what is already proposed here. I'm hesitant about specifying which underlying approach an implementation of this API should take, but if we can avoid that, I think this has the potential to be a valuable and portable filter.

I've updated the PR, but I think we should discuss a couple of fields:

  • Metadata: This could be a useful field to add. It will allow the user to add "hardcoded" specific information either for the controller or the authorization service. This can be implemented in the form of a Header for nginx or as context metadata in envoy.
  • RequestBody: Send the original request body to the authorization service or not. This can be configured in Envoy or Nginx.

Another interesting "common" field could be:

  • ForwardHeaders: A list of headers that will be forwarded to the authorization endpoint from the original request, instead of the "default" behavior of sending all of them or a known subset.

@k8s-ci-robot k8s-ci-robot added the needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. label Feb 15, 2021
@k8s-ci-robot
Copy link
Contributor

[APPROVALNOTIFIER] This PR is NOT APPROVED

This pull-request has been approved by: jmprusi
To complete the pull request process, please assign robscott after the PR has been reviewed.
You can assign the PR to them by writing /assign @robscott in a comment when ready.

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

Needs approval from an approver in each of these files:

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

@k8s-ci-robot k8s-ci-robot added size/L Denotes a PR that changes 100-499 lines, ignoring generated files. and removed size/M Denotes a PR that changes 30-99 lines, ignoring generated files. needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. labels Feb 17, 2021
@jmprusi jmprusi changed the title WIP - Authorization HTTPFilter Authorization HTTPFilter Feb 17, 2021
@k8s-ci-robot k8s-ci-robot added needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. and removed do-not-merge/work-in-progress Indicates that a PR should not merge because it is a work in progress. labels Feb 17, 2021
@k8s-ci-robot k8s-ci-robot added size/M Denotes a PR that changes 30-99 lines, ignoring generated files. and removed size/L Denotes a PR that changes 100-499 lines, ignoring generated files. needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. labels Mar 4, 2021
@jmprusi jmprusi requested a review from youngnick March 8, 2021 16:30
@jmprusi jmprusi requested review from danehans and jpeach March 8, 2021 16:30
@bowei
Copy link
Contributor

bowei commented Mar 10, 2021

/ok-to-test

@k8s-ci-robot k8s-ci-robot added ok-to-test Indicates a non-member PR verified by an org member that is safe to test. and removed needs-ok-to-test Indicates a PR that requires an org member to verify it is safe to test. labels Mar 10, 2021
// Support: Extended
//
// +optional
Metadata map[string]string `json:"metadata,omitempty"`
Copy link
Contributor

Choose a reason for hiding this comment

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

AFAIK, only the envoy GRPC protocol can pass arbitrary key value pairs here. How do you indicate missing or partial support for this field?

Copy link
Author

Choose a reason for hiding this comment

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

I think this is for the implementor to decide; for example, in Nginx, this could be implemented as a custom HTTP header sent to the authorization service. Perhaps we should put some validation in place to make that easier, like a max length and allowed characters.

If the implementation doesn't support this, it can reject the route and set the proper status condition.

// Support: Extended
//
// +optional
// +kubebuilder:default=http
Copy link
Contributor

Choose a reason for hiding this comment

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

Can we add enum validation for allowed values?

//
// +optional
// +kubebuilder:default=http
Protocol string `json:"protocol,omitempty"`
Copy link
Contributor

Choose a reason for hiding this comment

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

For protocols over TLS, is there a way to tweak the server certificate validation?

Copy link
Author

Choose a reason for hiding this comment

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

Yes, that would great to have, but I don't see any example of this in the API. I looked at the HTTPRouteForwardTo struct, and it doesn't seem to support any TLS settings. All the other TLS settings seem to be focused on the "listener side," not starting a connection.

Any suggestion on how can we add this to the filter?

@k8s-ci-robot k8s-ci-robot added the needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. label Apr 28, 2021
@k8s-ci-robot k8s-ci-robot removed the needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. label Jun 18, 2021
@evankanderson
Copy link
Contributor

(Looks like this got rebased a few weeks ago)

@k8s-ci-robot
Copy link
Contributor

@jmprusi: PR needs rebase.

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.

@k8s-ci-robot k8s-ci-robot added the needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. label Aug 19, 2021
@hbagdi
Copy link
Contributor

hbagdi commented Aug 23, 2021

I think it is unlikely that we will merge this. A custom filter would be the path forward here.
@robscott @jpeach @youngnick Thoughts?

@robscott
Copy link
Member

I tend to agree with that. If there's a way we can provide some form of portability for authorization here that would be awesome, but we've got so many things on the go right now I'm not sure how soon we'll be able to tackle that. It's likely easiest to start as a custom filter.

@hbagdi
Copy link
Contributor

hbagdi commented Aug 24, 2021

Let the community experiment for now. If there is convergence, we would love to get this into this API itself.
/close

@k8s-ci-robot
Copy link
Contributor

@hbagdi: Closed this PR.

In response to this:

Let the community experiment for now. If there is convergence, we would love to get this into this API itself.
/close

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.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. kind/design Categorizes issue or PR as related to design. needs-rebase Indicates a PR cannot be merged because it has merge conflicts with HEAD. ok-to-test Indicates a non-member PR verified by an org member that is safe to test. size/M Denotes a PR that changes 30-99 lines, ignoring generated files.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Pluggable access control
10 participants