jerqi commented on code in PR #4515:
URL: https://github.com/apache/gravitino/pull/4515#discussion_r1724766504


##########
authorizations/authorization-ranger/src/main/java/org/apache/gravitino/authorization/ranger/RangerHelper.java:
##########
@@ -0,0 +1,533 @@
+/*
+ * 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.gravitino.authorization.ranger;
+
+import com.google.common.annotations.VisibleForTesting;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.ImmutableSet;
+import com.google.common.collect.Lists;
+import com.google.common.collect.Sets;
+import com.google.errorprone.annotations.FormatMethod;
+import com.google.errorprone.annotations.FormatString;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
+import java.util.stream.Collectors;
+import org.apache.commons.lang.StringUtils;
+import org.apache.gravitino.MetadataObject;
+import org.apache.gravitino.authorization.Owner;
+import org.apache.gravitino.authorization.Privilege;
+import org.apache.gravitino.authorization.SecurableObject;
+import org.apache.gravitino.authorization.SecurableObjects;
+import org.apache.gravitino.authorization.ranger.reference.RangerDefines;
+import org.apache.gravitino.exceptions.AuthorizationPluginException;
+import org.apache.ranger.RangerServiceException;
+import org.apache.ranger.plugin.model.RangerPolicy;
+import org.apache.ranger.plugin.model.RangerRole;
+import org.apache.ranger.plugin.util.GrantRevokeRoleRequest;
+import org.apache.ranger.plugin.util.SearchFilter;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * This class is a helper class for the Ranger authorization plugin. It 
provides the ability to
+ * manage the Ranger policies and roles.
+ */
+public class RangerHelper {
+  private static final Logger LOG = 
LoggerFactory.getLogger(RangerHelper.class);
+  public static final String MANAGED_BY_GRAVITINO = "MANAGED_BY_GRAVITINO";
+
+  RangerAuthorizationPlugin rangerAuthorizationPlugin;
+
+  /** Mapping Gravitino privilege name to the underlying authorization system 
privileges. */
+  protected Map<Privilege.Name, Set<String>> privilegesMapping = null;
+  /** The owner privileges, the owner can do anything on the metadata object */
+  protected Set<String> ownerPrivileges = null;
+
+  /**
+   * Because Ranger doesn't support the precise search, Ranger will return the 
policy meets the
+   * wildcard(*,?) conditions, If you use `db.table` condition to search 
policy, the Ranger will
+   * match `db1.table1`, `db1.table2`, `db*.table*`, So we need to manually 
precisely filter this
+   * research results. <br>
+   * policySearchKeys: The search Ranger policy condition key defines. <br>
+   * policyPreciseFilterKeys: The precise filter Ranger search results key 
defines <br>
+   */
+  protected List<String> policySearchKeys = null;
+
+  protected List<String> policyPreciseFilterKeys = null;
+
+  public RangerHelper(RangerAuthorizationPlugin rangerAuthorizationPlugin, 
String catalogProvider) {
+    this.rangerAuthorizationPlugin = rangerAuthorizationPlugin;
+    switch (catalogProvider) {
+      case "hive":
+        initPrivilegesMapping();
+        initOwnerPrivileges();
+        initPolicySearchKeys();
+        initPreciseFilterKeys();
+        break;
+      default:
+        throw new IllegalArgumentException(
+            "Authorization plugin unsupported catalog provider: " + 
catalogProvider);
+    }
+  }
+
+  /** Initial mapping Gravitino privilege name to the underlying authorization 
system privileges. */
+  private void initPrivilegesMapping() {
+    privilegesMapping =
+        ImmutableMap.<Privilege.Name, Set<String>>builder()
+            .put(
+                Privilege.Name.CREATE_SCHEMA,
+                ImmutableSet.of(RangerDefines.ACCESS_TYPE_HIVE_CREATE))
+            .put(
+                Privilege.Name.CREATE_TABLE, 
ImmutableSet.of(RangerDefines.ACCESS_TYPE_HIVE_CREATE))
+            .put(
+                Privilege.Name.MODIFY_TABLE,
+                ImmutableSet.of(
+                    RangerDefines.ACCESS_TYPE_HIVE_UPDATE,
+                    RangerDefines.ACCESS_TYPE_HIVE_ALTER,
+                    RangerDefines.ACCESS_TYPE_HIVE_WRITE))
+            .put(
+                Privilege.Name.SELECT_TABLE,
+                ImmutableSet.of(
+                    RangerDefines.ACCESS_TYPE_HIVE_READ, 
RangerDefines.ACCESS_TYPE_HIVE_SELECT))
+            .build();
+  }
+
+  /** Initial Owner privileges */
+  private void initOwnerPrivileges() {
+    ownerPrivileges = ImmutableSet.of(RangerDefines.ACCESS_TYPE_HIVE_ALL);
+  }
+
+  /** Initial Ranger policy search key defines */
+  private void initPolicySearchKeys() {
+    policySearchKeys =
+        Arrays.asList(
+            RangerDefines.SEARCH_FILTER_DATABASE,
+            RangerDefines.SEARCH_FILTER_TABLE,
+            RangerDefines.SEARCH_FILTER_COLUMN);
+  }
+
+  /** Initial precise filter key defines */
+  private void initPreciseFilterKeys() {
+    policyPreciseFilterKeys =
+        Arrays.asList(
+            RangerDefines.RESOURCE_DATABASE,
+            RangerDefines.RESOURCE_TABLE,
+            RangerDefines.RESOURCE_COLUMN);
+  }
+
+  /**
+   * For easy management, each privilege will create one 
RangerPolicyItemAccess in the policy.
+   *
+   * @param policyItem The policy item to check
+   * @throws AuthorizationPluginException If the policy item contains more 
than one access type
+   */
+  void checkPolicyItemAccess(RangerPolicy.RangerPolicyItem policyItem)
+      throws AuthorizationPluginException {
+    if (policyItem.getAccesses().size() != 1) {
+      throw new AuthorizationPluginException(
+          "The access type only have one in the delegate Gravitino management 
policy");
+    }
+    Set<String> setAccesses = new HashSet<>();
+    policyItem
+        .getAccesses()
+        .forEach(
+            access -> {
+              if (setAccesses.contains(access.getType())) {
+                throw new AuthorizationPluginException(
+                    "Contain duplicate privilege(%s) in the delegate Gravitino 
management policy ",
+                    access.getType());
+              }
+              setAccesses.add(access.getType());
+            });
+  }
+
+  /**
+   * Add policy item access items base the securable object's privileges. <br>
+   * We didn't clean the policy items because one Ranger policy maybe contains 
multiple Gravitino
+   * securable objects. <br>
+   */
+  void addPolicyItem(RangerPolicy policy, String roleName, SecurableObject 
securableObject) {
+    // First check the privilege if support in the Ranger Hive
+    checkPrivileges(securableObject);
+
+    // Add the policy items by the securable object's privileges
+    securableObject
+        .privileges()
+        .forEach(
+            gravitinoPrivilege -> {
+              // Translate the Gravitino privilege to map Ranger privilege
+              rangerAuthorizationPlugin
+                  .translatePrivilege(gravitinoPrivilege.name())
+                  .forEach(
+                      mappedPrivilege -> {

Review Comment:
   Could you extract a method for `matchingPrivilege`? Many places use this.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to