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.regionserver; 019 020import static org.junit.jupiter.api.Assertions.assertTrue; 021 022import java.io.IOException; 023import org.apache.commons.lang3.RandomStringUtils; 024import org.apache.hadoop.hbase.HBaseTestingUtil; 025import org.apache.hadoop.hbase.client.ColumnFamilyDescriptor; 026import org.apache.hadoop.hbase.client.ColumnFamilyDescriptorBuilder; 027import org.apache.hadoop.hbase.client.Get; 028import org.apache.hadoop.hbase.client.Put; 029import org.apache.hadoop.hbase.filter.TimestampsFilter; 030import org.apache.hadoop.hbase.testclassification.LargeTests; 031import org.apache.hadoop.hbase.testclassification.RegionServerTests; 032import org.apache.hadoop.hbase.util.Bytes; 033import org.junit.jupiter.api.BeforeEach; 034import org.junit.jupiter.api.Tag; 035import org.junit.jupiter.api.Test; 036 037import org.apache.hbase.thirdparty.com.google.common.collect.ImmutableList; 038 039@Tag(RegionServerTests.TAG) 040@Tag(LargeTests.TAG) 041public class TestTimestampFilterSeekHint { 042 043 private final static HBaseTestingUtil TEST_UTIL = new HBaseTestingUtil(); 044 private final static String RK = "myRK"; 045 private final static byte[] RK_BYTES = Bytes.toBytes(RK); 046 047 private final static String FAMILY = "D"; 048 private final static byte[] FAMILY_BYTES = Bytes.toBytes(FAMILY); 049 050 private final static String QUAL = "0"; 051 private final static byte[] QUAL_BYTES = Bytes.toBytes(QUAL); 052 053 public static final int MAX_VERSIONS = 50000; 054 private HRegion region; 055 private int regionCount = 0; 056 057 @Test 058 public void testGetSeek() throws IOException { 059 StoreFileScanner.instrument(); 060 prepareRegion(); 061 062 Get g = new Get(RK_BYTES); 063 final TimestampsFilter timestampsFilter = new TimestampsFilter(ImmutableList.of(5L), true); 064 g.setFilter(timestampsFilter); 065 final long initialSeekCount = StoreFileScanner.getSeekCount(); 066 region.get(g); 067 final long finalSeekCount = StoreFileScanner.getSeekCount(); 068 069 /* 070 * Make sure there's more than one. Aka one seek to get to the row, and one to get to the time. 071 */ 072 assertTrue(finalSeekCount >= initialSeekCount + 3); 073 } 074 075 @Test 076 public void testGetDoesntSeekWithNoHint() throws IOException { 077 StoreFileScanner.instrument(); 078 prepareRegion(); 079 080 Get g = new Get(RK_BYTES); 081 g.setFilter(new TimestampsFilter(ImmutableList.of(5L))); 082 final long initialSeekCount = StoreFileScanner.getSeekCount(); 083 region.get(g); 084 final long finalSeekCount = StoreFileScanner.getSeekCount(); 085 086 assertTrue(finalSeekCount >= initialSeekCount); 087 assertTrue(finalSeekCount < initialSeekCount + 3); 088 } 089 090 @BeforeEach 091 public void prepareRegion() throws IOException { 092 ColumnFamilyDescriptor columnFamilyDescriptor = ColumnFamilyDescriptorBuilder 093 .newBuilder(Bytes.toBytes(FAMILY)).setBlocksize(1024).setMaxVersions(MAX_VERSIONS).build(); 094 region = TEST_UTIL.createTestRegion("TestTimestampFilterSeekHint" + regionCount++, 095 columnFamilyDescriptor); 096 097 for (long i = 0; i < MAX_VERSIONS - 2; i++) { 098 Put p = new Put(RK_BYTES, i); 099 p.addColumn(FAMILY_BYTES, QUAL_BYTES, Bytes.toBytes(RandomStringUtils.randomAlphabetic(255))); 100 region.put(p); 101 } 102 region.flush(true); 103 } 104}