You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@hive.apache.org by xu...@apache.org on 2015/10/28 13:11:18 UTC

[25/55] [abbrv] hive git commit: HIVE-11755 :Incorrect method called with Kerberos enabled in AccumuloStorageHandler (Josh Elser via Brock Noland)

HIVE-11755 :Incorrect method called with Kerberos enabled in AccumuloStorageHandler (Josh Elser via Brock Noland)

Signed-off-by: Ashutosh Chauhan <ha...@apache.org>


Project: http://git-wip-us.apache.org/repos/asf/hive/repo
Commit: http://git-wip-us.apache.org/repos/asf/hive/commit/ee2d3189
Tree: http://git-wip-us.apache.org/repos/asf/hive/tree/ee2d3189
Diff: http://git-wip-us.apache.org/repos/asf/hive/diff/ee2d3189

Branch: refs/heads/spark
Commit: ee2d3189ff9a7e8bd604b2e036d53632a9b4e616
Parents: 3e0d87f
Author: Josh Elser <jo...@gmail.com>
Authored: Tue Sep 8 14:46:00 2015 -0800
Committer: Ashutosh Chauhan <ha...@apache.org>
Committed: Sat Oct 24 14:30:14 2015 -0700

----------------------------------------------------------------------
 .../hive/accumulo/HiveAccumuloHelper.java       | 55 ++++++++++---
 .../mr/HiveAccumuloTableOutputFormat.java       | 50 ++++++++----
 .../hive/accumulo/TestHiveAccumuloHelper.java   | 69 +++++++++++++++-
 .../mr/TestHiveAccumuloTableOutputFormat.java   | 86 +++++++++++++++++++-
 4 files changed, 229 insertions(+), 31 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/hive/blob/ee2d3189/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/HiveAccumuloHelper.java
----------------------------------------------------------------------
diff --git a/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/HiveAccumuloHelper.java b/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/HiveAccumuloHelper.java
index dfc5d03..71b8b77 100644
--- a/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/HiveAccumuloHelper.java
+++ b/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/HiveAccumuloHelper.java
@@ -19,6 +19,7 @@ package org.apache.hadoop.hive.accumulo;
 import static com.google.common.base.Preconditions.checkNotNull;
 
 import java.io.IOException;
+import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
 import java.util.Collection;
 
@@ -238,22 +239,56 @@ public class HiveAccumuloHelper {
   public void setZooKeeperInstance(JobConf jobConf, Class<?> inputOrOutputFormatClass, String
       zookeepers, String instanceName, boolean useSasl) throws IOException {
     try {
-      Class<?> clientConfigClass = JavaUtils.loadClass(CLIENT_CONFIGURATION_CLASS_NAME);
-
-      // get the ClientConfiguration
-      Object clientConfig = getClientConfiguration(zookeepers, instanceName, useSasl);
-
-      // AccumuloOutputFormat.setZooKeeperInstance(JobConf, ClientConfiguration) or
-      // AccumuloInputFormat.setZooKeeperInstance(JobConf, ClientConfiguration)
-      Method setZooKeeperMethod = inputOrOutputFormatClass.getMethod(
-          SET_ZOOKEEPER_INSTANCE_METHOD_NAME, JobConf.class, clientConfigClass);
-      setZooKeeperMethod.invoke(null, jobConf, clientConfig);
+      setZooKeeperInstanceWithReflection(jobConf, inputOrOutputFormatClass, zookeepers,
+          instanceName, useSasl);
+    } catch (InvocationTargetException e) {
+      Throwable cause = e.getCause();
+      if (null != cause && cause instanceof IllegalStateException) {
+        throw (IllegalStateException) cause;
+      }
+      throw new IOException("Failed to invoke setZooKeeperInstance method", e);
+    } catch (IllegalStateException e) {
+      // re-throw the ISE so the caller can work around the silly impl that throws this in the
+      // first place.
+      throw e;
     } catch (Exception e) {
       throw new IOException("Failed to invoke setZooKeeperInstance method", e);
     }
   }
 
   /**
+   * Wrap the setZooKeeperInstance reflected-call into its own method for testing
+   *
+   * @param jobConf
+   *          The JobConf
+   * @param inputOrOutputFormatClass
+   *          The InputFormat or OutputFormat class
+   * @param zookeepers
+   *          ZooKeeper hosts
+   * @param instanceName
+   *          Accumulo instance name
+   * @param useSasl
+   *          Is SASL enabled
+   * @throws IOException
+   *           When invocation of the method fails
+   */
+  void setZooKeeperInstanceWithReflection(JobConf jobConf, Class<?> inputOrOutputFormatClass, String
+      zookeepers, String instanceName, boolean useSasl) throws IOException, ClassNotFoundException,
+      NoSuchMethodException, SecurityException, IllegalAccessException, IllegalArgumentException,
+      InvocationTargetException {
+    Class<?> clientConfigClass = JavaUtils.loadClass(CLIENT_CONFIGURATION_CLASS_NAME);
+
+    // get the ClientConfiguration
+    Object clientConfig = getClientConfiguration(zookeepers, instanceName, useSasl);
+
+    // AccumuloOutputFormat.setZooKeeperInstance(JobConf, ClientConfiguration) or
+    // AccumuloInputFormat.setZooKeeperInstance(JobConf, ClientConfiguration)
+    Method setZooKeeperMethod = inputOrOutputFormatClass.getMethod(
+        SET_ZOOKEEPER_INSTANCE_METHOD_NAME, JobConf.class, clientConfigClass);
+    setZooKeeperMethod.invoke(null, jobConf, clientConfig);
+  }
+      
+  /**
    * Wrapper around <code>ConfiguratorBase.unwrapAuthenticationToken</code> which only exists in
    * 1.7.0 and new. Uses reflection to not break compat.
    *

http://git-wip-us.apache.org/repos/asf/hive/blob/ee2d3189/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/mr/HiveAccumuloTableOutputFormat.java
----------------------------------------------------------------------
diff --git a/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/mr/HiveAccumuloTableOutputFormat.java b/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/mr/HiveAccumuloTableOutputFormat.java
index 0189c07..3ae5431 100644
--- a/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/mr/HiveAccumuloTableOutputFormat.java
+++ b/accumulo-handler/src/java/org/apache/hadoop/hive/accumulo/mr/HiveAccumuloTableOutputFormat.java
@@ -61,7 +61,7 @@ public class HiveAccumuloTableOutputFormat extends AccumuloOutputFormat {
   }
 
   protected void configureAccumuloOutputFormat(JobConf job) throws IOException {
-    AccumuloConnectionParameters cnxnParams = new AccumuloConnectionParameters(job);
+    AccumuloConnectionParameters cnxnParams = getConnectionParams(job);
 
     final String tableName = job.get(AccumuloSerDeParameters.TABLE_NAME);
 
@@ -72,35 +72,35 @@ public class HiveAccumuloTableOutputFormat extends AccumuloOutputFormat {
     // Set the necessary Accumulo information
     try {
       if (cnxnParams.useMockInstance()) {
-        setAccumuloMockInstance(job, cnxnParams.getAccumuloInstanceName());
+        setMockInstanceWithErrorChecking(job, cnxnParams.getAccumuloInstanceName());
       } else {
         // Accumulo instance name with ZK quorum
-        setAccumuloZooKeeperInstance(job, cnxnParams.getAccumuloInstanceName(),
+        setZooKeeperInstanceWithErrorChecking(job, cnxnParams.getAccumuloInstanceName(),
             cnxnParams.getZooKeepers(), cnxnParams.useSasl());
       }
 
       // Extract the delegation Token from the UGI and add it to the job
       // The AccumuloOutputFormat will look for it there.
       if (cnxnParams.useSasl()) {
-        UserGroupInformation ugi = UserGroupInformation.getCurrentUser();
-        if (!ugi.hasKerberosCredentials()) {
-          helper.addTokenFromUserToJobConf(ugi, job);
+        UserGroupInformation ugi = getCurrentUser();
+        if (!hasKerberosCredentials(ugi)) {
+          getHelper().addTokenFromUserToJobConf(ugi, job);
         } else {
           // Still in the local JVM, can use Kerberos credentials
           try {
             Connector connector = cnxnParams.getConnector();
-            AuthenticationToken token = helper.getDelegationToken(connector);
+            AuthenticationToken token = getHelper().getDelegationToken(connector);
 
             // Send the DelegationToken down to the Configuration for Accumulo to use
-            setConnectorInfo(job, cnxnParams.getAccumuloUserName(), token);
+            setConnectorInfoWithErrorChecking(job, cnxnParams.getAccumuloUserName(), token);
 
             // Convert the Accumulo token in a Hadoop token
-            Token<? extends TokenIdentifier> accumuloToken = helper.getHadoopToken(token);
+            Token<? extends TokenIdentifier> accumuloToken = getHelper().getHadoopToken(token);
 
             log.info("Adding Hadoop Token for Accumulo to Job's Credentials");
 
             // Add the Hadoop token to the JobConf
-            helper.mergeTokenIntoJobConf(job, accumuloToken);
+            getHelper().mergeTokenIntoJobConf(job, accumuloToken);
 
             // Make sure the UGI contains the token too for good measure
             if (!ugi.addToken(accumuloToken)) {
@@ -111,7 +111,7 @@ public class HiveAccumuloTableOutputFormat extends AccumuloOutputFormat {
           }
         }
       } else {
-        setAccumuloConnectorInfo(job, cnxnParams.getAccumuloUserName(),
+        setConnectorInfoWithErrorChecking(job, cnxnParams.getAccumuloUserName(),
             new PasswordToken(cnxnParams.getAccumuloPassword()));
       }
 
@@ -125,7 +125,7 @@ public class HiveAccumuloTableOutputFormat extends AccumuloOutputFormat {
 
   // Non-static methods to wrap the static AccumuloOutputFormat methods to enable testing
 
-  protected void setAccumuloConnectorInfo(JobConf conf, String username, AuthenticationToken token)
+  protected void setConnectorInfoWithErrorChecking(JobConf conf, String username, AuthenticationToken token)
       throws AccumuloSecurityException {
     try {
       AccumuloOutputFormat.setConnectorInfo(conf, username, token);
@@ -136,14 +136,14 @@ public class HiveAccumuloTableOutputFormat extends AccumuloOutputFormat {
   }
 
   @SuppressWarnings("deprecation")
-  protected void setAccumuloZooKeeperInstance(JobConf conf, String instanceName, String zookeepers,
+  protected void setZooKeeperInstanceWithErrorChecking(JobConf conf, String instanceName, String zookeepers,
       boolean isSasl) throws IOException {
     try {
       if (isSasl) {
         // Reflection to support Accumulo 1.5. Remove when Accumulo 1.5 support is dropped
         // 1.6 works with the deprecated 1.5 method, but must use reflection for 1.7-only
         // SASL support
-        helper.setZooKeeperInstance(conf, AccumuloOutputFormat.class, zookeepers, instanceName,
+        getHelper().setZooKeeperInstance(conf, AccumuloOutputFormat.class, zookeepers, instanceName,
             isSasl);
       } else {
         AccumuloOutputFormat.setZooKeeperInstance(conf, instanceName, zookeepers);
@@ -155,7 +155,7 @@ public class HiveAccumuloTableOutputFormat extends AccumuloOutputFormat {
     }
   }
 
-  protected void setAccumuloMockInstance(JobConf conf, String instanceName) {
+  protected void setMockInstanceWithErrorChecking(JobConf conf, String instanceName) {
     try {
       AccumuloOutputFormat.setMockInstance(conf, instanceName);
     } catch (IllegalStateException e) {
@@ -167,4 +167,24 @@ public class HiveAccumuloTableOutputFormat extends AccumuloOutputFormat {
   protected void setDefaultAccumuloTableName(JobConf conf, String tableName) {
     AccumuloOutputFormat.setDefaultTableName(conf, tableName);
   }
+
+  HiveAccumuloHelper getHelper() {
+    // Allows mocking in testing.
+    return helper;
+  }
+
+  AccumuloConnectionParameters getConnectionParams(JobConf conf) {
+    // Allows mocking in testing.
+    return new AccumuloConnectionParameters(conf);
+  }
+
+  boolean hasKerberosCredentials(UserGroupInformation ugi) {
+    // Allows mocking in testing.
+    return ugi.hasKerberosCredentials();
+  }
+
+  UserGroupInformation getCurrentUser() throws IOException {
+    // Allows mocking in testing.
+    return UserGroupInformation.getCurrentUser();
+  }
 }

http://git-wip-us.apache.org/repos/asf/hive/blob/ee2d3189/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/TestHiveAccumuloHelper.java
----------------------------------------------------------------------
diff --git a/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/TestHiveAccumuloHelper.java b/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/TestHiveAccumuloHelper.java
index 88544f0..406768a 100644
--- a/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/TestHiveAccumuloHelper.java
+++ b/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/TestHiveAccumuloHelper.java
@@ -18,18 +18,23 @@ package org.apache.hadoop.hive.accumulo;
 
 import static org.junit.Assert.assertEquals;
 
+import java.io.IOException;
+import java.lang.reflect.InvocationTargetException;
 import java.util.ArrayList;
 import java.util.Collection;
 
+import org.apache.accumulo.core.client.mapred.AccumuloInputFormat;
 import org.apache.hadoop.io.Text;
 import org.apache.hadoop.mapred.JobConf;
 import org.apache.hadoop.security.UserGroupInformation;
 import org.apache.hadoop.security.token.Token;
+import org.apache.log4j.Logger;
 import org.junit.Before;
 import org.junit.Test;
 import org.mockito.Mockito;
 
 public class TestHiveAccumuloHelper {
+  private static final Logger log = Logger.getLogger(TestHiveAccumuloHelper.class);
 
   private HiveAccumuloHelper helper;
 
@@ -46,7 +51,13 @@ public class TestHiveAccumuloHelper {
 
     Mockito.when(token.getService()).thenReturn(service);
 
-    helper.mergeTokenIntoJobConf(jobConf, token);
+    try {
+      helper.mergeTokenIntoJobConf(jobConf, token);
+    } catch (IOException e) {
+      // Hadoop 1 doesn't support credential merging, so this will fail.
+      log.info("Ignoring exception, likely coming from Hadoop 1", e);
+      return;
+    }
 
     Collection<Token<?>> tokens = jobConf.getCredentials().getAllTokens();
     assertEquals(1, tokens.size());
@@ -66,10 +77,64 @@ public class TestHiveAccumuloHelper {
     Mockito.when(token.getKind()).thenReturn(HiveAccumuloHelper.ACCUMULO_SERVICE);
     Mockito.when(token.getService()).thenReturn(service);
 
-    helper.addTokenFromUserToJobConf(ugi, jobConf);
+    try {
+      helper.addTokenFromUserToJobConf(ugi, jobConf);
+    } catch (IOException e) {
+      // Hadoop 1 doesn't support credential merging, so this will fail.
+      log.info("Ignoring exception, likely coming from Hadoop 1", e);
+      return;
+    }
 
     Collection<Token<?>> credTokens = jobConf.getCredentials().getAllTokens();
     assertEquals(1, credTokens.size());
     assertEquals(service, credTokens.iterator().next().getService());
   }
+
+  @Test(expected = IllegalStateException.class)
+  public void testISEIsPropagated() throws Exception {
+    final HiveAccumuloHelper helper = Mockito.mock(HiveAccumuloHelper.class);
+
+    final JobConf jobConf = Mockito.mock(JobConf.class);
+    final Class<?> inputOrOutputFormatClass = AccumuloInputFormat.class;
+    final String zookeepers = "localhost:2181";
+    final String instanceName = "accumulo_instance";
+    final boolean useSasl = false;
+
+    // Call the real "public" method
+    Mockito.doCallRealMethod().when(helper).setZooKeeperInstance(jobConf, inputOrOutputFormatClass,
+        zookeepers, instanceName, useSasl);
+
+    // Mock the private one to throw the ISE
+    Mockito.doThrow(new IllegalStateException()).when(helper).
+        setZooKeeperInstanceWithReflection(jobConf, inputOrOutputFormatClass, zookeepers,
+            instanceName, useSasl);
+
+    // Should throw an IllegalStateException
+    helper.setZooKeeperInstance(jobConf, inputOrOutputFormatClass, zookeepers, instanceName,
+        useSasl);
+  }
+
+  @Test(expected = IllegalStateException.class)
+  public void testISEIsPropagatedWithReflection() throws Exception {
+    final HiveAccumuloHelper helper = Mockito.mock(HiveAccumuloHelper.class);
+
+    final JobConf jobConf = Mockito.mock(JobConf.class);
+    final Class<?> inputOrOutputFormatClass = AccumuloInputFormat.class;
+    final String zookeepers = "localhost:2181";
+    final String instanceName = "accumulo_instance";
+    final boolean useSasl = false;
+
+    // Call the real "public" method
+    Mockito.doCallRealMethod().when(helper).setZooKeeperInstance(jobConf, inputOrOutputFormatClass,
+        zookeepers, instanceName, useSasl);
+
+    // Mock the private one to throw the IAE
+    Mockito.doThrow(new InvocationTargetException(new IllegalStateException())).when(helper).
+        setZooKeeperInstanceWithReflection(jobConf, inputOrOutputFormatClass, zookeepers,
+            instanceName, useSasl);
+
+    // Should throw an IllegalStateException
+    helper.setZooKeeperInstance(jobConf, inputOrOutputFormatClass, zookeepers, instanceName,
+        useSasl);
+  }
 }

http://git-wip-us.apache.org/repos/asf/hive/blob/ee2d3189/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/mr/TestHiveAccumuloTableOutputFormat.java
----------------------------------------------------------------------
diff --git a/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/mr/TestHiveAccumuloTableOutputFormat.java b/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/mr/TestHiveAccumuloTableOutputFormat.java
index 5d3f15b..5fdab28 100644
--- a/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/mr/TestHiveAccumuloTableOutputFormat.java
+++ b/accumulo-handler/src/test/org/apache/hadoop/hive/accumulo/mr/TestHiveAccumuloTableOutputFormat.java
@@ -18,15 +18,18 @@ package org.apache.hadoop.hive.accumulo.mr;
 
 import java.io.IOException;
 import java.util.Arrays;
+import java.util.Collection;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Map.Entry;
 import java.util.Properties;
 
+import org.apache.accumulo.core.client.AccumuloException;
 import org.apache.accumulo.core.client.AccumuloSecurityException;
 import org.apache.accumulo.core.client.Connector;
 import org.apache.accumulo.core.client.Instance;
 import org.apache.accumulo.core.client.mock.MockInstance;
+import org.apache.accumulo.core.client.security.tokens.AuthenticationToken;
 import org.apache.accumulo.core.client.security.tokens.PasswordToken;
 import org.apache.accumulo.core.data.Key;
 import org.apache.accumulo.core.data.Mutation;
@@ -36,6 +39,7 @@ import org.apache.accumulo.core.security.ColumnVisibility;
 import org.apache.hadoop.conf.Configuration;
 import org.apache.hadoop.fs.FileSystem;
 import org.apache.hadoop.hive.accumulo.AccumuloConnectionParameters;
+import org.apache.hadoop.hive.accumulo.HiveAccumuloHelper;
 import org.apache.hadoop.hive.accumulo.columns.ColumnEncoding;
 import org.apache.hadoop.hive.accumulo.serde.AccumuloRowSerializer;
 import org.apache.hadoop.hive.accumulo.serde.AccumuloSerDe;
@@ -54,6 +58,10 @@ import org.apache.hadoop.hive.serde2.typeinfo.TypeInfoFactory;
 import org.apache.hadoop.io.Text;
 import org.apache.hadoop.mapred.JobConf;
 import org.apache.hadoop.mapred.RecordWriter;
+import org.apache.hadoop.security.UserGroupInformation;
+import org.apache.hadoop.security.token.Token;
+import org.apache.hadoop.security.token.TokenIdentifier;
+import org.junit.After;
 import org.junit.Assert;
 import org.junit.Before;
 import org.junit.Rule;
@@ -87,6 +95,15 @@ public class TestHiveAccumuloTableOutputFormat {
     conf.set(AccumuloConnectionParameters.INSTANCE_NAME, instanceName);
     conf.set(AccumuloConnectionParameters.ZOOKEEPERS, zookeepers);
     conf.set(AccumuloConnectionParameters.TABLE_NAME, outputTable);
+
+    System.setProperty("java.security.krb5.realm", "accumulo");
+    System.setProperty("java.security.krb5.kdc", "fake");
+  }
+
+  @After
+  public void cleanup() {
+    System.setProperty("java.security.krb5.realm", "");
+    System.setProperty("java.security.krb5.kdc", "");
   }
 
   @Test
@@ -94,12 +111,72 @@ public class TestHiveAccumuloTableOutputFormat {
     HiveAccumuloTableOutputFormat outputFormat = Mockito.mock(HiveAccumuloTableOutputFormat.class);
 
     Mockito.doCallRealMethod().when(outputFormat).configureAccumuloOutputFormat(conf);
+    Mockito.doCallRealMethod().when(outputFormat).getConnectionParams(conf);
+
+    outputFormat.configureAccumuloOutputFormat(conf);
+
+    Mockito.verify(outputFormat).setConnectorInfoWithErrorChecking(conf, user, new PasswordToken(password));
+    Mockito.verify(outputFormat).setZooKeeperInstanceWithErrorChecking(conf, instanceName, zookeepers, false);
+    Mockito.verify(outputFormat).setDefaultAccumuloTableName(conf, outputTable);
+  }
+
+  @SuppressWarnings({"rawtypes", "unchecked"})
+  @Test
+  public void testSaslConfiguration() throws IOException, AccumuloException, AccumuloSecurityException {
+    final HiveAccumuloTableOutputFormat outputFormat = Mockito.mock(HiveAccumuloTableOutputFormat.class);
+    final AuthenticationToken authToken = Mockito.mock(AuthenticationToken.class);
+    final Token hadoopToken = Mockito.mock(Token.class);
+    final HiveAccumuloHelper helper = Mockito.mock(HiveAccumuloHelper.class);
+    final AccumuloConnectionParameters cnxnParams = Mockito.mock(AccumuloConnectionParameters.class);
+    final Connector connector = Mockito.mock(Connector.class);
+
+    // Set UGI to use Kerberos
+    // Have to use the string constant to support hadoop 1
+    conf.set("hadoop.security.authentication", "kerberos");
+    UserGroupInformation.setConfiguration(conf);
+
+    // Set the current UGI to a fake user
+    UserGroupInformation user1 = UserGroupInformation.createUserForTesting(user, new String[0]);
+    // Use that as the "current user"
+    Mockito.when(outputFormat.getCurrentUser()).thenReturn(user1);
+
+    // Turn off passwords, enable sasl and set a keytab
+    conf.unset(AccumuloConnectionParameters.USER_PASS);
+
+    // Call the real method instead of the mock
+    Mockito.doCallRealMethod().when(outputFormat).configureAccumuloOutputFormat(conf);
+
+    // Return our mocked objects
+    Mockito.when(outputFormat.getHelper()).thenReturn(helper);
+    Mockito.when(outputFormat.getConnectionParams(conf)).thenReturn(cnxnParams);
+    Mockito.when(cnxnParams.getConnector()).thenReturn(connector);
+    Mockito.when(helper.getDelegationToken(connector)).thenReturn(authToken);
+    Mockito.when(helper.getHadoopToken(authToken)).thenReturn(hadoopToken);
 
+    // Stub AccumuloConnectionParameters actions
+    Mockito.when(cnxnParams.useSasl()).thenReturn(true);
+    Mockito.when(cnxnParams.getAccumuloUserName()).thenReturn(user);
+    Mockito.when(cnxnParams.getAccumuloInstanceName()).thenReturn(instanceName);
+    Mockito.when(cnxnParams.getZooKeepers()).thenReturn(zookeepers);
+
+    // Stub OutputFormat actions
+    Mockito.when(outputFormat.hasKerberosCredentials(user1)).thenReturn(true);
+
+    // Invoke the method
     outputFormat.configureAccumuloOutputFormat(conf);
 
-    Mockito.verify(outputFormat).setAccumuloConnectorInfo(conf, user, new PasswordToken(password));
-    Mockito.verify(outputFormat).setAccumuloZooKeeperInstance(conf, instanceName, zookeepers, false);
+    // The AccumuloInputFormat methods
+    Mockito.verify(outputFormat).setZooKeeperInstanceWithErrorChecking(conf, instanceName, zookeepers, true);
+    Mockito.verify(outputFormat).setConnectorInfoWithErrorChecking(conf, user, authToken);
     Mockito.verify(outputFormat).setDefaultAccumuloTableName(conf, outputTable);
+
+    // Other methods we expect
+    Mockito.verify(helper).mergeTokenIntoJobConf(conf, hadoopToken);
+
+    // Make sure the token made it into the UGI
+    Collection<Token<? extends TokenIdentifier>> tokens = user1.getTokens();
+    Assert.assertEquals(1, tokens.size());
+    Assert.assertEquals(hadoopToken, tokens.iterator().next());
   }
 
   @Test
@@ -109,11 +186,12 @@ public class TestHiveAccumuloTableOutputFormat {
     conf.unset(AccumuloConnectionParameters.ZOOKEEPERS);
 
     Mockito.doCallRealMethod().when(outputFormat).configureAccumuloOutputFormat(conf);
+    Mockito.doCallRealMethod().when(outputFormat).getConnectionParams(conf);
 
     outputFormat.configureAccumuloOutputFormat(conf);
 
-    Mockito.verify(outputFormat).setAccumuloConnectorInfo(conf, user, new PasswordToken(password));
-    Mockito.verify(outputFormat).setAccumuloMockInstance(conf, instanceName);
+    Mockito.verify(outputFormat).setConnectorInfoWithErrorChecking(conf, user, new PasswordToken(password));
+    Mockito.verify(outputFormat).setMockInstanceWithErrorChecking(conf, instanceName);
     Mockito.verify(outputFormat).setDefaultAccumuloTableName(conf, outputTable);
   }