如何对Java Hbase API进行单元测试

dan*_*ilo 6 java hadoop hbase mocking apache-storm

我正在使用Java HBase API从Hbase获取值.这是我的代码.

public class GetViewFromHbaseBolt extends BaseBasicBolt {

private HTable table;
private String zkQuorum;
private String zkClientPort;
private String tableName;

public GetViewFromHbaseBolt(String table, String zkQuorum,
        String zkClientPort) {
    this.tableName = table;
    this.zkQuorum = zkQuorum;
    this.zkClientPort = zkClientPort;
}

@Override
public void prepare(Map config, TopologyContext context) {
    try {
        table = getHTable();
    } catch (IOException e) {

        e.printStackTrace();
    }
}

@Override
public void execute(Tuple tuple, BasicOutputCollector collector) {
    try {
        if (tuple.size() > 0) {

            Long dtmid = tuple.getLong(0);

            byte[] rowKey = HBaseRowKeyDistributor.getDistributedKey(dtmid);
            Get get = new Get(rowKey);
            get.addFamily("a".getBytes());

            Result result = table.get(get);
            System.out.println(result);
            byte[] bidUser = result.getValue("a".getBytes(),
                    "co_created_5076".getBytes());
            collector.emit(new Values(dtmid, bidUser));
        }

    } catch (IOException e) {
        e.printStackTrace();

    }

}

@Override
public void declareOutputFields(OutputFieldsDeclarer declarer) {

    declarer.declare(new Fields("dtmi", "bidUser"));

}

// setting up the conections for Hbase
protected HTable getHTable() throws IOException {
    HTable table = null;
    Configuration conf;
    conf = HBaseConfiguration.create();
    conf.set("hbase.zookeeper.property.clientPort", zkClientPort);
    conf.set("hbase.zookeeper.quorum", zkQuorum);

    table = new HTable(conf, tableName);

    return table;
}
Run Code Online (Sandbox Code Playgroud)

这很好用.现在我正在使用Mockito API编写单元测试.在我的测试类中,当得到一个java.langNullPointerException时(table.get(any(Get.class))).thenReturn(result); 叫做.

   public class GetViewFromHbaseBoltTest {

@Mock
private TopologyContext topologyContext;
@Mock
private  HTable table;
//HTable table = mock(HTable.class);


@Test
public void testExecute() throws IOException {

    long dtmId = 350000000770902930L;
    final byte[] COL_FAMILY = "a".getBytes();
    final byte[] COL_QUALIFIER = "co_created_5076".getBytes();

    // A mock tuple with a single dtmid
    Tuple tuple = mock(Tuple.class);
    when(tuple.size()).thenReturn(1);
    when(tuple.getLong(0)).thenReturn(dtmId);

    List<KeyValue> kvs = new ArrayList<KeyValue>();
    kvs.add(new KeyValue(COL_FAMILY, COL_QUALIFIER, Bytes
            .toBytes("ExpedtedBytes")));
    Result result = new Result(kvs);


    when(table.get(any(Get.class))).thenReturn(result);

    BasicOutputCollector collector = mock(BasicOutputCollector.class);

    GetViewFromHbaseBolt bolt = mock(GetViewFromHbaseBolt.class);
    // Execute the bolt.
    bolt.execute(tuple, collector);

    ArgumentCaptor<Values> valuesArg = ArgumentCaptor
            .forClass(Values.class);
    verify(collector).emit(valuesArg.capture());
    ArrayList<Object> d = valuesArg.getValue();

// verify

}
Run Code Online (Sandbox Code Playgroud)

K13*_*139 3

编辑

“单元测试”是为了验证和验证特定的“代码单元”。如果该“代码单元”依赖于外部调用,那么我们会模拟这些调用以返回某些值。

如果您不从测试用例中调用“实际代码单元”,那么对代码进行单元测试还有什么意义。知道了?

您应该仅模拟来自实际方法的外部调用,而不是实际方法本身。

所以我会嘲笑:

@Mock
private HBaseRowKeyDistributor hDist;

@Mock
private HTable table;

@Test
public void sampleTest(){

    //Mock data and external calls

    final byte [] COL_FAMILY = "a".getBytes();
    final byte [] COL_QUALIFIER = "co_created_5076".getBytes();

    List<KeyValue> kvs =new ArrayList<KeyValue>();
    kvs.add(new KeyValue(COL_FAMILY, COL_QUALIFIER,
                           Bytes.toBytes("ExpedtedBytes")));
     Result result = new Result(kvs);

     byte[] rowKey = "Hello".getBytes();
     when(hdist.getDistributedKey(anyString()).thenReturn(rowKey);

     when(table.get(any(Get.class))).thenReturn(result);

     //Call the actual method
     calloriginalUnitTestingMethod();


     //Now Verify the result using Mockito verify like
     verify(...)

     //You could also intercept the attributes

}
Run Code Online (Sandbox Code Playgroud)