001/* 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018package org.apache.hadoop.hbase.security; 019 020import static org.apache.hadoop.hbase.security.HBaseKerberosUtils.getClientKeytabForTesting; 021import static org.apache.hadoop.hbase.security.HBaseKerberosUtils.getClientPrincipalForTesting; 022import static org.apache.hadoop.hbase.security.HBaseKerberosUtils.getKeytabFileForTesting; 023import static org.apache.hadoop.hbase.security.HBaseKerberosUtils.getPrincipalForTesting; 024import static org.apache.hadoop.hbase.security.HBaseKerberosUtils.getSecuredConfiguration; 025import static org.junit.Assert.assertEquals; 026import static org.junit.Assert.assertFalse; 027import static org.junit.Assert.assertNotNull; 028import static org.junit.Assert.assertTrue; 029 030import java.io.File; 031import java.io.IOException; 032import org.apache.hadoop.conf.Configuration; 033import org.apache.hadoop.hbase.AuthUtil; 034import org.apache.hadoop.hbase.HBaseClassTestRule; 035import org.apache.hadoop.hbase.HBaseTestingUtility; 036import org.apache.hadoop.hbase.testclassification.SecurityTests; 037import org.apache.hadoop.hbase.testclassification.SmallTests; 038import org.apache.hadoop.minikdc.MiniKdc; 039import org.apache.hadoop.security.UserGroupInformation; 040import org.junit.AfterClass; 041import org.junit.BeforeClass; 042import org.junit.ClassRule; 043import org.junit.Test; 044import org.junit.experimental.categories.Category; 045 046@Category({ SecurityTests.class, SmallTests.class }) 047public class TestUsersOperationsWithSecureHadoop { 048 049 @ClassRule 050 public static final HBaseClassTestRule CLASS_RULE = 051 HBaseClassTestRule.forClass(TestUsersOperationsWithSecureHadoop.class); 052 053 private static final HBaseTestingUtility TEST_UTIL = new HBaseTestingUtility(); 054 private static final File KEYTAB_FILE = 055 new File(TEST_UTIL.getDataTestDir("keytab").toUri().getPath()); 056 057 private static MiniKdc KDC; 058 059 private static String HOST = "localhost"; 060 061 private static String PRINCIPAL; 062 063 private static String CLIENT_NAME; 064 065 @BeforeClass 066 public static void setUp() throws Exception { 067 KDC = TEST_UTIL.setupMiniKdc(KEYTAB_FILE); 068 PRINCIPAL = "hbase/" + HOST; 069 CLIENT_NAME = "foo"; 070 KDC.createPrincipal(KEYTAB_FILE, PRINCIPAL, CLIENT_NAME); 071 HBaseKerberosUtils.setPrincipalForTesting(PRINCIPAL + "@" + KDC.getRealm()); 072 HBaseKerberosUtils.setKeytabFileForTesting(KEYTAB_FILE.getAbsolutePath()); 073 HBaseKerberosUtils.setClientPrincipalForTesting(CLIENT_NAME + "@" + KDC.getRealm()); 074 HBaseKerberosUtils.setClientKeytabForTesting(KEYTAB_FILE.getAbsolutePath()); 075 } 076 077 @AfterClass 078 public static void tearDown() throws IOException { 079 if (KDC != null) { 080 KDC.stop(); 081 } 082 TEST_UTIL.cleanupTestDir(); 083 } 084 085 /** 086 * test login with security enabled configuration To run this test, we must specify the following 087 * system properties: 088 * <p> 089 * <b> hbase.regionserver.kerberos.principal </b> 090 * <p> 091 * <b> hbase.regionserver.keytab.file </b> 092 */ 093 @Test 094 public void testUserLoginInSecureHadoop() throws Exception { 095 // Default login is system user. 096 UserGroupInformation defaultLogin = UserGroupInformation.getCurrentUser(); 097 098 String nnKeyTab = getKeytabFileForTesting(); 099 String dnPrincipal = getPrincipalForTesting(); 100 101 assertNotNull("KerberosKeytab was not specified", nnKeyTab); 102 assertNotNull("KerberosPrincipal was not specified", dnPrincipal); 103 104 Configuration conf = getSecuredConfiguration(); 105 UserGroupInformation.setConfiguration(conf); 106 107 User.login(conf, HBaseKerberosUtils.KRB_KEYTAB_FILE, HBaseKerberosUtils.KRB_PRINCIPAL, 108 "localhost"); 109 UserGroupInformation successLogin = UserGroupInformation.getLoginUser(); 110 assertFalse("ugi should be different in in case success login", 111 defaultLogin.equals(successLogin)); 112 } 113 114 @Test 115 public void testLoginWithUserKeytabAndPrincipal() throws Exception { 116 String clientKeytab = getClientKeytabForTesting(); 117 String clientPrincipal = getClientPrincipalForTesting(); 118 assertNotNull("Path for client keytab is not specified.", clientKeytab); 119 assertNotNull("Client principal is not specified.", clientPrincipal); 120 121 Configuration conf = getSecuredConfiguration(); 122 conf.set(AuthUtil.HBASE_CLIENT_KEYTAB_FILE, clientKeytab); 123 conf.set(AuthUtil.HBASE_CLIENT_KERBEROS_PRINCIPAL, clientPrincipal); 124 UserGroupInformation.setConfiguration(conf); 125 126 UserProvider provider = UserProvider.instantiate(conf); 127 assertTrue("Client principal or keytab is empty", provider.shouldLoginFromKeytab()); 128 129 provider.login(AuthUtil.HBASE_CLIENT_KEYTAB_FILE, AuthUtil.HBASE_CLIENT_KERBEROS_PRINCIPAL); 130 User loginUser = provider.getCurrent(); 131 assertEquals(CLIENT_NAME, loginUser.getShortName()); 132 assertEquals(getClientPrincipalForTesting(), loginUser.getName()); 133 } 134 135 @Test 136 public void testAuthUtilLogin() throws Exception { 137 String clientKeytab = getClientKeytabForTesting(); 138 String clientPrincipal = getClientPrincipalForTesting(); 139 Configuration conf = getSecuredConfiguration(); 140 conf.set(AuthUtil.HBASE_CLIENT_KEYTAB_FILE, clientKeytab); 141 conf.set(AuthUtil.HBASE_CLIENT_KERBEROS_PRINCIPAL, clientPrincipal); 142 UserGroupInformation.setConfiguration(conf); 143 144 User user = AuthUtil.loginClient(conf); 145 assertTrue(user.isLoginFromKeytab()); 146 assertEquals(CLIENT_NAME, user.getShortName()); 147 assertEquals(getClientPrincipalForTesting(), user.getName()); 148 } 149}