Revert "SENTRY-2012 - Make SentryShellGeneric extendible. Mano Kovacs, reviewed by Colm O hEigeartaigh."
This reverts commit 2314e465496114444d83cec7dced60f482670179. Project: http://git-wip-us.apache.org/repos/asf/sentry/repo Commit: http://git-wip-us.apache.org/repos/asf/sentry/commit/5fc1e977 Tree: http://git-wip-us.apache.org/repos/asf/sentry/tree/5fc1e977 Diff: http://git-wip-us.apache.org/repos/asf/sentry/diff/5fc1e977 Branch: refs/heads/akolb-cli Commit: 5fc1e97790936ff0002fbebc156fccd06b4a9014 Parents: 2314e46 Author: Colm O hEigeartaigh <[email protected]> Authored: Fri Nov 17 13:12:33 2017 +0000 Committer: Colm O hEigeartaigh <[email protected]> Committed: Fri Nov 17 13:12:33 2017 +0000 ---------------------------------------------------------------------- bin/sentryShell | 6 +- .../common/AbstractAuthorizableFactory.java | 72 ------ .../sentry/core/common/AuthorizableFactory.java | 50 ----- .../sentry/core/common/AuthorizableType.java | 21 -- .../core/model/kafka/KafkaAuthorizable.java | 2 +- .../model/kafka/KafkaModelAuthorizables.java | 27 ++- .../core/model/solr/SolrModelAuthorizable.java | 6 +- .../core/model/solr/SolrModelAuthorizables.java | 52 +++-- .../core/model/sqoop/SqoopAuthorizable.java | 2 +- .../model/sqoop/SqoopModelAuthorizables.java | 50 +++-- .../tools/GenericPrivilegeConverter.java | 96 ++++---- .../db/generic/tools/SentryConfigToolSolr.java | 9 +- .../db/generic/tools/SentryShellGeneric.java | 51 +++-- .../db/generic/tools/SentryShellKafka.java | 71 ------ .../db/generic/tools/SentryShellSolr.java | 52 ----- .../db/generic/tools/SentryShellSqoop.java | 52 ----- .../generic/tools/TestSentryConfigToolSolr.java | 9 +- .../db/generic/tools/TestSentryShellKafka.java | 207 +++++++++-------- .../db/generic/tools/TestSentryShellSolr.java | 224 ++++++++++--------- .../db/generic/tools/TestSentryShellSqoop.java | 164 +++++++------- 20 files changed, 473 insertions(+), 750 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/bin/sentryShell ---------------------------------------------------------------------- diff --git a/bin/sentryShell b/bin/sentryShell index d7a53b8..17b1429 100755 --- a/bin/sentryShell +++ b/bin/sentryShell @@ -60,9 +60,9 @@ while [ $# -gt 0 ]; do # Until you run out of parameters . . . if [[ "$1" = "-t" || "$1" = "--type" ]]; then case $2 in "hive") shell=org.apache.sentry.provider.db.tools.SentryShellHive ;; - "kafka") shell=org.apache.sentry.provider.db.generic.tools.SentryShellKafka ;; - "solr") shell=org.apache.sentry.provider.db.generic.tools.SentryShellSolr ;; - "sqoop") shell=org.apache.sentry.provider.db.generic.tools.SentryShellSqoop;; + "kafka") shell=org.apache.sentry.provider.db.generic.tools.SentryShellGeneric ;; + "solr") shell=org.apache.sentry.provider.db.generic.tools.SentryShellGeneric ;; + "sqoop") shell=org.apache.sentry.provider.db.generic.tools.SentryShellGeneric ;; *) echo "Doesn't support the type $2!"; exit 1 ;; esac fi http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AbstractAuthorizableFactory.java ---------------------------------------------------------------------- diff --git a/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AbstractAuthorizableFactory.java b/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AbstractAuthorizableFactory.java deleted file mode 100644 index 14bf2df..0000000 --- a/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AbstractAuthorizableFactory.java +++ /dev/null @@ -1,72 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.sentry.core.common; - -import com.google.common.base.Preconditions; -import com.google.common.collect.Lists; -import org.apache.sentry.core.common.utils.SentryConstants; - -import java.util.List; - -/** - * @param <A> The type of Authorizable the class handles - */ -public abstract class AbstractAuthorizableFactory<A extends Authorizable, T extends AuthorizableType<A>> implements AuthorizableFactory<A, T> { - - @Override - public A create(String s) { - List<String> kvList = Lists.newArrayList(SentryConstants.KV_SPLITTER.trimResults().limit(2).split(s)); - if (kvList.size() != 2) { - throw new IllegalArgumentException("Invalid authorizable string value: " + s + " " + kvList); - } - - String type; - String name; - - type = kvList.get(0); - Preconditions.checkArgument(!type.isEmpty(), "Type cannot be empty"); - name = kvList.get(1); - Preconditions.checkArgument(!name.isEmpty(), "Name cannot be empty"); - try { - return create(type, name); - } catch (IllegalArgumentException e) { - return null; - } - } - - @Override - public A create(String type, String name) { - T typeObject = getType(type); - if (typeObject == null) { - return null; - } else { - return create(typeObject, name); - } - } - - private T getType(String typeName) { - for (T type : getTypes()) { - if (typeName.equalsIgnoreCase(type.name())) { - return type; - } - } - return null; - } - - protected abstract T[] getTypes(); - -} http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AuthorizableFactory.java ---------------------------------------------------------------------- diff --git a/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AuthorizableFactory.java b/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AuthorizableFactory.java deleted file mode 100644 index 9d3b5e0..0000000 --- a/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AuthorizableFactory.java +++ /dev/null @@ -1,50 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.sentry.core.common; - -import javax.annotation.Nullable; - -/** - * Interface for factory class for creating authorizable objects from strings or type-name pairs. - * - * @param <A> Type of the Authorizable the implementation handles - */ -public interface AuthorizableFactory<A extends Authorizable, T extends AuthorizableType<A>> { - /** - * Parses authorizable and returns it. If s is unknown authorizable, it returns null. - * @param s type=name format of authorizable - * @return - */ - @Nullable - A create(String s); - - /** - * Returns authorizable based on type and name - * @param type - * @param name - * @return - */ - A create(String type, String name); - - /** - * Returns authorizable based on type and name - * @param type - * @param name - * @return - */ - A create(T type, String name); -} http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AuthorizableType.java ---------------------------------------------------------------------- diff --git a/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AuthorizableType.java b/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AuthorizableType.java deleted file mode 100644 index 71cc6dd..0000000 --- a/sentry-core/sentry-core-common/src/main/java/org/apache/sentry/core/common/AuthorizableType.java +++ /dev/null @@ -1,21 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.sentry.core.common; - -public interface AuthorizableType<T extends Authorizable> { - String name(); -} http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaAuthorizable.java ---------------------------------------------------------------------- diff --git a/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaAuthorizable.java b/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaAuthorizable.java index 269572c..52ae614 100644 --- a/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaAuthorizable.java +++ b/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaAuthorizable.java @@ -44,7 +44,7 @@ public interface KafkaAuthorizable extends Authorizable { /** * Types of resources that Kafka supports authorization on. */ - enum AuthorizableType implements org.apache.sentry.core.common.AuthorizableType<KafkaAuthorizable>{ + public enum AuthorizableType { CLUSTER, HOST, TOPIC, http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaModelAuthorizables.java ---------------------------------------------------------------------- diff --git a/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaModelAuthorizables.java b/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaModelAuthorizables.java index 57a4e20..45a1148 100644 --- a/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaModelAuthorizables.java +++ b/sentry-core/sentry-core-model-kafka/src/main/java/org/apache/sentry/core/model/kafka/KafkaModelAuthorizables.java @@ -16,19 +16,27 @@ */ package org.apache.sentry.core.model.kafka; -import org.apache.sentry.core.common.AbstractAuthorizableFactory; +import org.apache.sentry.core.common.utils.KeyValue; +import org.apache.sentry.core.model.kafka.KafkaAuthorizable.AuthorizableType; import org.apache.shiro.config.ConfigurationException; -public class KafkaModelAuthorizables extends AbstractAuthorizableFactory<KafkaAuthorizable, KafkaAuthorizable.AuthorizableType> { - private static final KafkaModelAuthorizables instance = new KafkaModelAuthorizables(); - +public class KafkaModelAuthorizables { + public static KafkaAuthorizable from(KeyValue keyValue) throws ConfigurationException { + String prefix = keyValue.getKey().toLowerCase(); + String name = keyValue.getValue(); + for (AuthorizableType type : AuthorizableType.values()) { + if (prefix.equalsIgnoreCase(type.name())) { + return from(type, name); + } + } + return null; + } public static KafkaAuthorizable from(String keyValue) throws ConfigurationException { - return instance.create(keyValue); + return from(new KeyValue(keyValue)); } - @Override - public KafkaAuthorizable create(KafkaAuthorizable.AuthorizableType type, String name) throws ConfigurationException { + public static KafkaAuthorizable from(AuthorizableType type, String name) throws ConfigurationException { switch (type) { case HOST: return new Host(name); @@ -46,9 +54,4 @@ public class KafkaModelAuthorizables extends AbstractAuthorizableFactory<KafkaAu return null; } } - - @Override - protected KafkaAuthorizable.AuthorizableType[] getTypes() { - return KafkaAuthorizable.AuthorizableType.values(); - } } http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizable.java ---------------------------------------------------------------------- diff --git a/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizable.java b/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizable.java index 9eb10c3..56cb4c2 100644 --- a/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizable.java +++ b/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizable.java @@ -22,15 +22,13 @@ import com.google.common.annotations.VisibleForTesting; public abstract class SolrModelAuthorizable implements Authorizable { - public enum AuthorizableType implements org.apache.sentry.core.common.AuthorizableType<SolrModelAuthorizable> { + public enum AuthorizableType { Collection, Field, Admin, Config, Schema - } - - ; + }; private final AuthorizableType type; private final String name; http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizables.java ---------------------------------------------------------------------- diff --git a/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizables.java b/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizables.java index 09255e7..7979b33 100644 --- a/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizables.java +++ b/sentry-core/sentry-core-model-solr/src/main/java/org/apache/sentry/core/model/solr/SolrModelAuthorizables.java @@ -16,39 +16,43 @@ */ package org.apache.sentry.core.model.solr; -import org.apache.sentry.core.common.AbstractAuthorizableFactory; +import org.apache.sentry.core.common.utils.KeyValue; import org.apache.sentry.core.model.solr.SolrModelAuthorizable.AuthorizableType; -public class SolrModelAuthorizables extends AbstractAuthorizableFactory<SolrModelAuthorizable, AuthorizableType> { - private static final SolrModelAuthorizables instance = new SolrModelAuthorizables(); +public class SolrModelAuthorizables { - public static SolrModelAuthorizable from(String s) { - return instance.create(s); + private SolrModelAuthorizables() { + // Make constructor private to avoid instantiation } - public SolrModelAuthorizable create(SolrModelAuthorizable.AuthorizableType type, String name) { + public static SolrModelAuthorizable from(KeyValue keyValue) { + String prefix = keyValue.getKey().toLowerCase(); + String name = keyValue.getValue().toLowerCase(); SolrModelAuthorizable result = null; - switch (type) { - case Collection: - result = new Collection(name); - break; - case Admin: - result = new AdminOperation(name); - break; - case Config: - result = new Config(name); - break; - case Schema: - result = new Schema(name); - break; - default: - break; + for(AuthorizableType type : AuthorizableType.values()) { + if(prefix.equalsIgnoreCase(type.name())) { + switch (type) { + case Collection: + result = new Collection(name); + break; + case Admin: + result = new AdminOperation(name); + break; + case Config: + result = new Config(name); + break; + case Schema: + result = new Schema(name); + break; + default: + break; + } + } } return result; } - @Override - protected SolrModelAuthorizable.AuthorizableType[] getTypes() { - return SolrModelAuthorizable.AuthorizableType.values(); + public static SolrModelAuthorizable from(String s) { + return from(new KeyValue(s)); } } http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopAuthorizable.java ---------------------------------------------------------------------- diff --git a/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopAuthorizable.java b/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopAuthorizable.java index f060d27..934875e 100644 --- a/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopAuthorizable.java +++ b/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopAuthorizable.java @@ -24,7 +24,7 @@ import org.apache.sentry.core.common.Authorizable; */ public interface SqoopAuthorizable extends Authorizable { String ALL = "*"; - enum AuthorizableType implements org.apache.sentry.core.common.AuthorizableType<SqoopAuthorizable> { + public enum AuthorizableType { SERVER, CONNECTOR, LINK, http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopModelAuthorizables.java ---------------------------------------------------------------------- diff --git a/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopModelAuthorizables.java b/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopModelAuthorizables.java index 0227fb8..3bb9a19 100644 --- a/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopModelAuthorizables.java +++ b/sentry-core/sentry-core-model-sqoop/src/main/java/org/apache/sentry/core/model/sqoop/SqoopModelAuthorizables.java @@ -16,34 +16,42 @@ */ package org.apache.sentry.core.model.sqoop; -import org.apache.sentry.core.common.AbstractAuthorizableFactory; +import org.apache.sentry.core.model.sqoop.SqoopAuthorizable.AuthorizableType; +import org.apache.sentry.core.common.utils.KeyValue; -public class SqoopModelAuthorizables extends AbstractAuthorizableFactory<SqoopAuthorizable, SqoopAuthorizable.AuthorizableType> { +public class SqoopModelAuthorizables { - private static final SqoopModelAuthorizables instance = new SqoopModelAuthorizables(); + private SqoopModelAuthorizables() { + // Make constructor private to avoid instantiation + } - public static SqoopAuthorizable from(String keyValue) { - return instance.create(keyValue); + public static SqoopAuthorizable from(KeyValue keyValue) { + String prefix = keyValue.getKey().toLowerCase(); + String name = keyValue.getValue().toLowerCase(); + for (AuthorizableType type : AuthorizableType.values()) { + if(prefix.equalsIgnoreCase(type.name())) { + return from(type, name); + } + } + return null; } + public static SqoopAuthorizable from(String keyValue) { + return from(new KeyValue(keyValue)); + } - public SqoopAuthorizable create(SqoopAuthorizable.AuthorizableType type, String name) { + public static SqoopAuthorizable from(AuthorizableType type, String name) { switch(type) { - case SERVER: - return new Server(name); - case JOB: - return new Job(name); - case CONNECTOR: - return new Connector(name); - case LINK: - return new Link(name); - default: - return null; + case SERVER: + return new Server(name); + case JOB: + return new Job(name); + case CONNECTOR: + return new Connector(name); + case LINK: + return new Link(name); + default: + return null; } } - - @Override - protected SqoopAuthorizable.AuthorizableType[] getTypes() { - return SqoopAuthorizable.AuthorizableType.values(); - } } http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/GenericPrivilegeConverter.java ---------------------------------------------------------------------- diff --git a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/GenericPrivilegeConverter.java b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/GenericPrivilegeConverter.java index e6fa763..c65b66d 100644 --- a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/GenericPrivilegeConverter.java +++ b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/GenericPrivilegeConverter.java @@ -18,25 +18,37 @@ package org.apache.sentry.provider.db.generic.tools; -import com.google.common.base.Function; +import static org.apache.sentry.core.common.utils.SentryConstants.AUTHORIZABLE_SEPARATOR; +import static org.apache.sentry.core.common.utils.SentryConstants.KV_SEPARATOR; +import static org.apache.sentry.core.common.utils.SentryConstants.RESOURCE_WILDCARD_VALUE; + import com.google.common.collect.Lists; + +import java.util.Iterator; +import java.util.LinkedList; +import java.util.List; + import org.apache.sentry.core.common.Authorizable; -import org.apache.sentry.core.common.AuthorizableFactory; import org.apache.sentry.core.common.exception.SentryUserException; import org.apache.sentry.core.common.utils.KeyValue; import org.apache.sentry.core.common.utils.PolicyFileConstants; import org.apache.sentry.core.common.utils.SentryConstants; import org.apache.sentry.core.common.validator.PrivilegeValidator; import org.apache.sentry.core.common.validator.PrivilegeValidatorContext; +import org.apache.sentry.core.model.kafka.KafkaAuthorizable; +import org.apache.sentry.core.model.kafka.KafkaModelAuthorizables; +import org.apache.sentry.core.model.kafka.KafkaPrivilegeModel; +import org.apache.sentry.core.model.solr.SolrModelAuthorizables; +import org.apache.sentry.core.model.solr.SolrPrivilegeModel; +import org.apache.sentry.core.model.sqoop.SqoopModelAuthorizables; +import org.apache.sentry.core.model.sqoop.SqoopPrivilegeModel; +import org.apache.sentry.provider.common.AuthorizationComponent; import org.apache.sentry.provider.db.generic.service.thrift.TAuthorizable; import org.apache.sentry.provider.db.generic.service.thrift.TSentryGrantOption; import org.apache.sentry.provider.db.generic.service.thrift.TSentryPrivilege; import org.apache.sentry.provider.db.generic.tools.command.TSentryPrivilegeConverter; import org.apache.shiro.config.ConfigurationException; -import java.util.ArrayList; -import java.util.List; - /** * A TSentryPrivilegeConverter implementation for "Generic" privileges, covering Apache Kafka, Apache Solr and Apache Sqoop. * It converts privilege Strings to TSentryPrivilege Objects, and vice versa, for Generic clients. @@ -49,24 +61,16 @@ public class GenericPrivilegeConverter implements TSentryPrivilegeConverter { private String service; private boolean validate; - private List<PrivilegeValidator> privilegeValidators; - - private AuthorizableFactory authorizableFactory; - - /** - * Optional function to parse or convert privilege string. - */ - private Function<String, String> privilegeStrParser; + public GenericPrivilegeConverter(String component, String service) { + this(component, service, true); + } - public GenericPrivilegeConverter(String component, String service, List<PrivilegeValidator> privilegeValidators, AuthorizableFactory authorizableFactory, boolean validate) { + public GenericPrivilegeConverter(String component, String service, boolean validate) { this.component = component; this.service = service; - this.privilegeValidators = privilegeValidators; - this.authorizableFactory = authorizableFactory; this.validate = validate; } - public TSentryPrivilege fromString(String privilegeStr) throws SentryUserException { privilegeStr = parsePrivilegeString(privilegeStr); if (validate) { @@ -74,13 +78,13 @@ public class GenericPrivilegeConverter implements TSentryPrivilegeConverter { } TSentryPrivilege tSentryPrivilege = new TSentryPrivilege(); - List<TAuthorizable> authorizables = new ArrayList<>(); + List<TAuthorizable> authorizables = new LinkedList<TAuthorizable>(); for (String authorizable : SentryConstants.AUTHORIZABLE_SPLITTER.split(privilegeStr)) { KeyValue keyValue = new KeyValue(authorizable); String key = keyValue.getKey(); String value = keyValue.getValue(); - Authorizable authz = authorizableFactory.create(key, value); + Authorizable authz = getAuthorizable(keyValue); if (authz != null) { authorizables.add(new TAuthorizable(authz.getTypeName(), authz.getName())); } else if (PolicyFileConstants.PRIVILEGE_ACTION_NAME.equalsIgnoreCase(key)) { @@ -107,30 +111,39 @@ public class GenericPrivilegeConverter implements TSentryPrivilegeConverter { String grantOption = (tSentryPrivilege.getGrantOption() == TSentryGrantOption.TRUE ? "true" : "false"); - for (TAuthorizable tAuthorizable : authorizables) { - privileges.add(SentryConstants.KV_JOINER.join( - tAuthorizable.getType(), tAuthorizable.getName())); + Iterator<TAuthorizable> it = authorizables.iterator(); + if (it != null) { + while (it.hasNext()) { + TAuthorizable tAuthorizable = it.next(); + privileges.add(SentryConstants.KV_JOINER.join( + tAuthorizable.getType(), tAuthorizable.getName())); + } } if (!authorizables.isEmpty()) { privileges.add(SentryConstants.KV_JOINER.join( - PolicyFileConstants.PRIVILEGE_ACTION_NAME, action)); + PolicyFileConstants.PRIVILEGE_ACTION_NAME, action)); } // only append the grant option to privilege string if it's true if ("true".equals(grantOption)) { privileges.add(SentryConstants.KV_JOINER.join( - PolicyFileConstants.PRIVILEGE_GRANT_OPTION_NAME, grantOption)); + PolicyFileConstants.PRIVILEGE_GRANT_OPTION_NAME, grantOption)); } } return SentryConstants.AUTHORIZABLE_JOINER.join(privileges); } private String parsePrivilegeString(String privilegeStr) { - if (privilegeStrParser == null) { - return privilegeStr; + if (AuthorizationComponent.KAFKA.equals(component)) { + final String hostPrefix = KafkaAuthorizable.AuthorizableType.HOST.name() + KV_SEPARATOR; + final String hostPrefixLowerCase = hostPrefix.toLowerCase(); + if (!privilegeStr.toLowerCase().startsWith(hostPrefixLowerCase)) { + return hostPrefix + RESOURCE_WILDCARD_VALUE + AUTHORIZABLE_SEPARATOR + privilegeStr; + } } - return privilegeStrParser.apply(privilegeStr); + + return privilegeStr; } private void validatePrivilegeHierarchy(String privilegeStr) throws SentryUserException { @@ -145,21 +158,28 @@ public class GenericPrivilegeConverter implements TSentryPrivilegeConverter { } } - private List<PrivilegeValidator> getPrivilegeValidators() { - return privilegeValidators; - } - + private List<PrivilegeValidator> getPrivilegeValidators() throws SentryUserException { + if (AuthorizationComponent.KAFKA.equals(component)) { + return KafkaPrivilegeModel.getInstance().getPrivilegeValidators(); + } else if ("SOLR".equals(component)) { + return SolrPrivilegeModel.getInstance().getPrivilegeValidators(); + } else if (AuthorizationComponent.SQOOP.equals(component)) { + return SqoopPrivilegeModel.getInstance().getPrivilegeValidators(service); + } - public void setPrivilegeValidators(List<PrivilegeValidator> privilegeValidators) { - this.privilegeValidators = privilegeValidators; + throw new SentryUserException("Invalid component specified for GenericPrivilegeCoverter: " + component); } - public void setAuthorizableFactory(AuthorizableFactory authorizableFactory) { - this.authorizableFactory = authorizableFactory; - } + private Authorizable getAuthorizable(KeyValue keyValue) throws SentryUserException { + if (AuthorizationComponent.KAFKA.equals(component)) { + return KafkaModelAuthorizables.from(keyValue); + } else if ("SOLR".equals(component)) { + return SolrModelAuthorizables.from(keyValue); + } else if (AuthorizationComponent.SQOOP.equals(component)) { + return SqoopModelAuthorizables.from(keyValue); + } - public void setPrivilegeStrParser(Function<String, String> privilegeStrParser) { - this.privilegeStrParser = privilegeStrParser; + throw new SentryUserException("Invalid component specified for GenericPrivilegeCoverter: " + component); } } http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryConfigToolSolr.java ---------------------------------------------------------------------- diff --git a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryConfigToolSolr.java b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryConfigToolSolr.java index 10b875d..5649f43 100644 --- a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryConfigToolSolr.java +++ b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryConfigToolSolr.java @@ -18,7 +18,6 @@ package org.apache.sentry.provider.db.generic.tools; -import com.google.common.collect.ImmutableList; import com.google.common.collect.Lists; import com.google.common.collect.Sets; import com.google.common.collect.Table; @@ -30,8 +29,6 @@ import org.apache.sentry.core.common.Action; import org.apache.sentry.core.common.exception.SentryConfigurationException; import org.apache.sentry.core.common.utils.KeyValue; import org.apache.sentry.core.common.utils.SentryConstants; -import org.apache.sentry.core.common.validator.PrivilegeValidator; -import org.apache.sentry.core.model.solr.SolrModelAuthorizables; import org.apache.sentry.core.model.solr.SolrPrivilegeModel; import org.apache.sentry.provider.common.ProviderBackend; import org.apache.sentry.provider.common.ProviderBackendContext; @@ -95,8 +92,7 @@ public class SentryConfigToolSolr extends SentryConfigToolCommon { SimpleFileProviderBackend policyFileBackend = new SimpleFileProviderBackend(conf, policyFile); ProviderBackendContext context = new ProviderBackendContext(); - ImmutableList<PrivilegeValidator> privilegeValidators = SolrPrivilegeModel.getInstance().getPrivilegeValidators(); - context.setValidators(privilegeValidators); + context.setValidators(SolrPrivilegeModel.getInstance().getPrivilegeValidators()); policyFileBackend.initialize(context); if (validate) { validatePolicy(policyFileBackend); @@ -110,8 +106,7 @@ public class SentryConfigToolSolr extends SentryConfigToolCommon { Set<String> roles = Sets.newHashSet(); Table<String, String, Set<String>> groupRolePrivilegeTable = policyFileBackend.getGroupRolePrivilegeTable(); - SolrModelAuthorizables authorizableFactory = new SolrModelAuthorizables(); - GenericPrivilegeConverter converter = new GenericPrivilegeConverter(component, service, privilegeValidators, authorizableFactory, false); + GenericPrivilegeConverter converter = new GenericPrivilegeConverter(component, service, false); for (String groupName : groupRolePrivilegeTable.rowKeySet()) { for (String roleName : groupRolePrivilegeTable.columnKeySet()) { http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellGeneric.java ---------------------------------------------------------------------- diff --git a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellGeneric.java b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellGeneric.java index 8dc04f3..1623f38 100644 --- a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellGeneric.java +++ b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellGeneric.java @@ -25,11 +25,12 @@ import org.apache.commons.lang.StringUtils; import org.apache.hadoop.conf.Configuration; import org.apache.hadoop.fs.Path; import org.apache.hadoop.security.UserGroupInformation; +import org.apache.sentry.provider.common.AuthorizationComponent; import org.apache.sentry.provider.db.generic.service.thrift.SentryGenericServiceClient; import org.apache.sentry.provider.db.generic.service.thrift.SentryGenericServiceClientFactory; import org.apache.sentry.provider.db.generic.tools.command.GenericShellCommand; +import org.apache.sentry.provider.db.generic.tools.command.TSentryPrivilegeConverter; import org.apache.sentry.provider.db.tools.SentryShellCommon; -import org.apache.sentry.service.thrift.ServiceConstants; import org.apache.sentry.provider.db.tools.ShellCommand; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -42,26 +43,25 @@ import com.google.common.collect.Sets; * create role, drop role, add group to role, grant privilege to role, * revoke privilege from role, list roles, list privilege for role. */ -abstract public class SentryShellGeneric extends SentryShellCommon { +public class SentryShellGeneric extends SentryShellCommon { private static final Logger LOGGER = LoggerFactory.getLogger(SentryShellGeneric.class); - - abstract protected GenericPrivilegeConverter getPrivilegeConverter(String component, String service); - - abstract protected String getComponent(Configuration conf); + private static final String KAFKA_SERVICE_NAME = "sentry.service.client.kafka.service.name"; + private static final String SOLR_SERVICE_NAME = "sentry.service.client.solr.service.name"; + private static final String SQOOP_SERVICE_NAME = "sentry.service.client.sqoop.service.name"; @Override public void run() throws Exception { + String component = getComponent(); Configuration conf = getSentryConf(); - String component = getComponent(conf); - String service = getServiceName(conf); - + String service = getService(conf); try (SentryGenericServiceClient client = - SentryGenericServiceClientFactory.create(conf)) { + SentryGenericServiceClientFactory.create(conf)) { UserGroupInformation ugi = UserGroupInformation.getLoginUser(); String requestorName = ugi.getShortUserName(); - ShellCommand command = new GenericShellCommand(client, component, service, getPrivilegeConverter(component, service)); + TSentryPrivilegeConverter converter = new GenericPrivilegeConverter(component, service); + ShellCommand command = new GenericShellCommand(client, component, service, converter); // check the requestor name if (StringUtils.isEmpty(requestorName)) { @@ -102,12 +102,28 @@ abstract public class SentryShellGeneric extends SentryShellCommon { } } - protected String getServiceName(Configuration conf) { - return getServiceNameGeneric(conf); + private String getComponent() throws Exception { + if (type == TYPE.kafka) { + return AuthorizationComponent.KAFKA; + } else if (type == TYPE.solr) { + return "SOLR"; + } else if (type == TYPE.sqoop) { + return AuthorizationComponent.SQOOP; + } + + throw new Exception("Invalid type specified for SentryShellGeneric: " + type); } - protected String getServiceNameGeneric(Configuration conf) { - return conf.get(ServiceConstants.ClientConfig.SERVICE_NAME); + private String getService(Configuration conf) throws Exception { + if (type == TYPE.kafka) { + return conf.get(KAFKA_SERVICE_NAME, AuthorizationComponent.KAFKA); + } else if (type == TYPE.solr) { + return conf.get(SOLR_SERVICE_NAME, "service1"); + } else if (type == TYPE.sqoop) { + return conf.get(SQOOP_SERVICE_NAME, "sqoopServer1"); + } + + throw new Exception("Invalid type specified for SentryShellGeneric: " + type); } private Configuration getSentryConf() { @@ -116,9 +132,10 @@ abstract public class SentryShellGeneric extends SentryShellCommon { return conf; } - protected void doMain(String[] args) throws Exception { + public static void main(String[] args) throws Exception { + SentryShellGeneric sentryShell = new SentryShellGeneric(); try { - executeShell(args); + sentryShell.executeShell(args); } catch (Exception e) { LOGGER.error(e.getMessage(), e); Throwable current = e; http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellKafka.java ---------------------------------------------------------------------- diff --git a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellKafka.java b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellKafka.java deleted file mode 100644 index 225c2e3..0000000 --- a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellKafka.java +++ /dev/null @@ -1,71 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.sentry.provider.db.generic.tools; - -import com.google.common.base.Function; -import org.apache.hadoop.conf.Configuration; -import org.apache.sentry.core.model.kafka.KafkaAuthorizable; -import org.apache.sentry.core.model.kafka.KafkaModelAuthorizables; -import org.apache.sentry.core.model.kafka.KafkaPrivilegeModel; -import org.apache.sentry.provider.common.AuthorizationComponent; - -import javax.annotation.Nullable; - -import static org.apache.sentry.core.common.utils.SentryConstants.*; - -public class SentryShellKafka extends SentryShellGeneric { - private static final String KAFKA_SERVICE_NAME = "sentry.service.client.kafka.service.name"; - - @Override - protected GenericPrivilegeConverter getPrivilegeConverter(String component, String service) { - GenericPrivilegeConverter privilegeConverter = new GenericPrivilegeConverter( - component, - service, - KafkaPrivilegeModel.getInstance().getPrivilegeValidators(), - new KafkaModelAuthorizables(), - true - ); - privilegeConverter.setPrivilegeStrParser(new Function<String, String>() { - @Nullable - @Override - public String apply(@Nullable String privilegeStr) { - final String hostPrefix = KafkaAuthorizable.AuthorizableType.HOST.name() + KV_SEPARATOR; - final String hostPrefixLowerCase = hostPrefix.toLowerCase(); - if (!privilegeStr.toLowerCase().startsWith(hostPrefixLowerCase)) { - return hostPrefix + RESOURCE_WILDCARD_VALUE + AUTHORIZABLE_SEPARATOR + privilegeStr; - } - return privilegeStr; - } - }); - return privilegeConverter; - } - - @Override - protected String getComponent(Configuration conf) { - return AuthorizationComponent.KAFKA; - } - - @Override - protected String getServiceName(Configuration conf) { - return conf.get(KAFKA_SERVICE_NAME, AuthorizationComponent.KAFKA); - } - - public static void main(String[] args) throws Exception { - new SentryShellKafka().doMain(args); - } -} http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellSolr.java ---------------------------------------------------------------------- diff --git a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellSolr.java b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellSolr.java deleted file mode 100644 index de37e42..0000000 --- a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellSolr.java +++ /dev/null @@ -1,52 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.sentry.provider.db.generic.tools; - -import org.apache.hadoop.conf.Configuration; -import org.apache.sentry.core.model.solr.SolrModelAuthorizables; -import org.apache.sentry.core.model.solr.SolrPrivilegeModel; -import org.apache.sentry.provider.common.AuthorizationComponent; - -public class SentryShellSolr extends SentryShellGeneric { - private static final String SOLR_SERVICE_NAME = "sentry.service.client.solr.service.name"; - - @Override - protected GenericPrivilegeConverter getPrivilegeConverter(String component, String service) { - return new GenericPrivilegeConverter( - component, - service, - SolrPrivilegeModel.getInstance().getPrivilegeValidators(), - new SolrModelAuthorizables(), - true - ); - } - - @Override - protected String getComponent(Configuration conf) { - return AuthorizationComponent.Search; - } - - @Override - protected String getServiceName(Configuration conf) { - return conf.get(SOLR_SERVICE_NAME, "service1"); - } - - public static void main(String[] args) throws Exception { - new SentryShellSolr().doMain(args); - } -} http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellSqoop.java ---------------------------------------------------------------------- diff --git a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellSqoop.java b/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellSqoop.java deleted file mode 100644 index 6315bb5..0000000 --- a/sentry-provider/sentry-provider-db/src/main/java/org/apache/sentry/provider/db/generic/tools/SentryShellSqoop.java +++ /dev/null @@ -1,52 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.sentry.provider.db.generic.tools; - -import org.apache.hadoop.conf.Configuration; -import org.apache.sentry.core.model.sqoop.SqoopModelAuthorizables; -import org.apache.sentry.core.model.sqoop.SqoopPrivilegeModel; -import org.apache.sentry.provider.common.AuthorizationComponent; - -public class SentryShellSqoop extends SentryShellGeneric { - private static final String SQOOP_SERVICE_NAME = "sentry.service.client.sqoop.service.name"; - - @Override - protected GenericPrivilegeConverter getPrivilegeConverter(String component, String service) { - return new GenericPrivilegeConverter( - component, - service, - SqoopPrivilegeModel.getInstance().getPrivilegeValidators(service), - new SqoopModelAuthorizables(), - true - ); - } - - @Override - protected String getComponent(Configuration conf) { - return AuthorizationComponent.SQOOP; - } - - @Override - protected String getServiceName(Configuration conf) { - return conf.get(SQOOP_SERVICE_NAME, "sqoopServer1"); - } - - public static void main(String[] args) throws Exception { - new SentryShellSqoop().doMain(args); - } -} http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryConfigToolSolr.java ---------------------------------------------------------------------- diff --git a/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryConfigToolSolr.java b/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryConfigToolSolr.java index 4a94776..9e6ff42 100644 --- a/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryConfigToolSolr.java +++ b/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryConfigToolSolr.java @@ -33,8 +33,6 @@ import java.util.Map; import java.util.Set; import org.apache.commons.io.FileUtils; -import org.apache.sentry.core.model.solr.SolrModelAuthorizables; -import org.apache.sentry.core.model.solr.SolrPrivilegeModel; import org.apache.sentry.provider.db.generic.service.thrift.SentryGenericServiceIntegrationBase; import org.apache.sentry.provider.db.generic.service.thrift.TSentryRole; import org.apache.sentry.provider.db.generic.service.thrift.TSentryPrivilege; @@ -135,12 +133,7 @@ public class TestSentryConfigToolSolr extends SentryGenericServiceIntegrationBas } // check privileges - GenericPrivilegeConverter convert = new GenericPrivilegeConverter( - SOLR, - service, - SolrPrivilegeModel.getInstance().getPrivilegeValidators(), - new SolrModelAuthorizables(), - true); + GenericPrivilegeConverter convert = new GenericPrivilegeConverter(SOLR, service); for (String role : roles) { Set<TSentryPrivilege> privileges = client.listAllPrivilegesByRoleName( requestorName, role, SOLR, service); http://git-wip-us.apache.org/repos/asf/sentry/blob/5fc1e977/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryShellKafka.java ---------------------------------------------------------------------- diff --git a/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryShellKafka.java b/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryShellKafka.java index fc1d1ac..a9234fa 100644 --- a/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryShellKafka.java +++ b/sentry-provider/sentry-provider-db/src/test/java/org/apache/sentry/provider/db/generic/tools/TestSentryShellKafka.java @@ -79,32 +79,32 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { @Override public void runTestAsSubject() throws Exception { // test: create role with -cr - String[] args = { "-cr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + String[] args = { "-cr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // test: create role with --create_role args = new String[] { "--create_role", "-r", TEST_ROLE_NAME_2, "-conf", - confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // validate the result, list roles with -lr - args = new String[] { "-lr", "-conf", confPath.getAbsolutePath() }; - SentryShellKafka sentryShell = new SentryShellKafka(); + args = new String[] { "-lr", "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric sentryShell = new SentryShellGeneric(); Set<String> roleNames = getShellResultWithOSRedirect(sentryShell, args, true); validateRoleNames(roleNames, TEST_ROLE_NAME_1, TEST_ROLE_NAME_2); // validate the result, list roles with --list_role - args = new String[] { "--list_role", "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "--list_role", "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); roleNames = getShellResultWithOSRedirect(sentryShell, args, true); validateRoleNames(roleNames, TEST_ROLE_NAME_1, TEST_ROLE_NAME_2); // test: drop role with -dr - args = new String[] { "-dr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + args = new String[] { "-dr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // test: drop role with --drop_role args = new String[] { "--drop_role", "-r", TEST_ROLE_NAME_2, "-conf", - confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // validate the result Set<TSentryRole> roles = client.listAllRoles(requestorName, KAFKA); @@ -128,41 +128,41 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { client.createRole(requestorName, TEST_ROLE_NAME_2, KAFKA); // test: add role to group with -arg String[] args = { "-arg", "-r", TEST_ROLE_NAME_1, "-g", TEST_GROUP_1, "-conf", - confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // test: add role to multiple groups args = new String[] { "-arg", "-r", TEST_ROLE_NAME_1, "-g", TEST_GROUP_2 + "," + TEST_GROUP_3, - "-conf", - confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + "-conf", + confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // test: add role to group with --add_role_group args = new String[] { "--add_role_group", "-r", TEST_ROLE_NAME_2, "-g", TEST_GROUP_1, - "-conf", - confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + "-conf", + confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // validate the result list roles with -lr and -g - args = new String[] { "-lr", "-g", TEST_GROUP_1, "-conf", confPath.getAbsolutePath() }; - SentryShellKafka sentryShell = new SentryShellKafka(); + args = new String[] { "-lr", "-g", TEST_GROUP_1, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric sentryShell = new SentryShellGeneric(); Set<String> roleNames = getShellResultWithOSRedirect(sentryShell, args, true); validateRoleNames(roleNames, TEST_ROLE_NAME_1, TEST_ROLE_NAME_2); // list roles with --list_role and -g args = new String[] { "--list_role", "-g", TEST_GROUP_2, "-conf", - confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); roleNames = getShellResultWithOSRedirect(sentryShell, args, true); validateRoleNames(roleNames, TEST_ROLE_NAME_1); args = new String[] { "--list_role", "-g", TEST_GROUP_3, "-conf", - confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); roleNames = getShellResultWithOSRedirect(sentryShell, args, true); validateRoleNames(roleNames, TEST_ROLE_NAME_1); // List the groups and roles via listGroups - args = new String[] { "--list_group", "-conf", confPath.getAbsolutePath()}; - sentryShell = new SentryShellKafka(); + args = new String[] { "--list_group", "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); Set<String> groups = getShellResultWithOSRedirect(sentryShell, args, true); assertEquals(3, groups.size()); assertTrue(groups.contains("testGroup3 = testrole1")); @@ -171,17 +171,17 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { // test: delete role from group with -drg args = new String[] { "-drg", "-r", TEST_ROLE_NAME_1, "-g", TEST_GROUP_1, "-conf", - confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // test: delete role to multiple groups args = new String[] { "-drg", "-r", TEST_ROLE_NAME_1, "-g", TEST_GROUP_2 + "," + TEST_GROUP_3, - "-conf", - confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + "-conf", + confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // test: delete role from group with --delete_role_group args = new String[] { "--delete_role_group", "-r", TEST_ROLE_NAME_2, "-g", TEST_GROUP_1, - "-conf", confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); // validate the result Set<TSentryRole> roles = client.listRolesByGroupName(requestorName, TEST_GROUP_1, KAFKA); @@ -207,17 +207,17 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { client.createRole(requestorName, TEST_ROLE_NAME_1, KAFKA); // add role to a group (lower case) String[] args = {"-arg", "-r", TEST_ROLE_NAME_1, "-g", "group1", "-conf", - confPath.getAbsolutePath()}; - SentryShellKafka.main(args); + confPath.getAbsolutePath(), "-t", "kafka"}; + SentryShellGeneric.main(args); // validate the roles when group name is same case as above - args = new String[]{"-lr", "-g", "group1", "-conf", confPath.getAbsolutePath()}; - SentryShellKafka sentryShell = new SentryShellKafka(); + args = new String[]{"-lr", "-g", "group1", "-conf", confPath.getAbsolutePath(), "-t", "kafka"}; + SentryShellGeneric sentryShell = new SentryShellGeneric(); Set<String> roleNames = getShellResultWithOSRedirect(sentryShell, args, true); validateRoleNames(roleNames, TEST_ROLE_NAME_1); // roles should be empty when group name is different case than above - args = new String[]{"-lr", "-g", "GROUP1", "-conf", confPath.getAbsolutePath()}; + args = new String[]{"-lr", "-g", "GROUP1", "-conf", confPath.getAbsolutePath(), "-t", "kafka"}; roleNames = getShellResultWithOSRedirect(sentryShell, args, true); validateRoleNames(roleNames); } @@ -245,23 +245,23 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { client.createRole(requestorName, TEST_ROLE_NAME_2, KAFKA); String [] privs = { - "HOST=*->CLUSTER=kafka-cluster->action=read", - "HOST=h1->TOPIC=t1->action=write", - "HOST=*->CONSUMERGROUP=cg1->action=read", - "CLUSTER=kafka-cluster->action=write", - "CONSUMERGROUP=cg2->action=write" + "HOST=*->CLUSTER=kafka-cluster->action=read", + "HOST=h1->TOPIC=t1->action=write", + "HOST=*->CONSUMERGROUP=cg1->action=read", + "CLUSTER=kafka-cluster->action=write", + "CONSUMERGROUP=cg2->action=write" }; for (int i = 0; i < privs.length; ++i) { // test: grant privilege to role String [] args = new String [] { grant(shortOption), "-r", TEST_ROLE_NAME_1, "-p", - privs[ i ], - "-conf", confPath.getAbsolutePath()}; - SentryShellKafka.main(args); + privs[ i ], + "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); } // test the list privilege - String [] args = new String[] { list(shortOption), "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath()}; - SentryShellKafka sentryShell = new SentryShellKafka(); + String [] args = new String[] { list(shortOption), "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric sentryShell = new SentryShellGeneric(); Set<String> privilegeStrs = getShellResultWithOSRedirect(sentryShell, args, true); assertEquals("Incorrect number of privileges", privs.length, privilegeStrs.size()); @@ -272,8 +272,8 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { for (int i = 0; i < privs.length; ++i) { args = new String[] { revoke(shortOption), "-r", TEST_ROLE_NAME_1, "-p", privs[ i ], "-conf", - confPath.getAbsolutePath() }; - SentryShellKafka.main(args); + confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric.main(args); Set<TSentryPrivilege> privileges = client.listAllPrivilegesByRoleName(requestorName, TEST_ROLE_NAME_1, KAFKA, service); assertEquals("Incorrect number of privileges. Received privileges: " + Arrays.toString(privileges.toArray()), privs.length - (i + 1), privileges.size()); @@ -305,8 +305,8 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { public void runTestAsSubject() throws Exception { client.createRole(requestorName, TEST_ROLE_NAME_1, KAFKA); // test: create duplicate role with -cr - String[] args = { "-cr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath() }; - SentryShellKafka sentryShell = new SentryShellKafka(); + String[] args = { "-cr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + SentryShellGeneric sentryShell = new SentryShellGeneric(); try { sentryShell.executeShell(args); fail("Exception should be thrown for creating duplicate role"); @@ -317,8 +317,8 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { } // test: drop non-exist role with -dr - args = new String[] { "-dr", "-r", TEST_ROLE_NAME_2, "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-dr", "-r", TEST_ROLE_NAME_2, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); try { sentryShell.executeShell(args); fail("Exception should be thrown for dropping non-exist role"); @@ -330,8 +330,8 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { // test: add non-exist role to group with -arg args = new String[] { "-arg", "-r", TEST_ROLE_NAME_2, "-g", "testGroup1", "-conf", - confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); try { sentryShell.executeShell(args); fail("Exception should be thrown for granting non-exist role to group"); @@ -343,8 +343,8 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { // test: drop group from non-exist role with -drg args = new String[] { "-drg", "-r", TEST_ROLE_NAME_2, "-g", "testGroup1", "-conf", - confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); try { sentryShell.executeShell(args); fail("Exception should be thrown for drop group from non-exist role"); @@ -356,8 +356,8 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { // test: grant privilege to role with the error privilege format args = new String[] { "-gpr", "-r", TEST_ROLE_NAME_1, "-p", "serverserver1->action=all", - "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); try { sentryShell.executeShell(args); fail("Exception should be thrown for the error privilege format, invalid key value."); @@ -369,17 +369,16 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { // test: grant privilege to role with the error privilege hierarchy args = new String[] { "-gpr", "-r", TEST_ROLE_NAME_1, "-p", - "consumergroup=cg1->host=h1->action=create", "-conf", - confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + "consumergroup=cg1->host=h1->action=create", "-conf", + confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); try { sentryShell.executeShell(args); fail("Exception should be thrown for the error privilege format, invalid key value."); } catch (IllegalArgumentException e) { // expected exception } catch (Exception e) { - throw e; -// fail ("Unexpected exception received. " + e); + fail ("Unexpected exception received. " + e); } // clear the test data @@ -396,86 +395,86 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { String strOptionConf = "conf"; client.createRole(requestorName, TEST_ROLE_NAME_1, KAFKA); // test: the conf is required argument - String[] args = { "-cr", "-r", TEST_ROLE_NAME_1 }; - SentryShellKafka sentryShell = new SentryShellKafka(); + String[] args = { "-cr", "-r", TEST_ROLE_NAME_1, "-t", "kafka" }; + SentryShellGeneric sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + strOptionConf); // test: -r is required when create role - args = new String[] { "-cr", "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-cr", "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_ROLE_NAME); // test: -r is required when drop role - args = new String[] { "-dr", "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-dr", "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_ROLE_NAME); // test: -r is required when add role to group - args = new String[] { "-arg", "-g", "testGroup1", "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-arg", "-g", "testGroup1", "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_ROLE_NAME); // test: -g is required when add role to group - args = new String[] { "-arg", "-r", TEST_ROLE_NAME_2, "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-arg", "-r", TEST_ROLE_NAME_2, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_GROUP_NAME); // test: -r is required when delete role from group - args = new String[] { "-drg", "-g", "testGroup1", "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-drg", "-g", "testGroup1", "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_ROLE_NAME); // test: -g is required when delete role from group - args = new String[] { "-drg", "-r", TEST_ROLE_NAME_2, "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-drg", "-r", TEST_ROLE_NAME_2, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_GROUP_NAME); // test: -r is required when grant privilege to role - args = new String[] { "-gpr", "-p", "server=server1", "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-gpr", "-p", "server=server1", "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_ROLE_NAME); // test: -p is required when grant privilege to role - args = new String[] { "-gpr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-gpr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_PRIVILEGE); // test: action is required in privilege - args = new String[] { "-gpr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath(), "-p", "host=*->topic=t1" }; - sentryShell = new SentryShellKafka(); - try { + args = new String[] { "-gpr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath(), "-p", "host=*->topic=t1", "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); + try { getShellResultWithOSRedirect(sentryShell, args, false); fail("Expected IllegalArgumentException"); } catch (IllegalArgumentException e) { assert(("Kafka privilege must end with a valid action.\n" + KafkaPrivilegeValidator.KafkaPrivilegeHelpMsg).equals(e.getCause().getMessage())); } catch (Exception e) { - fail ("Unexpected exception received. " + e); - } + fail ("Unexpected exception received. " + e); + } // test: -r is required when revoke privilege from role - args = new String[] { "-rpr", "-p", "host=h1", "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-rpr", "-p", "host=h1", "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_ROLE_NAME); // test: -p is required when revoke privilege from role - args = new String[] { "-rpr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] { "-rpr", "-r", TEST_ROLE_NAME_1, "-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsg(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + SentryShellCommon.OPTION_DESC_PRIVILEGE); // test: command option is required for shell - args = new String[] {"-conf", confPath.getAbsolutePath() }; - sentryShell = new SentryShellKafka(); + args = new String[] {"-conf", confPath.getAbsolutePath(), "-t", "kafka" }; + sentryShell = new SentryShellGeneric(); validateMissingParameterMsgsContains(sentryShell, args, SentryShellCommon.PREFIX_MESSAGE_MISSING_OPTION + "[", "-arg Add role to group", @@ -494,8 +493,8 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { } // redirect the System.out to ByteArrayOutputStream, then execute the command and parse the result. - private Set<String> getShellResultWithOSRedirect(SentryShellKafka sentryShell, - String[] args, boolean expectedExecuteResult) throws Exception { + private Set<String> getShellResultWithOSRedirect(SentryShellGeneric sentryShell, + String[] args, boolean expectedExecuteResult) throws Exception { PrintStream oldOut = System.out; ByteArrayOutputStream outContent = new ByteArrayOutputStream(); System.setOut(new PrintStream(outContent)); @@ -508,7 +507,7 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { private void validateRoleNames(Set<String> roleNames, String ... expectedRoleNames) { if (expectedRoleNames != null && expectedRoleNames.length > 0) { assertEquals("Found: " + roleNames.size() + " roles, expected: " + expectedRoleNames.length, - expectedRoleNames.length, roleNames.size()); + expectedRoleNames.length, roleNames.size()); Set<String> lowerCaseRoles = new HashSet<String>(); for (String role : roleNames) { lowerCaseRoles.add(role.toLowerCase()); @@ -516,19 +515,19 @@ public class TestSentryShellKafka extends SentryGenericServiceIntegrationBase { for (String expectedRole : expectedRoleNames) { assertTrue("Expected role: " + expectedRole, - lowerCaseRoles.contains(expectedRole.toLowerCase())); + lowerCaseRoles.contains(expectedRole.toLowerCase())); } } } - private void validateMissingParameterMsg(SentryShellKafka sentryShell, String[] args, - String expectedErrorMsg) throws Exception { + private void validateMissingParameterMsg(SentryShellGeneric sentryShell, String[] args, + String expectedErrorMsg) throws Exception { Set<String> errorMsgs = getShellResultWithOSRedirect(sentryShell, args, false); assertTrue("Expected error message: " + expectedErrorMsg, errorMsgs.contains(expectedErrorMsg)); } - private void validateMissingParameterMsgsContains(SentryShellKafka sentryShell, String[] args, - String ... expectedErrorMsgsContains) throws Exception { + private void validateMissingParameterMsgsContains(SentryShellGeneric sentryShell, String[] args, + String ... expectedErrorMsgsContains) throws Exception { Set<String> errorMsgs = getShellResultWithOSRedirect(sentryShell, args, false); boolean foundAllMessages = false; Iterator<String> it = errorMsgs.iterator();
