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

policy: Per route authorization #8901

Merged
merged 6 commits into from
Jul 20, 2022
Merged

policy: Per route authorization #8901

merged 6 commits into from
Jul 20, 2022

Conversation

adleong
Copy link
Member

@adleong adleong commented Jul 16, 2022

Fixes #8890

When building the InboundHttpRoute, we find all authorizations which target that route and copy the associated authentications onto the route and return them in the api. This allows AuthorizationPolicies to target HttpRoutes.

We also add admission, api, and e2e tests.

Signed-off-by: Alex Leong <[email protected]>
@adleong adleong requested a review from a team as a code owner July 16, 2022 00:21
policy-controller/k8s/index/src/authorization_policy.rs Outdated Show resolved Hide resolved
policy-controller/k8s/index/src/index.rs Outdated Show resolved Hide resolved
) -> HashMap<AuthorizationRef, ClientAuthorization> {
let mut authzs = HashMap::default();

for (name, spec) in self.authorization_policies.iter() {
Copy link
Contributor

Choose a reason for hiding this comment

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

style nit, not important: &HashMap implements IntoIterator, so i believe this could just be

Suggested change
for (name, spec) in self.authorization_policies.iter() {
for (name, spec) in self.authorization_policies {

policy-controller/k8s/index/src/index.rs Show resolved Hide resolved
Signed-off-by: Alex Leong <[email protected]>
Copy link
Member

@olix0r olix0r 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 looking pretty good to me! I think we need some deeper testing--I'll try to do some manual testing in the meantime.

@olix0r
Copy link
Member

olix0r commented Jul 19, 2022

Great! Seems to work as expected using a config like https://gist.github.com/olix0r/0d13b32037e91ad802a907077f29b821#file-emojivoto-policy-yml

inbound_http_authz_allow_total{target_addr="10.42.0.214:8080",target_ip="10.42.0.214",target_port="8080",srv_group="policy.linkerd.io",srv_kind="server",srv_name="web-http",route_group="",route_kind="default",route_name="default",authz_group="policy.linkerd.io",authz_kind="authorizationpolicy",authz_name="web-public",tls="true",client_id="default.emojivoto.serviceaccount.identity.linkerd.cluster.local"} 298
inbound_http_authz_allow_total{target_addr="0.0.0.0:4191",target_ip="0.0.0.0",target_port="4191",srv_group="policy.linkerd.io",srv_kind="server",srv_name="linkerd-admin",route_group="gateway.networking.k8s.io",route_kind="HTTPRoute",route_name="linkerd-metrics",authz_group="",authz_kind="default",authz_name="localhost",tls="no_identity",no_tls_reason="no_tls_from_remote"} 5
inbound_http_authz_allow_total{target_addr="0.0.0.0:4191",target_ip="0.0.0.0",target_port="4191",srv_group="policy.linkerd.io",srv_kind="server",srv_name="linkerd-admin",route_group="gateway.networking.k8s.io",route_kind="HTTPRoute",route_name="linkerd-probes",authz_group="policy.linkerd.io",authz_kind="authorizationpolicy",authz_name="linkerd-probes",tls="no_identity",no_tls_reason="no_tls_from_remote"} 31

Signed-off-by: Alex Leong <[email protected]>
Comment on lines 88 to 107
let curl = curl::Runner::init(&client, &ns).await;
let (allowed, denied) = tokio::join!(
curl.run(
"curl-allowed",
"http://nginx/allowed",
LinkerdInject::Enabled
),
curl.run("curl-denied", "http://nginx/denied", LinkerdInject::Enabled),
);
let (allowed_status, denied_status) = tokio::join!(allowed.exit_code(), denied.exit_code());
assert_eq!(
allowed_status, 0,
"curling allowed route must contact nginx"
);
assert_ne!(
denied_status, 0,
"curl which does not match route must not contact nginx"
);
})
.await;
Copy link
Member

Choose a reason for hiding this comment

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

There are probably a few more states worth considering here:

  • allowed by a server-scoped authorization
  • allowed by a server-scoped authorization but not present in routes (should get a 404).

not a blocker

policy-test/src/lib.rs Outdated Show resolved Hide resolved
Signed-off-by: Alex Leong <[email protected]>
"http://nginx/allowed",
LinkerdInject::Enabled
),
curl.run("curl-denied", "http://nginx/denied", LinkerdInject::Enabled),
Copy link
Member

Choose a reason for hiding this comment

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

Sorry, I still think this is a little off: this case is hitting an endpoint on no route. we probably want an additional route object that matches /denied (or an empty route to match all endpoints?). OR we should rename "denied" to something like "no-route"

Signed-off-by: Alex Leong <[email protected]>
@olix0r olix0r enabled auto-merge (squash) July 20, 2022 18:18
@olix0r olix0r changed the title Per route authorization policy: Per route authorization Jul 20, 2022
@olix0r olix0r merged commit fe29318 into main Jul 20, 2022
@olix0r olix0r deleted the alex/per-route-auth branch July 20, 2022 19:56
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

policy: Allow AuthorizationPolicies to target HTTPRoutes
3 participants