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

Extend ClusterPermission to consider requests #31998

Merged
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -5,30 +5,92 @@
*/
package org.elasticsearch.xpack.core.security.authz.permission;

import org.elasticsearch.transport.TransportRequest;
import org.elasticsearch.xpack.core.security.authz.privilege.ClusterPrivilege;

import java.util.Collection;
import java.util.Set;
import java.util.function.Predicate;
import java.util.stream.Collectors;

/**
* A permission that is based on privileges for cluster wide actions
* A permission that is based on privileges for cluster wide actions, with the optional ability to inspect the request object
*/
public final class ClusterPermission {

public static final ClusterPermission NONE = new ClusterPermission(ClusterPrivilege.NONE);

public abstract class ClusterPermission {
private final ClusterPrivilege privilege;
private final Predicate<String> predicate;

ClusterPermission(ClusterPrivilege privilege) {
this.privilege = privilege;
this.predicate = privilege.predicate();
}

public ClusterPrivilege privilege() {
return privilege;
}

public boolean check(String action) {
return predicate.test(action);
public abstract boolean check(String action, TransportRequest request);

/**
* A permission that is based solely on cluster privileges and does not consider request state
*/
public static class SimpleClusterPermission extends ClusterPermission {

public static final SimpleClusterPermission NONE = new SimpleClusterPermission(ClusterPrivilege.NONE);

private final Predicate<String> predicate;

SimpleClusterPermission(ClusterPrivilege privilege) {
super(privilege);
this.predicate = privilege.predicate();
}

@Override
public boolean check(String action, TransportRequest request) {
return predicate.test(action);
}
}

/**
* A permission that makes use of both cluster privileges and request inspection
*/
public static class ConditionalClusterPermission extends ClusterPermission {
private final Predicate<String> actionPredicate;
private final Predicate<TransportRequest> requestPredicate;

public ConditionalClusterPermission(ClusterPrivilege privilege, Predicate<TransportRequest> requestPredicate) {
super(privilege);
this.actionPredicate = privilege.predicate();
this.requestPredicate = requestPredicate;
}

@Override
public boolean check(String action, TransportRequest request) {
return actionPredicate.test(action) && requestPredicate.test(request);
}
}

/**
* A permission that composes a number of other cluster permissions
*/
public static class CompositeClusterPermission extends ClusterPermission {
private final Collection<ClusterPermission> children;

public CompositeClusterPermission(Collection<ClusterPermission> children) {
super(buildPrivilege(children));
this.children = children;
}

private static ClusterPrivilege buildPrivilege(Collection<ClusterPermission> children) {
final Set<String> names = children.stream()
.map(ClusterPermission::privilege)
.map(ClusterPrivilege::name)
.flatMap(Set::stream)
.collect(Collectors.toSet());
return ClusterPrivilege.get(names);
}

@Override
public boolean check(String action, TransportRequest request) {
return children.stream().anyMatch(p -> p.check(action, request));
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ public IndicesAccessControl authorize(String action, Set<String> requestedIndice
public static class Builder {

private final String[] names;
private ClusterPermission cluster = ClusterPermission.NONE;
private ClusterPermission cluster = ClusterPermission.SimpleClusterPermission.NONE;
private RunAsPermission runAs = RunAsPermission.NONE;
private List<IndicesPermission.Group> groups = new ArrayList<>();
private List<Tuple<ApplicationPrivilege, Set<String>>> applicationPrivs = new ArrayList<>();
Expand All @@ -107,7 +107,7 @@ private Builder(String[] names) {
private Builder(RoleDescriptor rd, @Nullable FieldPermissionsCache fieldPermissionsCache) {
this.names = new String[] { rd.getName() };
if (rd.getClusterPrivileges().length == 0) {
cluster = ClusterPermission.NONE;
cluster = ClusterPermission.SimpleClusterPermission.NONE;
} else {
this.cluster(ClusterPrivilege.get(Sets.newHashSet(rd.getClusterPrivileges())));
}
Expand All @@ -125,7 +125,7 @@ private Builder(RoleDescriptor rd, @Nullable FieldPermissionsCache fieldPermissi
}

public Builder cluster(ClusterPrivilege privilege) {
cluster = new ClusterPermission(privilege);
cluster = new ClusterPermission.SimpleClusterPermission(privilege);
return this;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ public class ReservedRolesStore {
new String[] { "all" },
new RoleDescriptor.IndicesPrivileges[] {
RoleDescriptor.IndicesPrivileges.builder().indices("*").privileges("all").build()},
new RoleDescriptor.ApplicationResourcePrivileges[]{
new RoleDescriptor.ApplicationResourcePrivileges[] {
RoleDescriptor.ApplicationResourcePrivileges.builder().application("*").privileges("*").resources("*").build()
},
new String[] { "*" },
Expand Down
Loading