hadoop AccessControlList 源码

  • 2022-10-20
  • 浏览 (328)

haddop AccessControlList 代码

文件路径:/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/security/authorize/AccessControlList.java

/**
 * 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.hadoop.security.authorize;

import java.io.DataInput;
import java.io.DataOutput;
import java.io.IOException;
import java.util.Collection;
import java.util.HashSet;
import java.util.LinkedList;
import java.util.List;
import java.util.Set;

import org.apache.hadoop.classification.InterfaceAudience;
import org.apache.hadoop.classification.InterfaceStability;
import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.io.Writable;
import org.apache.hadoop.io.WritableFactories;
import org.apache.hadoop.io.WritableFactory;
import org.apache.hadoop.security.Groups;
import org.apache.hadoop.security.UserGroupInformation;
import org.apache.hadoop.util.StringUtils;

/**
 * Class representing a configured access control list.
 */
@InterfaceAudience.Public
@InterfaceStability.Evolving
public class AccessControlList implements Writable {

  static {                                      // register a ctor
    WritableFactories.setFactory
    (AccessControlList.class,
      new WritableFactory() {
        @Override
        public Writable newInstance() { return new AccessControlList(); }
      });
  }

  // Indicates an ACL string that represents access to all users
  public static final String WILDCARD_ACL_VALUE = "*";
  private static final int INITIAL_CAPACITY = 256;
  public static final String USE_REAL_ACLS = "~";

  // Set of users who are granted access.
  private Collection<String> users;
  // Set of groups which are granted access
  private Collection<String> groups;
  // Whether all users are granted access.
  private boolean allAllowed;

  private Groups groupsMapping = Groups.getUserToGroupsMappingService(new Configuration());

  /**
   * This constructor exists primarily for AccessControlList to be Writable.
   */
  public AccessControlList() {
  }

  /**
   * Construct a new ACL from a String representation of the same.
   * 
   * The String is a a comma separated list of users and groups.
   * The user list comes first and is separated by a space followed 
   * by the group list. For e.g. "user1,user2 group1,group2"
   * 
   * @param aclString String representation of the ACL
   */
  public AccessControlList(String aclString) {
    buildACL(aclString.split(" ", 2));
  }
  
  /**
   * Construct a new ACL from String representation of users and groups
   * 
   * The arguments are comma separated lists
   * 
   * @param users comma separated list of users
   * @param groups comma separated list of groups
   */
  public AccessControlList(String users, String groups) {
    buildACL(new String[] {users, groups});
  }

  /**
   * Build ACL from the given array of strings.
   * The strings contain comma separated values.
   *
   * @param userGroupStrings build ACL from array of Strings
   */
  private void buildACL(String[] userGroupStrings) {
    users = new HashSet<>();
    groups = new HashSet<>();
    for (String aclPart : userGroupStrings) {
      if (aclPart != null && isWildCardACLValue(aclPart)) {
        allAllowed = true;
        break;
      }
    }
    if (!allAllowed) {      
      if (userGroupStrings.length >= 1 && userGroupStrings[0] != null) {
        users = StringUtils.getTrimmedStringCollection(userGroupStrings[0]);
      } 
      
      if (userGroupStrings.length == 2 && userGroupStrings[1] != null) {
        groups = StringUtils.getTrimmedStringCollection(userGroupStrings[1]);
        groupsMapping.cacheGroupsAdd(new LinkedList<String>(groups));
      }
    }
  }
  
  /**
   * Checks whether ACL string contains wildcard
   *
   * @param aclString check this ACL string for wildcard
   * @return true if ACL string contains wildcard false otherwise
   */
  private boolean isWildCardACLValue(String aclString) {
    if (aclString.contains(WILDCARD_ACL_VALUE) && 
        aclString.trim().equals(WILDCARD_ACL_VALUE)) {
      return true;
    }
    return false;
  }

  public boolean isAllAllowed() {
    return allAllowed;
  }
  
  /**
   * Add user to the names of users allowed for this service.
   * 
   * @param user
   *          The user name
   */
  public void addUser(String user) {
    if (isWildCardACLValue(user)) {
      throw new IllegalArgumentException("User " + user + " can not be added");
    }
    if (!isAllAllowed()) {
      users.add(user);
    }
  }

  /**
   * Add group to the names of groups allowed for this service.
   * 
   * @param group
   *          The group name
   */
  public void addGroup(String group) {
    if (isWildCardACLValue(group)) {
      throw new IllegalArgumentException("Group " + group + " can not be added");
    }
    if (!isAllAllowed()) {
      List<String> groupsList = new LinkedList<String>();
      groupsList.add(group);
      groupsMapping.cacheGroupsAdd(groupsList);
      groups.add(group);
    }
  }

  /**
   * Remove user from the names of users allowed for this service.
   * 
   * @param user
   *          The user name
   */
  public void removeUser(String user) {
    if (isWildCardACLValue(user)) {
      throw new IllegalArgumentException("User " + user + " can not be removed");
    }
    if (!isAllAllowed()) {
      users.remove(user);
    }
  }

  /**
   * Remove group from the names of groups allowed for this service.
   * 
   * @param group
   *          The group name
   */
  public void removeGroup(String group) {
    if (isWildCardACLValue(group)) {
      throw new IllegalArgumentException("Group " + group
          + " can not be removed");
    }
    if (!isAllAllowed()) {
      groups.remove(group);
    }
  }

  /**
   * Get the names of users allowed for this service.
   * @return the set of user names. the set must not be modified.
   */
  public Collection<String> getUsers() {
    return users;
  }
  
  /**
   * Get the names of user groups allowed for this service.
   * @return the set of group names. the set must not be modified.
   */
  public Collection<String> getGroups() {
    return groups;
  }

  /**
   * Checks if a user represented by the provided {@link UserGroupInformation}
   * is a member of the Access Control List. If user was proxied and
   * USE_REAL_ACLS + the real user name is in the control list, then treat this
   * case as if user were in the ACL list.
   * @param ugi UserGroupInformation to check if contained in the ACL
   * @return true if ugi is member of the list or if USE_REAL_ACLS + real user
   * is in the list
   */
  public final boolean isUserInList(UserGroupInformation ugi) {
    if (allAllowed || users.contains(ugi.getShortUserName())) {
      return true;
    } else if (!groups.isEmpty()) {
      Set<String> ugiGroups = ugi.getGroupsSet();
      for (String group : groups) {
        if (ugiGroups.contains(group)) {
          return true;
        }
      }
    }
    UserGroupInformation realUgi = ugi.getRealUser();
    return realUgi != null &&
           users.contains(USE_REAL_ACLS + realUgi.getShortUserName());
  }

  public boolean isUserAllowed(UserGroupInformation ugi) {
    return isUserInList(ugi);
  }

  /**
   * Returns descriptive way of users and groups that are part of this ACL.
   * Use {@link #getAclString()} to get the exact String that can be given to
   * the constructor of AccessControlList to create a new instance.
   */
  @Override
  public String toString() {
    String str = null;

    if (allAllowed) {
      str = "All users are allowed";
    }
    else if (users.isEmpty() && groups.isEmpty()) {
      str = "No users are allowed";
    }
    else {
      String usersStr = null;
      String groupsStr = null;
      if (!users.isEmpty()) {
        usersStr = users.toString();
      }
      if (!groups.isEmpty()) {
        groupsStr = groups.toString();
      }

      if (!users.isEmpty() && !groups.isEmpty()) {
        str = "Users " + usersStr + " and members of the groups "
            + groupsStr + " are allowed";
      }
      else if (!users.isEmpty()) {
        str = "Users " + usersStr + " are allowed";
      }
      else {// users is empty array and groups is nonempty
        str = "Members of the groups "
            + groupsStr + " are allowed";
      }
    }

    return str;
  }

  /**
   * Returns the access control list as a String that can be used for building a
   * new instance by sending it to the constructor of {@link AccessControlList}.
   * @return acl string.
   */
  public String getAclString() {
    StringBuilder sb = new StringBuilder(INITIAL_CAPACITY);
    if (allAllowed) {
      sb.append('*');
    }
    else {
      sb.append(getUsersString())
          .append(" ")
          .append(getGroupsString());
    }
    return sb.toString();
  }

  /**
   * Serializes the AccessControlList object
   */
  @Override
  public void write(DataOutput out) throws IOException {
    String aclString = getAclString();
    Text.writeString(out, aclString);
  }

  /**
   * Deserializes the AccessControlList object
   */
  @Override
  public void readFields(DataInput in) throws IOException {
    String aclString = Text.readString(in);
    buildACL(aclString.split(" ", 2));
  }

  /**
   * Returns comma-separated concatenated single String of the set 'users'
   *
   * @return comma separated list of users
   */
  private String getUsersString() {
    return getString(users);
  }

  /**
   * Returns comma-separated concatenated single String of the set 'groups'
   *
   * @return comma separated list of groups
   */
  private String getGroupsString() {
    return getString(groups);
  }

  /**
   * Returns comma-separated concatenated single String of all strings of
   * the given set
   *
   * @param strings set of strings to concatenate
   */
  private String getString(Collection<String> strings) {
    StringBuilder sb = new StringBuilder(INITIAL_CAPACITY);
    boolean first = true;
    for(String str: strings) {
      if (!first) {
        sb.append(",");
      } else {
        first = false;
      }
      sb.append(str);
    }
    return sb.toString();
  }
}

相关信息

hadoop 源码目录

相关文章

hadoop AuthorizationException 源码

hadoop DefaultImpersonationProvider 源码

hadoop ImpersonationProvider 源码

hadoop PolicyProvider 源码

hadoop ProxyServers 源码

hadoop ProxyUsers 源码

hadoop RefreshAuthorizationPolicyProtocol 源码

hadoop Service 源码

hadoop ServiceAuthorizationManager 源码

hadoop package-info 源码

0  赞