@Test
 public void testUGIAuthMethodInRealUser() throws Exception {
   final UserGroupInformation ugi = UserGroupInformation.getCurrentUser();
   UserGroupInformation proxyUgi = UserGroupInformation.createProxyUser("proxy", ugi);
   final AuthenticationMethod am = AuthenticationMethod.KERBEROS;
   ugi.setAuthenticationMethod(am);
   Assert.assertEquals(am, ugi.getAuthenticationMethod());
   Assert.assertEquals(AuthenticationMethod.PROXY, proxyUgi.getAuthenticationMethod());
   proxyUgi.doAs(
       new PrivilegedExceptionAction<Object>() {
         public Object run() throws IOException {
           Assert.assertEquals(
               AuthenticationMethod.PROXY,
               UserGroupInformation.getCurrentUser().getAuthenticationMethod());
           Assert.assertEquals(
               am, UserGroupInformation.getCurrentUser().getRealUser().getAuthenticationMethod());
           return null;
         }
       });
   UserGroupInformation proxyUgi2 = new UserGroupInformation(proxyUgi.getSubject());
   proxyUgi2.setAuthenticationMethod(AuthenticationMethod.PROXY);
   Assert.assertEquals(proxyUgi, proxyUgi2);
   // Equality should work if authMethod is null
   UserGroupInformation realugi = UserGroupInformation.getCurrentUser();
   UserGroupInformation proxyUgi3 = UserGroupInformation.createProxyUser("proxyAnother", realugi);
   UserGroupInformation proxyUgi4 = new UserGroupInformation(proxyUgi3.getSubject());
   Assert.assertEquals(proxyUgi3, proxyUgi4);
 }
  /**
   * Log a user in from a keytab file. Loads a user identity from a keytab file and login them in.
   * This new user does not affect the currently logged-in user.
   *
   * @param user the principal name to load from the keytab
   * @param path the path to the keytab file
   * @throws IOException if the keytab file can't be read
   */
  public static synchronized UserGroupInformation loginUserFromKeytabAndReturnUGI(
      String user, String path) throws IOException {
    if (!isSecurityEnabled()) return UserGroupInformation.getCurrentUser();
    String oldKeytabFile = null;
    String oldKeytabPrincipal = null;

    long start = 0;
    try {
      oldKeytabFile = keytabFile;
      oldKeytabPrincipal = keytabPrincipal;
      keytabFile = path;
      keytabPrincipal = user;
      Subject subject = new Subject();

      LoginContext login =
          new LoginContext(HadoopConfiguration.KEYTAB_KERBEROS_CONFIG_NAME, subject);

      start = System.currentTimeMillis();
      login.login();
      metrics.loginSuccess.inc(System.currentTimeMillis() - start);
      UserGroupInformation newLoginUser = new UserGroupInformation(subject);
      newLoginUser.setLogin(login);
      newLoginUser.setAuthenticationMethod(AuthenticationMethod.KERBEROS);

      return newLoginUser;
    } catch (LoginException le) {
      if (start > 0) {
        metrics.loginFailure.inc(System.currentTimeMillis() - start);
      }
      throw new IOException("Login failure for " + user + " from keytab " + path, le);
    } finally {
      if (oldKeytabFile != null) keytabFile = oldKeytabFile;
      if (oldKeytabPrincipal != null) keytabPrincipal = oldKeytabPrincipal;
    }
  }
  /**
   * Log a user in from a keytab file. Loads a user identity from a keytab file and logs them in.
   * They become the currently logged-in user.
   *
   * @param user the principal name to load from the keytab
   * @param path the path to the keytab file
   * @throws IOException if the keytab file can't be read
   */
  public static synchronized void loginUserFromKeytab(String user, String path) throws IOException {
    if (!isSecurityEnabled()) {
      return;
    }

    keytabFile = path;
    keytabPrincipal = user;
    Subject subject = new Subject();
    LoginContext login;
    long start = 0;
    try {
      login = new LoginContext(HadoopConfiguration.KEYTAB_KERBEROS_CONFIG_NAME, subject);
      start = System.currentTimeMillis();
      login.login();
      metrics.loginSuccess.inc(System.currentTimeMillis() - start);
      loginUser = new UserGroupInformation(subject);
      loginUser.setLogin(login);
      loginUser.setAuthenticationMethod(AuthenticationMethod.KERBEROS);
    } catch (LoginException le) {
      if (start > 0) {
        metrics.loginFailure.inc(System.currentTimeMillis() - start);
      }
      throw new IOException("Login failure for " + user + " from keytab " + path, le);
    }
    LOG.info("Login successful for user " + keytabPrincipal + " using keytab file " + keytabFile);
  }
 /**
  * Create a user from a login name. It is intended to be used for remote users in RPC, since it
  * won't have any credentials.
  *
  * @param user the full user principal name, must not be empty or null
  * @return the UserGroupInformation for the remote user.
  */
 public static UserGroupInformation createRemoteUser(String user) {
   if (user == null || "".equals(user)) {
     throw new IllegalArgumentException("Null user");
   }
   Subject subject = new Subject();
   subject.getPrincipals().add(new User(user));
   UserGroupInformation result = new UserGroupInformation(subject);
   result.setAuthenticationMethod(AuthenticationMethod.SIMPLE);
   return result;
 }
 public static UserGroupInformation createConfigFileUser(String user, String password) {
   if (user == null || "".equals(user)) {
     throw new IllegalArgumentException("Null user");
   }
   Subject subject = new Subject();
   subject.getPrincipals().add(new User(user));
   subject.getPrivateCredentials().add(new ConfigFileCredentials(password));
   UserGroupInformation result = new UserGroupInformation(subject);
   result.setAuthenticationMethod(AuthenticationMethod.CONFIGFILE);
   return result;
 }
 @Test
 public void testUGIAuthMethod() throws Exception {
   final UserGroupInformation ugi = UserGroupInformation.getCurrentUser();
   final AuthenticationMethod am = AuthenticationMethod.KERBEROS;
   ugi.setAuthenticationMethod(am);
   Assert.assertEquals(am, ugi.getAuthenticationMethod());
   ugi.doAs(
       new PrivilegedExceptionAction<Object>() {
         public Object run() throws IOException {
           Assert.assertEquals(
               am, UserGroupInformation.getCurrentUser().getAuthenticationMethod());
           return null;
         }
       });
 }
 /**
  * Create a proxy user using username of the effective user and the ugi of the real user.
  *
  * @param user
  * @param realUser
  * @return proxyUser ugi
  */
 public static UserGroupInformation createProxyUser(String user, UserGroupInformation realUser) {
   if (user == null || "".equals(user)) {
     throw new IllegalArgumentException("Null user");
   }
   if (realUser == null) {
     throw new IllegalArgumentException("Null real user");
   }
   Subject subject = new Subject();
   Set<Principal> principals = subject.getPrincipals();
   principals.add(new User(user));
   principals.add(new RealUser(realUser));
   UserGroupInformation result = new UserGroupInformation(subject);
   result.setAuthenticationMethod(AuthenticationMethod.PROXY);
   return result;
 }
  /**
   * Get the currently logged in user.
   *
   * @return the logged in user
   * @throws IOException if login fails
   */
  public static synchronized UserGroupInformation getLoginUser() throws IOException {
    if (loginUser == null) {
      try {
        Subject subject = new Subject();
        LoginContext login;
        if (isSecurityEnabled()) {
          login = new LoginContext(HadoopConfiguration.USER_KERBEROS_CONFIG_NAME, subject);
        } else if (useConfiguredFileAuth) {
          login = new LoginContext(HadoopConfiguration.FILE_CONFIG_NAME, subject);
        } else {
          login = new LoginContext(HadoopConfiguration.SIMPLE_CONFIG_NAME, subject);
        }
        login.login();
        loginUser = new UserGroupInformation(subject);
        loginUser.setLogin(login);
        // loginUser.setAuthenticationMethod(isSecurityEnabled() ?
        //                                  AuthenticationMethod.KERBEROS :
        //                                  AuthenticationMethod.SIMPLE);
        AuthenticationMethod authMethod = AuthenticationMethod.SIMPLE;
        if (isSecurityEnabled()) {
          authMethod = AuthenticationMethod.KERBEROS;
        } else if (useConfiguredFileAuth) {
          authMethod = AuthenticationMethod.CONFIGFILE;
        } else {
          authMethod = AuthenticationMethod.SIMPLE;
        }
        loginUser.setAuthenticationMethod(authMethod);

        loginUser = new UserGroupInformation(login.getSubject());
        String fileLocation = System.getenv(HADOOP_TOKEN_FILE_LOCATION);
        if (fileLocation != null && isSecurityEnabled()) {
          // load the token storage file and put all of the tokens into the
          // user.
          Credentials cred = Credentials.readTokenStorageFiles(fileLocation, conf);
          for (Token<?> token : cred.getAllTokens()) {
            loginUser.addToken(token);
          }
        }
        loginUser.spawnAutoRenewalThreadForUserCreds();
      } catch (LoginException le) {
        throw new IOException("failure to login", le);
      }
    }
    return loginUser;
  }
示例#9
0
 private static UserGroupInformation initUGI(
     final UserGroupInformation realUgi,
     final String doAsUserFromQuery,
     final HttpServletRequest request,
     final boolean isSecurityEnabled,
     final Configuration conf)
     throws AuthorizationException {
   final UserGroupInformation ugi;
   if (doAsUserFromQuery == null) {
     // non-proxy case
     ugi = realUgi;
   } else {
     // proxy case
     ugi = UserGroupInformation.createProxyUser(doAsUserFromQuery, realUgi);
     ugi.setAuthenticationMethod(
         isSecurityEnabled ? AuthenticationMethod.PROXY : AuthenticationMethod.SIMPLE);
     ProxyUsers.authorize(ugi, request.getRemoteAddr(), conf);
   }
   return ugi;
 }
示例#10
0
  @Test(timeout = 60000)
  public void testSecureProxyAuthParamsInUrl() throws IOException {
    Configuration conf = new Configuration();
    // fake turning on security so api thinks it should use tokens
    SecurityUtil.setAuthenticationMethod(KERBEROS, conf);
    UserGroupInformation.setConfiguration(conf);

    UserGroupInformation ugi = UserGroupInformation.createRemoteUser("test-user");
    ugi.setAuthenticationMethod(KERBEROS);
    ugi = UserGroupInformation.createProxyUser("test-proxy-user", ugi);
    UserGroupInformation.setLoginUser(ugi);

    WebHdfsFileSystem webhdfs = getWebHdfsFileSystem(ugi, conf);
    Path fsPath = new Path("/");
    String tokenString = webhdfs.getDelegationToken().encodeToUrlString();

    // send real+effective
    URL getTokenUrl = webhdfs.toUrl(GetOpParam.Op.GETDELEGATIONTOKEN, fsPath);
    checkQueryParams(
        new String[] {
          GetOpParam.Op.GETDELEGATIONTOKEN.toQueryString(),
          new UserParam(ugi.getRealUser().getShortUserName()).toString(),
          new DoAsParam(ugi.getShortUserName()).toString()
        },
        getTokenUrl);

    // send real+effective
    URL renewTokenUrl =
        webhdfs.toUrl(
            PutOpParam.Op.RENEWDELEGATIONTOKEN, fsPath, new TokenArgumentParam(tokenString));
    checkQueryParams(
        new String[] {
          PutOpParam.Op.RENEWDELEGATIONTOKEN.toQueryString(),
          new UserParam(ugi.getRealUser().getShortUserName()).toString(),
          new DoAsParam(ugi.getShortUserName()).toString(),
          new TokenArgumentParam(tokenString).toString(),
        },
        renewTokenUrl);

    // send token
    URL cancelTokenUrl =
        webhdfs.toUrl(
            PutOpParam.Op.CANCELDELEGATIONTOKEN, fsPath, new TokenArgumentParam(tokenString));
    checkQueryParams(
        new String[] {
          PutOpParam.Op.CANCELDELEGATIONTOKEN.toQueryString(),
          new UserParam(ugi.getRealUser().getShortUserName()).toString(),
          new DoAsParam(ugi.getShortUserName()).toString(),
          new TokenArgumentParam(tokenString).toString(),
        },
        cancelTokenUrl);

    // send token
    URL fileStatusUrl = webhdfs.toUrl(GetOpParam.Op.GETFILESTATUS, fsPath);
    checkQueryParams(
        new String[] {
          GetOpParam.Op.GETFILESTATUS.toQueryString(), new DelegationParam(tokenString).toString()
        },
        fileStatusUrl);

    // wipe out internal token to simulate auth always required
    webhdfs.setDelegationToken(null);

    // send real+effective
    cancelTokenUrl =
        webhdfs.toUrl(
            PutOpParam.Op.CANCELDELEGATIONTOKEN, fsPath, new TokenArgumentParam(tokenString));
    checkQueryParams(
        new String[] {
          PutOpParam.Op.CANCELDELEGATIONTOKEN.toQueryString(),
          new UserParam(ugi.getRealUser().getShortUserName()).toString(),
          new DoAsParam(ugi.getShortUserName()).toString(),
          new TokenArgumentParam(tokenString).toString()
        },
        cancelTokenUrl);

    // send real+effective
    fileStatusUrl = webhdfs.toUrl(GetOpParam.Op.GETFILESTATUS, fsPath);
    checkQueryParams(
        new String[] {
          GetOpParam.Op.GETFILESTATUS.toQueryString(),
          new UserParam(ugi.getRealUser().getShortUserName()).toString(),
          new DoAsParam(ugi.getShortUserName()).toString()
        },
        fileStatusUrl);
  }
示例#11
0
  /**
   * Get {@link UserGroupInformation} and possibly the delegation token out of the request.
   *
   * @param context the Servlet context
   * @param request the http request
   * @param conf configuration
   * @param secureAuthMethod the AuthenticationMethod used in secure mode.
   * @param tryUgiParameter Should it try the ugi parameter?
   * @return a new user from the request
   * @throws AccessControlException if the request has no token
   */
  public static UserGroupInformation getUGI(
      ServletContext context,
      HttpServletRequest request,
      Configuration conf,
      final AuthenticationMethod secureAuthMethod,
      final boolean tryUgiParameter)
      throws IOException {
    final UserGroupInformation ugi;
    final String usernameFromQuery = getUsernameFromQuery(request, tryUgiParameter);
    final String doAsUserFromQuery = request.getParameter(DoAsParam.NAME);

    if (UserGroupInformation.isSecurityEnabled()) {
      final String remoteUser = request.getRemoteUser();
      String tokenString = request.getParameter(DELEGATION_PARAMETER_NAME);
      if (tokenString != null) {
        Token<DelegationTokenIdentifier> token = new Token<DelegationTokenIdentifier>();
        token.decodeFromUrlString(tokenString);
        SecurityUtil.setTokenService(token, NameNode.getAddress(conf));
        token.setKind(DelegationTokenIdentifier.HDFS_DELEGATION_KIND);

        ByteArrayInputStream buf = new ByteArrayInputStream(token.getIdentifier());
        DataInputStream in = new DataInputStream(buf);
        DelegationTokenIdentifier id = new DelegationTokenIdentifier();
        id.readFields(in);
        if (context != null) {
          NameNode nn = (NameNode) context.getAttribute("name.node");
          if (nn != null) {
            // Verify the token.
            nn.getNamesystem()
                .getDelegationTokenSecretManager()
                .verifyToken(id, token.getPassword());
          }
        }
        ugi = id.getUser();
        if (ugi.getRealUser() == null) {
          // non-proxy case
          checkUsername(ugi.getShortUserName(), usernameFromQuery);
          checkUsername(null, doAsUserFromQuery);
        } else {
          // proxy case
          checkUsername(ugi.getRealUser().getShortUserName(), usernameFromQuery);
          checkUsername(ugi.getShortUserName(), doAsUserFromQuery);
          ProxyUsers.authorize(ugi, request.getRemoteAddr(), conf);
        }
        ugi.addToken(token);
        ugi.setAuthenticationMethod(AuthenticationMethod.TOKEN);
      } else {
        if (remoteUser == null) {
          throw new IOException("Security enabled but user not " + "authenticated by filter");
        }
        final UserGroupInformation realUgi = UserGroupInformation.createRemoteUser(remoteUser);
        checkUsername(realUgi.getShortUserName(), usernameFromQuery);
        // This is not necessarily true, could have been auth'ed by user-facing
        // filter
        realUgi.setAuthenticationMethod(secureAuthMethod);
        ugi = initUGI(realUgi, doAsUserFromQuery, request, true, conf);
      }
    } else { // Security's not on, pull from url
      final UserGroupInformation realUgi =
          usernameFromQuery == null
              ? getDefaultWebUser(conf) // not specified in request
              : UserGroupInformation.createRemoteUser(usernameFromQuery);
      realUgi.setAuthenticationMethod(AuthenticationMethod.SIMPLE);
      ugi = initUGI(realUgi, doAsUserFromQuery, request, false, conf);
    }

    if (LOG.isDebugEnabled()) LOG.debug("getUGI is returning: " + ugi.getShortUserName());
    return ugi;
  }