|  | <!DOCTYPE HTML> | 
|  | <html lang="en"> | 
|  | <head> | 
|  | <!-- Generated by javadoc (17) --> | 
|  | <title>Source code</title> | 
|  | <meta name="viewport" content="width=device-width, initial-scale=1"> | 
|  | <meta name="description" content="source: package: org.apache.hadoop.hbase.regionserver, class: TestHRegion, class: NoOpRegionCoprocessor"> | 
|  | <meta name="generator" content="javadoc/SourceToHTMLConverter"> | 
|  | <link rel="stylesheet" type="text/css" href="../../../../../../stylesheet.css" title="Style"> | 
|  | </head> | 
|  | <body class="source-page"> | 
|  | <main role="main"> | 
|  | <div class="source-container"> | 
|  | <pre><span class="source-line-no">001</span><span id="line-1">/*</span> | 
|  | <span class="source-line-no">002</span><span id="line-2"> * Licensed to the Apache Software Foundation (ASF) under one</span> | 
|  | <span class="source-line-no">003</span><span id="line-3"> * or more contributor license agreements.  See the NOTICE file</span> | 
|  | <span class="source-line-no">004</span><span id="line-4"> * distributed with this work for additional information</span> | 
|  | <span class="source-line-no">005</span><span id="line-5"> * regarding copyright ownership.  The ASF licenses this file</span> | 
|  | <span class="source-line-no">006</span><span id="line-6"> * to you under the Apache License, Version 2.0 (the</span> | 
|  | <span class="source-line-no">007</span><span id="line-7"> * "License"); you may not use this file except in compliance</span> | 
|  | <span class="source-line-no">008</span><span id="line-8"> * with the License.  You may obtain a copy of the License at</span> | 
|  | <span class="source-line-no">009</span><span id="line-9"> *</span> | 
|  | <span class="source-line-no">010</span><span id="line-10"> *     http://www.apache.org/licenses/LICENSE-2.0</span> | 
|  | <span class="source-line-no">011</span><span id="line-11"> *</span> | 
|  | <span class="source-line-no">012</span><span id="line-12"> * Unless required by applicable law or agreed to in writing, software</span> | 
|  | <span class="source-line-no">013</span><span id="line-13"> * distributed under the License is distributed on an "AS IS" BASIS,</span> | 
|  | <span class="source-line-no">014</span><span id="line-14"> * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.</span> | 
|  | <span class="source-line-no">015</span><span id="line-15"> * See the License for the specific language governing permissions and</span> | 
|  | <span class="source-line-no">016</span><span id="line-16"> * limitations under the License.</span> | 
|  | <span class="source-line-no">017</span><span id="line-17"> */</span> | 
|  | <span class="source-line-no">018</span><span id="line-18">package org.apache.hadoop.hbase.regionserver;</span> | 
|  | <span class="source-line-no">019</span><span id="line-19"></span> | 
|  | <span class="source-line-no">020</span><span id="line-20">import static org.apache.hadoop.hbase.HBaseTestingUtil.COLUMNS;</span> | 
|  | <span class="source-line-no">021</span><span id="line-21">import static org.apache.hadoop.hbase.HBaseTestingUtil.fam1;</span> | 
|  | <span class="source-line-no">022</span><span id="line-22">import static org.apache.hadoop.hbase.HBaseTestingUtil.fam2;</span> | 
|  | <span class="source-line-no">023</span><span id="line-23">import static org.apache.hadoop.hbase.HBaseTestingUtil.fam3;</span> | 
|  | <span class="source-line-no">024</span><span id="line-24">import static org.junit.Assert.assertArrayEquals;</span> | 
|  | <span class="source-line-no">025</span><span id="line-25">import static org.junit.Assert.assertEquals;</span> | 
|  | <span class="source-line-no">026</span><span id="line-26">import static org.junit.Assert.assertFalse;</span> | 
|  | <span class="source-line-no">027</span><span id="line-27">import static org.junit.Assert.assertNotNull;</span> | 
|  | <span class="source-line-no">028</span><span id="line-28">import static org.junit.Assert.assertNull;</span> | 
|  | <span class="source-line-no">029</span><span id="line-29">import static org.junit.Assert.assertThrows;</span> | 
|  | <span class="source-line-no">030</span><span id="line-30">import static org.junit.Assert.assertTrue;</span> | 
|  | <span class="source-line-no">031</span><span id="line-31">import static org.junit.Assert.fail;</span> | 
|  | <span class="source-line-no">032</span><span id="line-32">import static org.mockito.ArgumentMatchers.any;</span> | 
|  | <span class="source-line-no">033</span><span id="line-33">import static org.mockito.ArgumentMatchers.anyLong;</span> | 
|  | <span class="source-line-no">034</span><span id="line-34">import static org.mockito.ArgumentMatchers.anyString;</span> | 
|  | <span class="source-line-no">035</span><span id="line-35">import static org.mockito.ArgumentMatchers.isA;</span> | 
|  | <span class="source-line-no">036</span><span id="line-36">import static org.mockito.Mockito.atLeast;</span> | 
|  | <span class="source-line-no">037</span><span id="line-37">import static org.mockito.Mockito.doAnswer;</span> | 
|  | <span class="source-line-no">038</span><span id="line-38">import static org.mockito.Mockito.doThrow;</span> | 
|  | <span class="source-line-no">039</span><span id="line-39">import static org.mockito.Mockito.mock;</span> | 
|  | <span class="source-line-no">040</span><span id="line-40">import static org.mockito.Mockito.never;</span> | 
|  | <span class="source-line-no">041</span><span id="line-41">import static org.mockito.Mockito.spy;</span> | 
|  | <span class="source-line-no">042</span><span id="line-42">import static org.mockito.Mockito.times;</span> | 
|  | <span class="source-line-no">043</span><span id="line-43">import static org.mockito.Mockito.verify;</span> | 
|  | <span class="source-line-no">044</span><span id="line-44">import static org.mockito.Mockito.when;</span> | 
|  | <span class="source-line-no">045</span><span id="line-45"></span> | 
|  | <span class="source-line-no">046</span><span id="line-46">import java.io.IOException;</span> | 
|  | <span class="source-line-no">047</span><span id="line-47">import java.io.InterruptedIOException;</span> | 
|  | <span class="source-line-no">048</span><span id="line-48">import java.math.BigDecimal;</span> | 
|  | <span class="source-line-no">049</span><span id="line-49">import java.security.PrivilegedExceptionAction;</span> | 
|  | <span class="source-line-no">050</span><span id="line-50">import java.util.ArrayList;</span> | 
|  | <span class="source-line-no">051</span><span id="line-51">import java.util.Arrays;</span> | 
|  | <span class="source-line-no">052</span><span id="line-52">import java.util.Collection;</span> | 
|  | <span class="source-line-no">053</span><span id="line-53">import java.util.List;</span> | 
|  | <span class="source-line-no">054</span><span id="line-54">import java.util.Map;</span> | 
|  | <span class="source-line-no">055</span><span id="line-55">import java.util.NavigableMap;</span> | 
|  | <span class="source-line-no">056</span><span id="line-56">import java.util.Objects;</span> | 
|  | <span class="source-line-no">057</span><span id="line-57">import java.util.Set;</span> | 
|  | <span class="source-line-no">058</span><span id="line-58">import java.util.TreeMap;</span> | 
|  | <span class="source-line-no">059</span><span id="line-59">import java.util.concurrent.Callable;</span> | 
|  | <span class="source-line-no">060</span><span id="line-60">import java.util.concurrent.CountDownLatch;</span> | 
|  | <span class="source-line-no">061</span><span id="line-61">import java.util.concurrent.ExecutorService;</span> | 
|  | <span class="source-line-no">062</span><span id="line-62">import java.util.concurrent.Executors;</span> | 
|  | <span class="source-line-no">063</span><span id="line-63">import java.util.concurrent.Future;</span> | 
|  | <span class="source-line-no">064</span><span id="line-64">import java.util.concurrent.TimeUnit;</span> | 
|  | <span class="source-line-no">065</span><span id="line-65">import java.util.concurrent.atomic.AtomicBoolean;</span> | 
|  | <span class="source-line-no">066</span><span id="line-66">import java.util.concurrent.atomic.AtomicInteger;</span> | 
|  | <span class="source-line-no">067</span><span id="line-67">import java.util.concurrent.atomic.AtomicLong;</span> | 
|  | <span class="source-line-no">068</span><span id="line-68">import java.util.concurrent.atomic.AtomicReference;</span> | 
|  | <span class="source-line-no">069</span><span id="line-69">import org.apache.commons.lang3.RandomStringUtils;</span> | 
|  | <span class="source-line-no">070</span><span id="line-70">import org.apache.hadoop.conf.Configuration;</span> | 
|  | <span class="source-line-no">071</span><span id="line-71">import org.apache.hadoop.fs.FSDataOutputStream;</span> | 
|  | <span class="source-line-no">072</span><span id="line-72">import org.apache.hadoop.fs.FileStatus;</span> | 
|  | <span class="source-line-no">073</span><span id="line-73">import org.apache.hadoop.fs.FileSystem;</span> | 
|  | <span class="source-line-no">074</span><span id="line-74">import org.apache.hadoop.fs.Path;</span> | 
|  | <span class="source-line-no">075</span><span id="line-75">import org.apache.hadoop.hbase.ArrayBackedTag;</span> | 
|  | <span class="source-line-no">076</span><span id="line-76">import org.apache.hadoop.hbase.Cell;</span> | 
|  | <span class="source-line-no">077</span><span id="line-77">import org.apache.hadoop.hbase.Cell.Type;</span> | 
|  | <span class="source-line-no">078</span><span id="line-78">import org.apache.hadoop.hbase.CellBuilderFactory;</span> | 
|  | <span class="source-line-no">079</span><span id="line-79">import org.apache.hadoop.hbase.CellBuilderType;</span> | 
|  | <span class="source-line-no">080</span><span id="line-80">import org.apache.hadoop.hbase.CellUtil;</span> | 
|  | <span class="source-line-no">081</span><span id="line-81">import org.apache.hadoop.hbase.CompareOperator;</span> | 
|  | <span class="source-line-no">082</span><span id="line-82">import org.apache.hadoop.hbase.CompatibilitySingletonFactory;</span> | 
|  | <span class="source-line-no">083</span><span id="line-83">import org.apache.hadoop.hbase.DoNotRetryIOException;</span> | 
|  | <span class="source-line-no">084</span><span id="line-84">import org.apache.hadoop.hbase.DroppedSnapshotException;</span> | 
|  | <span class="source-line-no">085</span><span id="line-85">import org.apache.hadoop.hbase.ExtendedCell;</span> | 
|  | <span class="source-line-no">086</span><span id="line-86">import org.apache.hadoop.hbase.ExtendedCellBuilderFactory;</span> | 
|  | <span class="source-line-no">087</span><span id="line-87">import org.apache.hadoop.hbase.HBaseClassTestRule;</span> | 
|  | <span class="source-line-no">088</span><span id="line-88">import org.apache.hadoop.hbase.HBaseConfiguration;</span> | 
|  | <span class="source-line-no">089</span><span id="line-89">import org.apache.hadoop.hbase.HBaseTestingUtil;</span> | 
|  | <span class="source-line-no">090</span><span id="line-90">import org.apache.hadoop.hbase.HConstants;</span> | 
|  | <span class="source-line-no">091</span><span id="line-91">import org.apache.hadoop.hbase.HConstants.OperationStatusCode;</span> | 
|  | <span class="source-line-no">092</span><span id="line-92">import org.apache.hadoop.hbase.HDFSBlocksDistribution;</span> | 
|  | <span class="source-line-no">093</span><span id="line-93">import org.apache.hadoop.hbase.KeyValue;</span> | 
|  | <span class="source-line-no">094</span><span id="line-94">import org.apache.hadoop.hbase.MultithreadedTestUtil;</span> | 
|  | <span class="source-line-no">095</span><span id="line-95">import org.apache.hadoop.hbase.MultithreadedTestUtil.RepeatingTestThread;</span> | 
|  | <span class="source-line-no">096</span><span id="line-96">import org.apache.hadoop.hbase.MultithreadedTestUtil.TestThread;</span> | 
|  | <span class="source-line-no">097</span><span id="line-97">import org.apache.hadoop.hbase.NotServingRegionException;</span> | 
|  | <span class="source-line-no">098</span><span id="line-98">import org.apache.hadoop.hbase.PrivateCellUtil;</span> | 
|  | <span class="source-line-no">099</span><span id="line-99">import org.apache.hadoop.hbase.RegionTooBusyException;</span> | 
|  | <span class="source-line-no">100</span><span id="line-100">import org.apache.hadoop.hbase.ServerName;</span> | 
|  | <span class="source-line-no">101</span><span id="line-101">import org.apache.hadoop.hbase.SingleProcessHBaseCluster;</span> | 
|  | <span class="source-line-no">102</span><span id="line-102">import org.apache.hadoop.hbase.StartTestingClusterOption;</span> | 
|  | <span class="source-line-no">103</span><span id="line-103">import org.apache.hadoop.hbase.TableName;</span> | 
|  | <span class="source-line-no">104</span><span id="line-104">import org.apache.hadoop.hbase.TagType;</span> | 
|  | <span class="source-line-no">105</span><span id="line-105">import org.apache.hadoop.hbase.Waiter;</span> | 
|  | <span class="source-line-no">106</span><span id="line-106">import org.apache.hadoop.hbase.client.Append;</span> | 
|  | <span class="source-line-no">107</span><span id="line-107">import org.apache.hadoop.hbase.client.CheckAndMutate;</span> | 
|  | <span class="source-line-no">108</span><span id="line-108">import org.apache.hadoop.hbase.client.CheckAndMutateResult;</span> | 
|  | <span class="source-line-no">109</span><span id="line-109">import org.apache.hadoop.hbase.client.ClientInternalHelper;</span> | 
|  | <span class="source-line-no">110</span><span id="line-110">import org.apache.hadoop.hbase.client.ColumnFamilyDescriptor;</span> | 
|  | <span class="source-line-no">111</span><span id="line-111">import org.apache.hadoop.hbase.client.ColumnFamilyDescriptorBuilder;</span> | 
|  | <span class="source-line-no">112</span><span id="line-112">import org.apache.hadoop.hbase.client.Delete;</span> | 
|  | <span class="source-line-no">113</span><span id="line-113">import org.apache.hadoop.hbase.client.Durability;</span> | 
|  | <span class="source-line-no">114</span><span id="line-114">import org.apache.hadoop.hbase.client.Get;</span> | 
|  | <span class="source-line-no">115</span><span id="line-115">import org.apache.hadoop.hbase.client.Increment;</span> | 
|  | <span class="source-line-no">116</span><span id="line-116">import org.apache.hadoop.hbase.client.Mutation;</span> | 
|  | <span class="source-line-no">117</span><span id="line-117">import org.apache.hadoop.hbase.client.Put;</span> | 
|  | <span class="source-line-no">118</span><span id="line-118">import org.apache.hadoop.hbase.client.RegionInfo;</span> | 
|  | <span class="source-line-no">119</span><span id="line-119">import org.apache.hadoop.hbase.client.RegionInfoBuilder;</span> | 
|  | <span class="source-line-no">120</span><span id="line-120">import org.apache.hadoop.hbase.client.Result;</span> | 
|  | <span class="source-line-no">121</span><span id="line-121">import org.apache.hadoop.hbase.client.RowMutations;</span> | 
|  | <span class="source-line-no">122</span><span id="line-122">import org.apache.hadoop.hbase.client.Scan;</span> | 
|  | <span class="source-line-no">123</span><span id="line-123">import org.apache.hadoop.hbase.client.Table;</span> | 
|  | <span class="source-line-no">124</span><span id="line-124">import org.apache.hadoop.hbase.client.TableDescriptor;</span> | 
|  | <span class="source-line-no">125</span><span id="line-125">import org.apache.hadoop.hbase.client.TableDescriptorBuilder;</span> | 
|  | <span class="source-line-no">126</span><span id="line-126">import org.apache.hadoop.hbase.coprocessor.CoprocessorHost;</span> | 
|  | <span class="source-line-no">127</span><span id="line-127">import org.apache.hadoop.hbase.coprocessor.MetaTableMetrics;</span> | 
|  | <span class="source-line-no">128</span><span id="line-128">import org.apache.hadoop.hbase.coprocessor.RegionCoprocessor;</span> | 
|  | <span class="source-line-no">129</span><span id="line-129">import org.apache.hadoop.hbase.coprocessor.RegionObserver;</span> | 
|  | <span class="source-line-no">130</span><span id="line-130">import org.apache.hadoop.hbase.exceptions.FailedSanityCheckException;</span> | 
|  | <span class="source-line-no">131</span><span id="line-131">import org.apache.hadoop.hbase.filter.BigDecimalComparator;</span> | 
|  | <span class="source-line-no">132</span><span id="line-132">import org.apache.hadoop.hbase.filter.BinaryComparator;</span> | 
|  | <span class="source-line-no">133</span><span id="line-133">import org.apache.hadoop.hbase.filter.ColumnCountGetFilter;</span> | 
|  | <span class="source-line-no">134</span><span id="line-134">import org.apache.hadoop.hbase.filter.Filter;</span> | 
|  | <span class="source-line-no">135</span><span id="line-135">import org.apache.hadoop.hbase.filter.FilterBase;</span> | 
|  | <span class="source-line-no">136</span><span id="line-136">import org.apache.hadoop.hbase.filter.FilterList;</span> | 
|  | <span class="source-line-no">137</span><span id="line-137">import org.apache.hadoop.hbase.filter.NullComparator;</span> | 
|  | <span class="source-line-no">138</span><span id="line-138">import org.apache.hadoop.hbase.filter.PrefixFilter;</span> | 
|  | <span class="source-line-no">139</span><span id="line-139">import org.apache.hadoop.hbase.filter.SingleColumnValueExcludeFilter;</span> | 
|  | <span class="source-line-no">140</span><span id="line-140">import org.apache.hadoop.hbase.filter.SingleColumnValueFilter;</span> | 
|  | <span class="source-line-no">141</span><span id="line-141">import org.apache.hadoop.hbase.filter.SubstringComparator;</span> | 
|  | <span class="source-line-no">142</span><span id="line-142">import org.apache.hadoop.hbase.filter.ValueFilter;</span> | 
|  | <span class="source-line-no">143</span><span id="line-143">import org.apache.hadoop.hbase.io.TimeRange;</span> | 
|  | <span class="source-line-no">144</span><span id="line-144">import org.apache.hadoop.hbase.io.hfile.HFile;</span> | 
|  | <span class="source-line-no">145</span><span id="line-145">import org.apache.hadoop.hbase.monitoring.MonitoredRPCHandler;</span> | 
|  | <span class="source-line-no">146</span><span id="line-146">import org.apache.hadoop.hbase.monitoring.MonitoredTask;</span> | 
|  | <span class="source-line-no">147</span><span id="line-147">import org.apache.hadoop.hbase.monitoring.TaskMonitor;</span> | 
|  | <span class="source-line-no">148</span><span id="line-148">import org.apache.hadoop.hbase.regionserver.Region.Operation;</span> | 
|  | <span class="source-line-no">149</span><span id="line-149">import org.apache.hadoop.hbase.regionserver.Region.RowLock;</span> | 
|  | <span class="source-line-no">150</span><span id="line-150">import org.apache.hadoop.hbase.regionserver.TestHStore.FaultyFileSystem;</span> | 
|  | <span class="source-line-no">151</span><span id="line-151">import org.apache.hadoop.hbase.regionserver.compactions.CompactionRequestImpl;</span> | 
|  | <span class="source-line-no">152</span><span id="line-152">import org.apache.hadoop.hbase.regionserver.wal.AbstractFSWAL;</span> | 
|  | <span class="source-line-no">153</span><span id="line-153">import org.apache.hadoop.hbase.regionserver.wal.AsyncFSWAL;</span> | 
|  | <span class="source-line-no">154</span><span id="line-154">import org.apache.hadoop.hbase.regionserver.wal.FSHLog;</span> | 
|  | <span class="source-line-no">155</span><span id="line-155">import org.apache.hadoop.hbase.regionserver.wal.MetricsWALSource;</span> | 
|  | <span class="source-line-no">156</span><span id="line-156">import org.apache.hadoop.hbase.regionserver.wal.WALUtil;</span> | 
|  | <span class="source-line-no">157</span><span id="line-157">import org.apache.hadoop.hbase.replication.regionserver.ReplicationObserver;</span> | 
|  | <span class="source-line-no">158</span><span id="line-158">import org.apache.hadoop.hbase.security.User;</span> | 
|  | <span class="source-line-no">159</span><span id="line-159">import org.apache.hadoop.hbase.test.MetricsAssertHelper;</span> | 
|  | <span class="source-line-no">160</span><span id="line-160">import org.apache.hadoop.hbase.testclassification.LargeTests;</span> | 
|  | <span class="source-line-no">161</span><span id="line-161">import org.apache.hadoop.hbase.testclassification.VerySlowRegionServerTests;</span> | 
|  | <span class="source-line-no">162</span><span id="line-162">import org.apache.hadoop.hbase.util.Bytes;</span> | 
|  | <span class="source-line-no">163</span><span id="line-163">import org.apache.hadoop.hbase.util.CommonFSUtils;</span> | 
|  | <span class="source-line-no">164</span><span id="line-164">import org.apache.hadoop.hbase.util.EnvironmentEdgeManager;</span> | 
|  | <span class="source-line-no">165</span><span id="line-165">import org.apache.hadoop.hbase.util.EnvironmentEdgeManagerTestHelper;</span> | 
|  | <span class="source-line-no">166</span><span id="line-166">import org.apache.hadoop.hbase.util.HFileArchiveUtil;</span> | 
|  | <span class="source-line-no">167</span><span id="line-167">import org.apache.hadoop.hbase.util.IncrementingEnvironmentEdge;</span> | 
|  | <span class="source-line-no">168</span><span id="line-168">import org.apache.hadoop.hbase.util.ManualEnvironmentEdge;</span> | 
|  | <span class="source-line-no">169</span><span id="line-169">import org.apache.hadoop.hbase.util.Threads;</span> | 
|  | <span class="source-line-no">170</span><span id="line-170">import org.apache.hadoop.hbase.wal.AbstractFSWALProvider;</span> | 
|  | <span class="source-line-no">171</span><span id="line-171">import org.apache.hadoop.hbase.wal.FaultyFSLog;</span> | 
|  | <span class="source-line-no">172</span><span id="line-172">import org.apache.hadoop.hbase.wal.NettyAsyncFSWALConfigHelper;</span> | 
|  | <span class="source-line-no">173</span><span id="line-173">import org.apache.hadoop.hbase.wal.WAL;</span> | 
|  | <span class="source-line-no">174</span><span id="line-174">import org.apache.hadoop.hbase.wal.WALEdit;</span> | 
|  | <span class="source-line-no">175</span><span id="line-175">import org.apache.hadoop.hbase.wal.WALEditInternalHelper;</span> | 
|  | <span class="source-line-no">176</span><span id="line-176">import org.apache.hadoop.hbase.wal.WALFactory;</span> | 
|  | <span class="source-line-no">177</span><span id="line-177">import org.apache.hadoop.hbase.wal.WALKeyImpl;</span> | 
|  | <span class="source-line-no">178</span><span id="line-178">import org.apache.hadoop.hbase.wal.WALProvider;</span> | 
|  | <span class="source-line-no">179</span><span id="line-179">import org.apache.hadoop.hbase.wal.WALProvider.Writer;</span> | 
|  | <span class="source-line-no">180</span><span id="line-180">import org.apache.hadoop.hbase.wal.WALSplitUtil;</span> | 
|  | <span class="source-line-no">181</span><span id="line-181">import org.apache.hadoop.hbase.wal.WALStreamReader;</span> | 
|  | <span class="source-line-no">182</span><span id="line-182">import org.junit.After;</span> | 
|  | <span class="source-line-no">183</span><span id="line-183">import org.junit.Assert;</span> | 
|  | <span class="source-line-no">184</span><span id="line-184">import org.junit.Before;</span> | 
|  | <span class="source-line-no">185</span><span id="line-185">import org.junit.ClassRule;</span> | 
|  | <span class="source-line-no">186</span><span id="line-186">import org.junit.Ignore;</span> | 
|  | <span class="source-line-no">187</span><span id="line-187">import org.junit.Rule;</span> | 
|  | <span class="source-line-no">188</span><span id="line-188">import org.junit.Test;</span> | 
|  | <span class="source-line-no">189</span><span id="line-189">import org.junit.experimental.categories.Category;</span> | 
|  | <span class="source-line-no">190</span><span id="line-190">import org.junit.rules.ExpectedException;</span> | 
|  | <span class="source-line-no">191</span><span id="line-191">import org.junit.rules.TestName;</span> | 
|  | <span class="source-line-no">192</span><span id="line-192">import org.mockito.ArgumentCaptor;</span> | 
|  | <span class="source-line-no">193</span><span id="line-193">import org.mockito.ArgumentMatcher;</span> | 
|  | <span class="source-line-no">194</span><span id="line-194">import org.mockito.invocation.InvocationOnMock;</span> | 
|  | <span class="source-line-no">195</span><span id="line-195">import org.mockito.stubbing.Answer;</span> | 
|  | <span class="source-line-no">196</span><span id="line-196">import org.slf4j.Logger;</span> | 
|  | <span class="source-line-no">197</span><span id="line-197">import org.slf4j.LoggerFactory;</span> | 
|  | <span class="source-line-no">198</span><span id="line-198"></span> | 
|  | <span class="source-line-no">199</span><span id="line-199">import org.apache.hbase.thirdparty.com.google.common.collect.Lists;</span> | 
|  | <span class="source-line-no">200</span><span id="line-200">import org.apache.hbase.thirdparty.com.google.protobuf.ByteString;</span> | 
|  | <span class="source-line-no">201</span><span id="line-201">import org.apache.hbase.thirdparty.io.netty.channel.EventLoopGroup;</span> | 
|  | <span class="source-line-no">202</span><span id="line-202">import org.apache.hbase.thirdparty.io.netty.channel.nio.NioEventLoopGroup;</span> | 
|  | <span class="source-line-no">203</span><span id="line-203">import org.apache.hbase.thirdparty.io.netty.channel.socket.nio.NioSocketChannel;</span> | 
|  | <span class="source-line-no">204</span><span id="line-204"></span> | 
|  | <span class="source-line-no">205</span><span id="line-205">import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;</span> | 
|  | <span class="source-line-no">206</span><span id="line-206">import org.apache.hadoop.hbase.shaded.protobuf.generated.WALProtos.CompactionDescriptor;</span> | 
|  | <span class="source-line-no">207</span><span id="line-207">import org.apache.hadoop.hbase.shaded.protobuf.generated.WALProtos.FlushDescriptor;</span> | 
|  | <span class="source-line-no">208</span><span id="line-208">import org.apache.hadoop.hbase.shaded.protobuf.generated.WALProtos.FlushDescriptor.FlushAction;</span> | 
|  | <span class="source-line-no">209</span><span id="line-209">import org.apache.hadoop.hbase.shaded.protobuf.generated.WALProtos.FlushDescriptor.StoreFlushDescriptor;</span> | 
|  | <span class="source-line-no">210</span><span id="line-210">import org.apache.hadoop.hbase.shaded.protobuf.generated.WALProtos.RegionEventDescriptor;</span> | 
|  | <span class="source-line-no">211</span><span id="line-211">import org.apache.hadoop.hbase.shaded.protobuf.generated.WALProtos.StoreDescriptor;</span> | 
|  | <span class="source-line-no">212</span><span id="line-212"></span> | 
|  | <span class="source-line-no">213</span><span id="line-213">/**</span> | 
|  | <span class="source-line-no">214</span><span id="line-214"> * Basic stand-alone testing of HRegion. No clusters! A lot of the meta information for an HRegion</span> | 
|  | <span class="source-line-no">215</span><span id="line-215"> * now lives inside other HRegions or in the HBaseMaster, so only basic testing is possible.</span> | 
|  | <span class="source-line-no">216</span><span id="line-216"> */</span> | 
|  | <span class="source-line-no">217</span><span id="line-217">@Category({ VerySlowRegionServerTests.class, LargeTests.class })</span> | 
|  | <span class="source-line-no">218</span><span id="line-218">@SuppressWarnings("deprecation")</span> | 
|  | <span class="source-line-no">219</span><span id="line-219">public class TestHRegion {</span> | 
|  | <span class="source-line-no">220</span><span id="line-220"></span> | 
|  | <span class="source-line-no">221</span><span id="line-221">  @ClassRule</span> | 
|  | <span class="source-line-no">222</span><span id="line-222">  public static final HBaseClassTestRule CLASS_RULE =</span> | 
|  | <span class="source-line-no">223</span><span id="line-223">    HBaseClassTestRule.forClass(TestHRegion.class);</span> | 
|  | <span class="source-line-no">224</span><span id="line-224"></span> | 
|  | <span class="source-line-no">225</span><span id="line-225">  // Do not spin up clusters in here. If you need to spin up a cluster, do it</span> | 
|  | <span class="source-line-no">226</span><span id="line-226">  // over in TestHRegionOnCluster.</span> | 
|  | <span class="source-line-no">227</span><span id="line-227">  private static final Logger LOG = LoggerFactory.getLogger(TestHRegion.class);</span> | 
|  | <span class="source-line-no">228</span><span id="line-228">  @Rule</span> | 
|  | <span class="source-line-no">229</span><span id="line-229">  public TestName name = new TestName();</span> | 
|  | <span class="source-line-no">230</span><span id="line-230">  @Rule</span> | 
|  | <span class="source-line-no">231</span><span id="line-231">  public final ExpectedException thrown = ExpectedException.none();</span> | 
|  | <span class="source-line-no">232</span><span id="line-232"></span> | 
|  | <span class="source-line-no">233</span><span id="line-233">  private static final String COLUMN_FAMILY = "MyCF";</span> | 
|  | <span class="source-line-no">234</span><span id="line-234">  private static final byte[] COLUMN_FAMILY_BYTES = Bytes.toBytes(COLUMN_FAMILY);</span> | 
|  | <span class="source-line-no">235</span><span id="line-235">  private static final EventLoopGroup GROUP = new NioEventLoopGroup();</span> | 
|  | <span class="source-line-no">236</span><span id="line-236"></span> | 
|  | <span class="source-line-no">237</span><span id="line-237">  HRegion region = null;</span> | 
|  | <span class="source-line-no">238</span><span id="line-238">  // Do not run unit tests in parallel (? Why not? It don't work? Why not? St.Ack)</span> | 
|  | <span class="source-line-no">239</span><span id="line-239">  protected static HBaseTestingUtil TEST_UTIL;</span> | 
|  | <span class="source-line-no">240</span><span id="line-240">  public static Configuration CONF;</span> | 
|  | <span class="source-line-no">241</span><span id="line-241">  private String dir;</span> | 
|  | <span class="source-line-no">242</span><span id="line-242">  private final int MAX_VERSIONS = 2;</span> | 
|  | <span class="source-line-no">243</span><span id="line-243"></span> | 
|  | <span class="source-line-no">244</span><span id="line-244">  // Test names</span> | 
|  | <span class="source-line-no">245</span><span id="line-245">  protected TableName tableName;</span> | 
|  | <span class="source-line-no">246</span><span id="line-246">  protected String method;</span> | 
|  | <span class="source-line-no">247</span><span id="line-247">  protected final byte[] qual = Bytes.toBytes("qual");</span> | 
|  | <span class="source-line-no">248</span><span id="line-248">  protected final byte[] qual1 = Bytes.toBytes("qual1");</span> | 
|  | <span class="source-line-no">249</span><span id="line-249">  protected final byte[] qual2 = Bytes.toBytes("qual2");</span> | 
|  | <span class="source-line-no">250</span><span id="line-250">  protected final byte[] qual3 = Bytes.toBytes("qual3");</span> | 
|  | <span class="source-line-no">251</span><span id="line-251">  protected final byte[] value = Bytes.toBytes("value");</span> | 
|  | <span class="source-line-no">252</span><span id="line-252">  protected final byte[] value1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">253</span><span id="line-253">  protected final byte[] value2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">254</span><span id="line-254">  protected final byte[] row = Bytes.toBytes("rowA");</span> | 
|  | <span class="source-line-no">255</span><span id="line-255">  protected final byte[] row2 = Bytes.toBytes("rowB");</span> | 
|  | <span class="source-line-no">256</span><span id="line-256"></span> | 
|  | <span class="source-line-no">257</span><span id="line-257">  protected final MetricsAssertHelper metricsAssertHelper =</span> | 
|  | <span class="source-line-no">258</span><span id="line-258">    CompatibilitySingletonFactory.getInstance(MetricsAssertHelper.class);</span> | 
|  | <span class="source-line-no">259</span><span id="line-259"></span> | 
|  | <span class="source-line-no">260</span><span id="line-260">  @Before</span> | 
|  | <span class="source-line-no">261</span><span id="line-261">  public void setup() throws IOException {</span> | 
|  | <span class="source-line-no">262</span><span id="line-262">    TEST_UTIL = new HBaseTestingUtil();</span> | 
|  | <span class="source-line-no">263</span><span id="line-263">    CONF = TEST_UTIL.getConfiguration();</span> | 
|  | <span class="source-line-no">264</span><span id="line-264">    NettyAsyncFSWALConfigHelper.setEventLoopConfig(CONF, GROUP, NioSocketChannel.class);</span> | 
|  | <span class="source-line-no">265</span><span id="line-265">    dir = TEST_UTIL.getDataTestDir("TestHRegion").toString();</span> | 
|  | <span class="source-line-no">266</span><span id="line-266">    method = name.getMethodName();</span> | 
|  | <span class="source-line-no">267</span><span id="line-267">    tableName = TableName.valueOf(method);</span> | 
|  | <span class="source-line-no">268</span><span id="line-268">    CONF.set(CompactingMemStore.IN_MEMORY_FLUSH_THRESHOLD_FACTOR_KEY, String.valueOf(0.09));</span> | 
|  | <span class="source-line-no">269</span><span id="line-269">    CONF.setLong(AbstractFSWAL.WAL_SYNC_TIMEOUT_MS, 10000);</span> | 
|  | <span class="source-line-no">270</span><span id="line-270">  }</span> | 
|  | <span class="source-line-no">271</span><span id="line-271"></span> | 
|  | <span class="source-line-no">272</span><span id="line-272">  @After</span> | 
|  | <span class="source-line-no">273</span><span id="line-273">  public void tearDown() throws IOException {</span> | 
|  | <span class="source-line-no">274</span><span id="line-274">    // Region may have been closed, but it is still no harm if we close it again here using HTU.</span> | 
|  | <span class="source-line-no">275</span><span id="line-275">    HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">276</span><span id="line-276">    EnvironmentEdgeManagerTestHelper.reset();</span> | 
|  | <span class="source-line-no">277</span><span id="line-277">    LOG.info("Cleaning test directory: " + TEST_UTIL.getDataTestDir());</span> | 
|  | <span class="source-line-no">278</span><span id="line-278">    TEST_UTIL.cleanupTestDir();</span> | 
|  | <span class="source-line-no">279</span><span id="line-279">  }</span> | 
|  | <span class="source-line-no">280</span><span id="line-280"></span> | 
|  | <span class="source-line-no">281</span><span id="line-281">  /**</span> | 
|  | <span class="source-line-no">282</span><span id="line-282">   * Test that I can use the max flushed sequence id after the close.</span> | 
|  | <span class="source-line-no">283</span><span id="line-283">   */</span> | 
|  | <span class="source-line-no">284</span><span id="line-284">  @Test</span> | 
|  | <span class="source-line-no">285</span><span id="line-285">  public void testSequenceId() throws IOException {</span> | 
|  | <span class="source-line-no">286</span><span id="line-286">    region = initHRegion(tableName, method, CONF, COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">287</span><span id="line-287">    assertEquals(HConstants.NO_SEQNUM, region.getMaxFlushedSeqId());</span> | 
|  | <span class="source-line-no">288</span><span id="line-288">    // Weird. This returns 0 if no store files or no edits. Afraid to change it.</span> | 
|  | <span class="source-line-no">289</span><span id="line-289">    assertEquals(0, (long) region.getMaxStoreSeqId().get(COLUMN_FAMILY_BYTES));</span> | 
|  | <span class="source-line-no">290</span><span id="line-290">    HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">291</span><span id="line-291">    assertEquals(HConstants.NO_SEQNUM, region.getMaxFlushedSeqId());</span> | 
|  | <span class="source-line-no">292</span><span id="line-292">    assertEquals(0, (long) region.getMaxStoreSeqId().get(COLUMN_FAMILY_BYTES));</span> | 
|  | <span class="source-line-no">293</span><span id="line-293">    HRegion oldRegion = region;</span> | 
|  | <span class="source-line-no">294</span><span id="line-294">    try {</span> | 
|  | <span class="source-line-no">295</span><span id="line-295">      // Open region again.</span> | 
|  | <span class="source-line-no">296</span><span id="line-296">      region = initHRegion(tableName, method, CONF, COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">297</span><span id="line-297">      byte[] value = Bytes.toBytes(method);</span> | 
|  | <span class="source-line-no">298</span><span id="line-298">      // Make a random put against our cf.</span> | 
|  | <span class="source-line-no">299</span><span id="line-299">      Put put = new Put(value);</span> | 
|  | <span class="source-line-no">300</span><span id="line-300">      put.addColumn(COLUMN_FAMILY_BYTES, null, value);</span> | 
|  | <span class="source-line-no">301</span><span id="line-301">      region.put(put);</span> | 
|  | <span class="source-line-no">302</span><span id="line-302">      // No flush yet so init numbers should still be in place.</span> | 
|  | <span class="source-line-no">303</span><span id="line-303">      assertEquals(HConstants.NO_SEQNUM, region.getMaxFlushedSeqId());</span> | 
|  | <span class="source-line-no">304</span><span id="line-304">      assertEquals(0, (long) region.getMaxStoreSeqId().get(COLUMN_FAMILY_BYTES));</span> | 
|  | <span class="source-line-no">305</span><span id="line-305">      region.flush(true);</span> | 
|  | <span class="source-line-no">306</span><span id="line-306">      long max = region.getMaxFlushedSeqId();</span> | 
|  | <span class="source-line-no">307</span><span id="line-307">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">308</span><span id="line-308">      assertEquals(max, region.getMaxFlushedSeqId());</span> | 
|  | <span class="source-line-no">309</span><span id="line-309">      this.region = null;</span> | 
|  | <span class="source-line-no">310</span><span id="line-310">    } finally {</span> | 
|  | <span class="source-line-no">311</span><span id="line-311">      HBaseTestingUtil.closeRegionAndWAL(oldRegion);</span> | 
|  | <span class="source-line-no">312</span><span id="line-312">    }</span> | 
|  | <span class="source-line-no">313</span><span id="line-313">  }</span> | 
|  | <span class="source-line-no">314</span><span id="line-314"></span> | 
|  | <span class="source-line-no">315</span><span id="line-315">  /**</span> | 
|  | <span class="source-line-no">316</span><span id="line-316">   * Test for Bug 2 of HBASE-10466. "Bug 2: Conditions for the first flush of region close</span> | 
|  | <span class="source-line-no">317</span><span id="line-317">   * (so-called pre-flush) If memstoreSize is smaller than a certain value, or when region close</span> | 
|  | <span class="source-line-no">318</span><span id="line-318">   * starts a flush is ongoing, the first flush is skipped and only the second flush takes place.</span> | 
|  | <span class="source-line-no">319</span><span id="line-319">   * However, two flushes are required in case previous flush fails and leaves some data in</span> | 
|  | <span class="source-line-no">320</span><span id="line-320">   * snapshot. The bug could cause loss of data in current memstore. The fix is removing all</span> | 
|  | <span class="source-line-no">321</span><span id="line-321">   * conditions except abort check so we ensure 2 flushes for region close."</span> | 
|  | <span class="source-line-no">322</span><span id="line-322">   */</span> | 
|  | <span class="source-line-no">323</span><span id="line-323">  @Test</span> | 
|  | <span class="source-line-no">324</span><span id="line-324">  public void testCloseCarryingSnapshot() throws IOException {</span> | 
|  | <span class="source-line-no">325</span><span id="line-325">    region = initHRegion(tableName, method, CONF, COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">326</span><span id="line-326">    HStore store = region.getStore(COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">327</span><span id="line-327">    // Get some random bytes.</span> | 
|  | <span class="source-line-no">328</span><span id="line-328">    byte[] value = Bytes.toBytes(method);</span> | 
|  | <span class="source-line-no">329</span><span id="line-329">    // Make a random put against our cf.</span> | 
|  | <span class="source-line-no">330</span><span id="line-330">    Put put = new Put(value);</span> | 
|  | <span class="source-line-no">331</span><span id="line-331">    put.addColumn(COLUMN_FAMILY_BYTES, null, value);</span> | 
|  | <span class="source-line-no">332</span><span id="line-332">    // First put something in current memstore, which will be in snapshot after flusher.prepare()</span> | 
|  | <span class="source-line-no">333</span><span id="line-333">    region.put(put);</span> | 
|  | <span class="source-line-no">334</span><span id="line-334">    StoreFlushContext storeFlushCtx = store.createFlushContext(12345, FlushLifeCycleTracker.DUMMY);</span> | 
|  | <span class="source-line-no">335</span><span id="line-335">    storeFlushCtx.prepare();</span> | 
|  | <span class="source-line-no">336</span><span id="line-336">    // Second put something in current memstore</span> | 
|  | <span class="source-line-no">337</span><span id="line-337">    put.addColumn(COLUMN_FAMILY_BYTES, Bytes.toBytes("abc"), value);</span> | 
|  | <span class="source-line-no">338</span><span id="line-338">    region.put(put);</span> | 
|  | <span class="source-line-no">339</span><span id="line-339">    // Close with something in memstore and something in the snapshot. Make sure all is cleared.</span> | 
|  | <span class="source-line-no">340</span><span id="line-340">    HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">341</span><span id="line-341">    assertEquals(0, region.getMemStoreDataSize());</span> | 
|  | <span class="source-line-no">342</span><span id="line-342">    region = null;</span> | 
|  | <span class="source-line-no">343</span><span id="line-343">  }</span> | 
|  | <span class="source-line-no">344</span><span id="line-344"></span> | 
|  | <span class="source-line-no">345</span><span id="line-345">  /*</span> | 
|  | <span class="source-line-no">346</span><span id="line-346">   * This test is for verifying memstore snapshot size is correctly updated in case of rollback See</span> | 
|  | <span class="source-line-no">347</span><span id="line-347">   * HBASE-10845</span> | 
|  | <span class="source-line-no">348</span><span id="line-348">   */</span> | 
|  | <span class="source-line-no">349</span><span id="line-349">  @Test</span> | 
|  | <span class="source-line-no">350</span><span id="line-350">  public void testMemstoreSnapshotSize() throws IOException {</span> | 
|  | <span class="source-line-no">351</span><span id="line-351">    class MyFaultyFSLog extends FaultyFSLog {</span> | 
|  | <span class="source-line-no">352</span><span id="line-352">      StoreFlushContext storeFlushCtx;</span> | 
|  | <span class="source-line-no">353</span><span id="line-353"></span> | 
|  | <span class="source-line-no">354</span><span id="line-354">      public MyFaultyFSLog(FileSystem fs, Path rootDir, String logName, Configuration conf)</span> | 
|  | <span class="source-line-no">355</span><span id="line-355">        throws IOException {</span> | 
|  | <span class="source-line-no">356</span><span id="line-356">        super(fs, rootDir, logName, conf);</span> | 
|  | <span class="source-line-no">357</span><span id="line-357">      }</span> | 
|  | <span class="source-line-no">358</span><span id="line-358"></span> | 
|  | <span class="source-line-no">359</span><span id="line-359">      void setStoreFlushCtx(StoreFlushContext storeFlushCtx) {</span> | 
|  | <span class="source-line-no">360</span><span id="line-360">        this.storeFlushCtx = storeFlushCtx;</span> | 
|  | <span class="source-line-no">361</span><span id="line-361">      }</span> | 
|  | <span class="source-line-no">362</span><span id="line-362"></span> | 
|  | <span class="source-line-no">363</span><span id="line-363">      @Override</span> | 
|  | <span class="source-line-no">364</span><span id="line-364">      protected void doSync(long txid, boolean forceSync) throws IOException {</span> | 
|  | <span class="source-line-no">365</span><span id="line-365">        storeFlushCtx.prepare();</span> | 
|  | <span class="source-line-no">366</span><span id="line-366">        super.doSync(txid, forceSync);</span> | 
|  | <span class="source-line-no">367</span><span id="line-367">      }</span> | 
|  | <span class="source-line-no">368</span><span id="line-368">    }</span> | 
|  | <span class="source-line-no">369</span><span id="line-369"></span> | 
|  | <span class="source-line-no">370</span><span id="line-370">    FileSystem fs = FileSystem.get(CONF);</span> | 
|  | <span class="source-line-no">371</span><span id="line-371">    Path rootDir = new Path(dir + "testMemstoreSnapshotSize");</span> | 
|  | <span class="source-line-no">372</span><span id="line-372">    MyFaultyFSLog faultyLog = new MyFaultyFSLog(fs, rootDir, "testMemstoreSnapshotSize", CONF);</span> | 
|  | <span class="source-line-no">373</span><span id="line-373">    faultyLog.init();</span> | 
|  | <span class="source-line-no">374</span><span id="line-374">    region = initHRegion(tableName, null, null, CONF, false, Durability.SYNC_WAL, faultyLog,</span> | 
|  | <span class="source-line-no">375</span><span id="line-375">      COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">376</span><span id="line-376"></span> | 
|  | <span class="source-line-no">377</span><span id="line-377">    HStore store = region.getStore(COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">378</span><span id="line-378">    // Get some random bytes.</span> | 
|  | <span class="source-line-no">379</span><span id="line-379">    byte[] value = Bytes.toBytes(method);</span> | 
|  | <span class="source-line-no">380</span><span id="line-380">    faultyLog.setStoreFlushCtx(store.createFlushContext(12345, FlushLifeCycleTracker.DUMMY));</span> | 
|  | <span class="source-line-no">381</span><span id="line-381"></span> | 
|  | <span class="source-line-no">382</span><span id="line-382">    Put put = new Put(value);</span> | 
|  | <span class="source-line-no">383</span><span id="line-383">    put.addColumn(COLUMN_FAMILY_BYTES, Bytes.toBytes("abc"), value);</span> | 
|  | <span class="source-line-no">384</span><span id="line-384">    faultyLog.setFailureType(FaultyFSLog.FailureType.SYNC);</span> | 
|  | <span class="source-line-no">385</span><span id="line-385">    boolean threwIOE = false;</span> | 
|  | <span class="source-line-no">386</span><span id="line-386">    try {</span> | 
|  | <span class="source-line-no">387</span><span id="line-387">      region.put(put);</span> | 
|  | <span class="source-line-no">388</span><span id="line-388">    } catch (IOException ioe) {</span> | 
|  | <span class="source-line-no">389</span><span id="line-389">      threwIOE = true;</span> | 
|  | <span class="source-line-no">390</span><span id="line-390">    } finally {</span> | 
|  | <span class="source-line-no">391</span><span id="line-391">      assertTrue("The regionserver should have thrown an exception", threwIOE);</span> | 
|  | <span class="source-line-no">392</span><span id="line-392">    }</span> | 
|  | <span class="source-line-no">393</span><span id="line-393">    MemStoreSize mss = store.getFlushableSize();</span> | 
|  | <span class="source-line-no">394</span><span id="line-394">    assertTrue("flushable size should be zero, but it is " + mss, mss.getDataSize() == 0);</span> | 
|  | <span class="source-line-no">395</span><span id="line-395">  }</span> | 
|  | <span class="source-line-no">396</span><span id="line-396"></span> | 
|  | <span class="source-line-no">397</span><span id="line-397">  /**</span> | 
|  | <span class="source-line-no">398</span><span id="line-398">   * Create a WAL outside of the usual helper in</span> | 
|  | <span class="source-line-no">399</span><span id="line-399">   * {@link HBaseTestingUtil#createWal(Configuration, Path, RegionInfo)} because that method doesn't</span> | 
|  | <span class="source-line-no">400</span><span id="line-400">   * play nicely with FaultyFileSystem. Call this method before overriding {@code fs.file.impl}.</span> | 
|  | <span class="source-line-no">401</span><span id="line-401">   * @param callingMethod a unique component for the path, probably the name of the test method.</span> | 
|  | <span class="source-line-no">402</span><span id="line-402">   */</span> | 
|  | <span class="source-line-no">403</span><span id="line-403">  private static WAL createWALCompatibleWithFaultyFileSystem(String callingMethod,</span> | 
|  | <span class="source-line-no">404</span><span id="line-404">    Configuration conf, TableName tableName) throws IOException {</span> | 
|  | <span class="source-line-no">405</span><span id="line-405">    final Path logDir = TEST_UTIL.getDataTestDirOnTestFS(callingMethod + ".log");</span> | 
|  | <span class="source-line-no">406</span><span id="line-406">    final Configuration walConf = new Configuration(conf);</span> | 
|  | <span class="source-line-no">407</span><span id="line-407">    CommonFSUtils.setRootDir(walConf, logDir);</span> | 
|  | <span class="source-line-no">408</span><span id="line-408">    return new WALFactory(walConf, callingMethod)</span> | 
|  | <span class="source-line-no">409</span><span id="line-409">      .getWAL(RegionInfoBuilder.newBuilder(tableName).build());</span> | 
|  | <span class="source-line-no">410</span><span id="line-410">  }</span> | 
|  | <span class="source-line-no">411</span><span id="line-411"></span> | 
|  | <span class="source-line-no">412</span><span id="line-412">  @Test</span> | 
|  | <span class="source-line-no">413</span><span id="line-413">  public void testMemstoreSizeAccountingWithFailedPostBatchMutate() throws IOException {</span> | 
|  | <span class="source-line-no">414</span><span id="line-414">    String testName = "testMemstoreSizeAccountingWithFailedPostBatchMutate";</span> | 
|  | <span class="source-line-no">415</span><span id="line-415">    FileSystem fs = FileSystem.get(CONF);</span> | 
|  | <span class="source-line-no">416</span><span id="line-416">    Path rootDir = new Path(dir + testName);</span> | 
|  | <span class="source-line-no">417</span><span id="line-417">    FSHLog hLog = new FSHLog(fs, rootDir, testName, CONF);</span> | 
|  | <span class="source-line-no">418</span><span id="line-418">    hLog.init();</span> | 
|  | <span class="source-line-no">419</span><span id="line-419">    region = initHRegion(tableName, null, null, CONF, false, Durability.SYNC_WAL, hLog,</span> | 
|  | <span class="source-line-no">420</span><span id="line-420">      COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">421</span><span id="line-421">    HStore store = region.getStore(COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">422</span><span id="line-422">    assertEquals(0, region.getMemStoreDataSize());</span> | 
|  | <span class="source-line-no">423</span><span id="line-423"></span> | 
|  | <span class="source-line-no">424</span><span id="line-424">    // Put one value</span> | 
|  | <span class="source-line-no">425</span><span id="line-425">    byte[] value = Bytes.toBytes(method);</span> | 
|  | <span class="source-line-no">426</span><span id="line-426">    Put put = new Put(value);</span> | 
|  | <span class="source-line-no">427</span><span id="line-427">    put.addColumn(COLUMN_FAMILY_BYTES, Bytes.toBytes("abc"), value);</span> | 
|  | <span class="source-line-no">428</span><span id="line-428">    region.put(put);</span> | 
|  | <span class="source-line-no">429</span><span id="line-429">    long onePutSize = region.getMemStoreDataSize();</span> | 
|  | <span class="source-line-no">430</span><span id="line-430">    assertTrue(onePutSize > 0);</span> | 
|  | <span class="source-line-no">431</span><span id="line-431"></span> | 
|  | <span class="source-line-no">432</span><span id="line-432">    RegionCoprocessorHost mockedCPHost = mock(RegionCoprocessorHost.class);</span> | 
|  | <span class="source-line-no">433</span><span id="line-433">    doThrow(new IOException()).when(mockedCPHost).postBatchMutate(any());</span> | 
|  | <span class="source-line-no">434</span><span id="line-434">    region.setCoprocessorHost(mockedCPHost);</span> | 
|  | <span class="source-line-no">435</span><span id="line-435"></span> | 
|  | <span class="source-line-no">436</span><span id="line-436">    put = new Put(value);</span> | 
|  | <span class="source-line-no">437</span><span id="line-437">    put.addColumn(COLUMN_FAMILY_BYTES, Bytes.toBytes("dfg"), value);</span> | 
|  | <span class="source-line-no">438</span><span id="line-438">    try {</span> | 
|  | <span class="source-line-no">439</span><span id="line-439">      region.put(put);</span> | 
|  | <span class="source-line-no">440</span><span id="line-440">      fail("Should have failed with IOException");</span> | 
|  | <span class="source-line-no">441</span><span id="line-441">    } catch (IOException expected) {</span> | 
|  | <span class="source-line-no">442</span><span id="line-442">    }</span> | 
|  | <span class="source-line-no">443</span><span id="line-443">    long expectedSize = onePutSize * 2;</span> | 
|  | <span class="source-line-no">444</span><span id="line-444">    assertEquals("memstoreSize should be incremented", expectedSize, region.getMemStoreDataSize());</span> | 
|  | <span class="source-line-no">445</span><span id="line-445">    assertEquals("flushable size should be incremented", expectedSize,</span> | 
|  | <span class="source-line-no">446</span><span id="line-446">      store.getFlushableSize().getDataSize());</span> | 
|  | <span class="source-line-no">447</span><span id="line-447"></span> | 
|  | <span class="source-line-no">448</span><span id="line-448">    region.setCoprocessorHost(null);</span> | 
|  | <span class="source-line-no">449</span><span id="line-449">  }</span> | 
|  | <span class="source-line-no">450</span><span id="line-450"></span> | 
|  | <span class="source-line-no">451</span><span id="line-451">  /**</span> | 
|  | <span class="source-line-no">452</span><span id="line-452">   * A test case of HBASE-21041</span> | 
|  | <span class="source-line-no">453</span><span id="line-453">   */</span> | 
|  | <span class="source-line-no">454</span><span id="line-454">  @Test</span> | 
|  | <span class="source-line-no">455</span><span id="line-455">  public void testFlushAndMemstoreSizeCounting() throws Exception {</span> | 
|  | <span class="source-line-no">456</span><span id="line-456">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">457</span><span id="line-457">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">458</span><span id="line-458">    for (byte[] row : HBaseTestingUtil.ROWS) {</span> | 
|  | <span class="source-line-no">459</span><span id="line-459">      Put put = new Put(row);</span> | 
|  | <span class="source-line-no">460</span><span id="line-460">      put.addColumn(family, family, row);</span> | 
|  | <span class="source-line-no">461</span><span id="line-461">      region.put(put);</span> | 
|  | <span class="source-line-no">462</span><span id="line-462">    }</span> | 
|  | <span class="source-line-no">463</span><span id="line-463">    region.flush(true);</span> | 
|  | <span class="source-line-no">464</span><span id="line-464">    // After flush, data size should be zero</span> | 
|  | <span class="source-line-no">465</span><span id="line-465">    assertEquals(0, region.getMemStoreDataSize());</span> | 
|  | <span class="source-line-no">466</span><span id="line-466">    // After flush, a new active mutable segment is created, so the heap size</span> | 
|  | <span class="source-line-no">467</span><span id="line-467">    // should equal to MutableSegment.DEEP_OVERHEAD</span> | 
|  | <span class="source-line-no">468</span><span id="line-468">    assertEquals(MutableSegment.DEEP_OVERHEAD, region.getMemStoreHeapSize());</span> | 
|  | <span class="source-line-no">469</span><span id="line-469">    // After flush, offheap should be zero</span> | 
|  | <span class="source-line-no">470</span><span id="line-470">    assertEquals(0, region.getMemStoreOffHeapSize());</span> | 
|  | <span class="source-line-no">471</span><span id="line-471">  }</span> | 
|  | <span class="source-line-no">472</span><span id="line-472"></span> | 
|  | <span class="source-line-no">473</span><span id="line-473">  /**</span> | 
|  | <span class="source-line-no">474</span><span id="line-474">   * Test we do not lose data if we fail a flush and then close. Part of HBase-10466. Tests the</span> | 
|  | <span class="source-line-no">475</span><span id="line-475">   * following from the issue description: "Bug 1: Wrong calculation of HRegion.memstoreSize: When a</span> | 
|  | <span class="source-line-no">476</span><span id="line-476">   * flush fails, data to be flushed is kept in each MemStore's snapshot and wait for next flush</span> | 
|  | <span class="source-line-no">477</span><span id="line-477">   * attempt to continue on it. But when the next flush succeeds, the counter of total memstore size</span> | 
|  | <span class="source-line-no">478</span><span id="line-478">   * in HRegion is always deduced by the sum of current memstore sizes instead of snapshots left</span> | 
|  | <span class="source-line-no">479</span><span id="line-479">   * from previous failed flush. This calculation is problematic that almost every time there is</span> | 
|  | <span class="source-line-no">480</span><span id="line-480">   * failed flush, HRegion.memstoreSize gets reduced by a wrong value. If region flush could not</span> | 
|  | <span class="source-line-no">481</span><span id="line-481">   * proceed for a couple cycles, the size in current memstore could be much larger than the</span> | 
|  | <span class="source-line-no">482</span><span id="line-482">   * snapshot. It's likely to drift memstoreSize much smaller than expected. In extreme case, if the</span> | 
|  | <span class="source-line-no">483</span><span id="line-483">   * error accumulates to even bigger than HRegion's memstore size limit, any further flush is</span> | 
|  | <span class="source-line-no">484</span><span id="line-484">   * skipped because flush does not do anything if memstoreSize is not larger than 0."</span> | 
|  | <span class="source-line-no">485</span><span id="line-485">   */</span> | 
|  | <span class="source-line-no">486</span><span id="line-486">  @Test</span> | 
|  | <span class="source-line-no">487</span><span id="line-487">  public void testFlushSizeAccounting() throws Exception {</span> | 
|  | <span class="source-line-no">488</span><span id="line-488">    final Configuration conf = HBaseConfiguration.create(CONF);</span> | 
|  | <span class="source-line-no">489</span><span id="line-489">    final WAL wal = createWALCompatibleWithFaultyFileSystem(method, conf, tableName);</span> | 
|  | <span class="source-line-no">490</span><span id="line-490">    // Only retry once.</span> | 
|  | <span class="source-line-no">491</span><span id="line-491">    conf.setInt("hbase.hstore.flush.retries.number", 1);</span> | 
|  | <span class="source-line-no">492</span><span id="line-492">    final User user = User.createUserForTesting(conf, method, new String[] { "foo" });</span> | 
|  | <span class="source-line-no">493</span><span id="line-493">    // Inject our faulty LocalFileSystem</span> | 
|  | <span class="source-line-no">494</span><span id="line-494">    conf.setClass("fs.file.impl", FaultyFileSystem.class, FileSystem.class);</span> | 
|  | <span class="source-line-no">495</span><span id="line-495">    user.runAs(new PrivilegedExceptionAction<Object>() {</span> | 
|  | <span class="source-line-no">496</span><span id="line-496">      @Override</span> | 
|  | <span class="source-line-no">497</span><span id="line-497">      public Object run() throws Exception {</span> | 
|  | <span class="source-line-no">498</span><span id="line-498">        // Make sure it worked (above is sensitive to caching details in hadoop core)</span> | 
|  | <span class="source-line-no">499</span><span id="line-499">        FileSystem fs = FileSystem.get(conf);</span> | 
|  | <span class="source-line-no">500</span><span id="line-500">        Assert.assertEquals(FaultyFileSystem.class, fs.getClass());</span> | 
|  | <span class="source-line-no">501</span><span id="line-501">        FaultyFileSystem ffs = (FaultyFileSystem) fs;</span> | 
|  | <span class="source-line-no">502</span><span id="line-502">        HRegion region = null;</span> | 
|  | <span class="source-line-no">503</span><span id="line-503">        try {</span> | 
|  | <span class="source-line-no">504</span><span id="line-504">          // Initialize region</span> | 
|  | <span class="source-line-no">505</span><span id="line-505">          region = initHRegion(tableName, null, null, CONF, false, Durability.SYNC_WAL, wal,</span> | 
|  | <span class="source-line-no">506</span><span id="line-506">            COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">507</span><span id="line-507">          long size = region.getMemStoreDataSize();</span> | 
|  | <span class="source-line-no">508</span><span id="line-508">          Assert.assertEquals(0, size);</span> | 
|  | <span class="source-line-no">509</span><span id="line-509">          // Put one item into memstore. Measure the size of one item in memstore.</span> | 
|  | <span class="source-line-no">510</span><span id="line-510">          Put p1 = new Put(row);</span> | 
|  | <span class="source-line-no">511</span><span id="line-511">          p1.add(new KeyValue(row, COLUMN_FAMILY_BYTES, qual1, 1, (byte[]) null));</span> | 
|  | <span class="source-line-no">512</span><span id="line-512">          region.put(p1);</span> | 
|  | <span class="source-line-no">513</span><span id="line-513">          final long sizeOfOnePut = region.getMemStoreDataSize();</span> | 
|  | <span class="source-line-no">514</span><span id="line-514">          // Fail a flush which means the current memstore will hang out as memstore 'snapshot'.</span> | 
|  | <span class="source-line-no">515</span><span id="line-515">          try {</span> | 
|  | <span class="source-line-no">516</span><span id="line-516">            LOG.info("Flushing");</span> | 
|  | <span class="source-line-no">517</span><span id="line-517">            region.flush(true);</span> | 
|  | <span class="source-line-no">518</span><span id="line-518">            Assert.fail("Didn't bubble up IOE!");</span> | 
|  | <span class="source-line-no">519</span><span id="line-519">          } catch (DroppedSnapshotException dse) {</span> | 
|  | <span class="source-line-no">520</span><span id="line-520">            // What we are expecting</span> | 
|  | <span class="source-line-no">521</span><span id="line-521">            region.closing.set(false); // this is needed for the rest of the test to work</span> | 
|  | <span class="source-line-no">522</span><span id="line-522">          }</span> | 
|  | <span class="source-line-no">523</span><span id="line-523">          // Make it so all writes succeed from here on out</span> | 
|  | <span class="source-line-no">524</span><span id="line-524">          ffs.fault.set(false);</span> | 
|  | <span class="source-line-no">525</span><span id="line-525">          // Check sizes. Should still be the one entry.</span> | 
|  | <span class="source-line-no">526</span><span id="line-526">          Assert.assertEquals(sizeOfOnePut, region.getMemStoreDataSize());</span> | 
|  | <span class="source-line-no">527</span><span id="line-527">          // Now add two entries so that on this next flush that fails, we can see if we</span> | 
|  | <span class="source-line-no">528</span><span id="line-528">          // subtract the right amount, the snapshot size only.</span> | 
|  | <span class="source-line-no">529</span><span id="line-529">          Put p2 = new Put(row);</span> | 
|  | <span class="source-line-no">530</span><span id="line-530">          p2.add(new KeyValue(row, COLUMN_FAMILY_BYTES, qual2, 2, (byte[]) null));</span> | 
|  | <span class="source-line-no">531</span><span id="line-531">          p2.add(new KeyValue(row, COLUMN_FAMILY_BYTES, qual3, 3, (byte[]) null));</span> | 
|  | <span class="source-line-no">532</span><span id="line-532">          region.put(p2);</span> | 
|  | <span class="source-line-no">533</span><span id="line-533">          long expectedSize = sizeOfOnePut * 3;</span> | 
|  | <span class="source-line-no">534</span><span id="line-534">          Assert.assertEquals(expectedSize, region.getMemStoreDataSize());</span> | 
|  | <span class="source-line-no">535</span><span id="line-535">          // Do a successful flush. It will clear the snapshot only. Thats how flushes work.</span> | 
|  | <span class="source-line-no">536</span><span id="line-536">          // If already a snapshot, we clear it else we move the memstore to be snapshot and flush</span> | 
|  | <span class="source-line-no">537</span><span id="line-537">          // it</span> | 
|  | <span class="source-line-no">538</span><span id="line-538">          region.flush(true);</span> | 
|  | <span class="source-line-no">539</span><span id="line-539">          // Make sure our memory accounting is right.</span> | 
|  | <span class="source-line-no">540</span><span id="line-540">          Assert.assertEquals(sizeOfOnePut * 2, region.getMemStoreDataSize());</span> | 
|  | <span class="source-line-no">541</span><span id="line-541">        } finally {</span> | 
|  | <span class="source-line-no">542</span><span id="line-542">          HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">543</span><span id="line-543">        }</span> | 
|  | <span class="source-line-no">544</span><span id="line-544">        return null;</span> | 
|  | <span class="source-line-no">545</span><span id="line-545">      }</span> | 
|  | <span class="source-line-no">546</span><span id="line-546">    });</span> | 
|  | <span class="source-line-no">547</span><span id="line-547">    FileSystem.closeAllForUGI(user.getUGI());</span> | 
|  | <span class="source-line-no">548</span><span id="line-548">  }</span> | 
|  | <span class="source-line-no">549</span><span id="line-549"></span> | 
|  | <span class="source-line-no">550</span><span id="line-550">  @Test</span> | 
|  | <span class="source-line-no">551</span><span id="line-551">  public void testCloseWithFailingFlush() throws Exception {</span> | 
|  | <span class="source-line-no">552</span><span id="line-552">    final Configuration conf = HBaseConfiguration.create(CONF);</span> | 
|  | <span class="source-line-no">553</span><span id="line-553">    final WAL wal = createWALCompatibleWithFaultyFileSystem(method, conf, tableName);</span> | 
|  | <span class="source-line-no">554</span><span id="line-554">    // Only retry once.</span> | 
|  | <span class="source-line-no">555</span><span id="line-555">    conf.setInt("hbase.hstore.flush.retries.number", 1);</span> | 
|  | <span class="source-line-no">556</span><span id="line-556">    final User user = User.createUserForTesting(conf, this.method, new String[] { "foo" });</span> | 
|  | <span class="source-line-no">557</span><span id="line-557">    // Inject our faulty LocalFileSystem</span> | 
|  | <span class="source-line-no">558</span><span id="line-558">    conf.setClass("fs.file.impl", FaultyFileSystem.class, FileSystem.class);</span> | 
|  | <span class="source-line-no">559</span><span id="line-559">    user.runAs(new PrivilegedExceptionAction<Object>() {</span> | 
|  | <span class="source-line-no">560</span><span id="line-560">      @Override</span> | 
|  | <span class="source-line-no">561</span><span id="line-561">      public Object run() throws Exception {</span> | 
|  | <span class="source-line-no">562</span><span id="line-562">        // Make sure it worked (above is sensitive to caching details in hadoop core)</span> | 
|  | <span class="source-line-no">563</span><span id="line-563">        FileSystem fs = FileSystem.get(conf);</span> | 
|  | <span class="source-line-no">564</span><span id="line-564">        Assert.assertEquals(FaultyFileSystem.class, fs.getClass());</span> | 
|  | <span class="source-line-no">565</span><span id="line-565">        FaultyFileSystem ffs = (FaultyFileSystem) fs;</span> | 
|  | <span class="source-line-no">566</span><span id="line-566">        HRegion region = null;</span> | 
|  | <span class="source-line-no">567</span><span id="line-567">        try {</span> | 
|  | <span class="source-line-no">568</span><span id="line-568">          // Initialize region</span> | 
|  | <span class="source-line-no">569</span><span id="line-569">          region = initHRegion(tableName, null, null, CONF, false, Durability.SYNC_WAL, wal,</span> | 
|  | <span class="source-line-no">570</span><span id="line-570">            COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">571</span><span id="line-571">          long size = region.getMemStoreDataSize();</span> | 
|  | <span class="source-line-no">572</span><span id="line-572">          Assert.assertEquals(0, size);</span> | 
|  | <span class="source-line-no">573</span><span id="line-573">          // Put one item into memstore. Measure the size of one item in memstore.</span> | 
|  | <span class="source-line-no">574</span><span id="line-574">          Put p1 = new Put(row);</span> | 
|  | <span class="source-line-no">575</span><span id="line-575">          p1.add(new KeyValue(row, COLUMN_FAMILY_BYTES, qual1, 1, (byte[]) null));</span> | 
|  | <span class="source-line-no">576</span><span id="line-576">          region.put(p1);</span> | 
|  | <span class="source-line-no">577</span><span id="line-577">          // Manufacture an outstanding snapshot -- fake a failed flush by doing prepare step only.</span> | 
|  | <span class="source-line-no">578</span><span id="line-578">          HStore store = region.getStore(COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">579</span><span id="line-579">          StoreFlushContext storeFlushCtx =</span> | 
|  | <span class="source-line-no">580</span><span id="line-580">            store.createFlushContext(12345, FlushLifeCycleTracker.DUMMY);</span> | 
|  | <span class="source-line-no">581</span><span id="line-581">          storeFlushCtx.prepare();</span> | 
|  | <span class="source-line-no">582</span><span id="line-582">          // Now add two entries to the foreground memstore.</span> | 
|  | <span class="source-line-no">583</span><span id="line-583">          Put p2 = new Put(row);</span> | 
|  | <span class="source-line-no">584</span><span id="line-584">          p2.add(new KeyValue(row, COLUMN_FAMILY_BYTES, qual2, 2, (byte[]) null));</span> | 
|  | <span class="source-line-no">585</span><span id="line-585">          p2.add(new KeyValue(row, COLUMN_FAMILY_BYTES, qual3, 3, (byte[]) null));</span> | 
|  | <span class="source-line-no">586</span><span id="line-586">          region.put(p2);</span> | 
|  | <span class="source-line-no">587</span><span id="line-587">          // Now try close on top of a failing flush.</span> | 
|  | <span class="source-line-no">588</span><span id="line-588">          HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">589</span><span id="line-589">          region = null;</span> | 
|  | <span class="source-line-no">590</span><span id="line-590">          fail();</span> | 
|  | <span class="source-line-no">591</span><span id="line-591">        } catch (DroppedSnapshotException dse) {</span> | 
|  | <span class="source-line-no">592</span><span id="line-592">          // Expected</span> | 
|  | <span class="source-line-no">593</span><span id="line-593">          LOG.info("Expected DroppedSnapshotException");</span> | 
|  | <span class="source-line-no">594</span><span id="line-594">        } finally {</span> | 
|  | <span class="source-line-no">595</span><span id="line-595">          // Make it so all writes succeed from here on out so can close clean</span> | 
|  | <span class="source-line-no">596</span><span id="line-596">          ffs.fault.set(false);</span> | 
|  | <span class="source-line-no">597</span><span id="line-597">          HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">598</span><span id="line-598">        }</span> | 
|  | <span class="source-line-no">599</span><span id="line-599">        return null;</span> | 
|  | <span class="source-line-no">600</span><span id="line-600">      }</span> | 
|  | <span class="source-line-no">601</span><span id="line-601">    });</span> | 
|  | <span class="source-line-no">602</span><span id="line-602">    FileSystem.closeAllForUGI(user.getUGI());</span> | 
|  | <span class="source-line-no">603</span><span id="line-603">  }</span> | 
|  | <span class="source-line-no">604</span><span id="line-604"></span> | 
|  | <span class="source-line-no">605</span><span id="line-605">  @Test</span> | 
|  | <span class="source-line-no">606</span><span id="line-606">  public void testCompactionAffectedByScanners() throws Exception {</span> | 
|  | <span class="source-line-no">607</span><span id="line-607">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">608</span><span id="line-608">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">609</span><span id="line-609"></span> | 
|  | <span class="source-line-no">610</span><span id="line-610">    Put put = new Put(Bytes.toBytes("r1"));</span> | 
|  | <span class="source-line-no">611</span><span id="line-611">    put.addColumn(family, Bytes.toBytes("q1"), Bytes.toBytes("v1"));</span> | 
|  | <span class="source-line-no">612</span><span id="line-612">    region.put(put);</span> | 
|  | <span class="source-line-no">613</span><span id="line-613">    region.flush(true);</span> | 
|  | <span class="source-line-no">614</span><span id="line-614"></span> | 
|  | <span class="source-line-no">615</span><span id="line-615">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">616</span><span id="line-616">    scan.readVersions(3);</span> | 
|  | <span class="source-line-no">617</span><span id="line-617">    // open the first scanner</span> | 
|  | <span class="source-line-no">618</span><span id="line-618">    try (RegionScanner scanner1 = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">619</span><span id="line-619">      Delete delete = new Delete(Bytes.toBytes("r1"));</span> | 
|  | <span class="source-line-no">620</span><span id="line-620">      region.delete(delete);</span> | 
|  | <span class="source-line-no">621</span><span id="line-621">      region.flush(true);</span> | 
|  | <span class="source-line-no">622</span><span id="line-622">      // open the second scanner</span> | 
|  | <span class="source-line-no">623</span><span id="line-623">      try (RegionScanner scanner2 = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">624</span><span id="line-624">        List<Cell> results = new ArrayList<>();</span> | 
|  | <span class="source-line-no">625</span><span id="line-625"></span> | 
|  | <span class="source-line-no">626</span><span id="line-626">        LOG.info("Smallest read point:" + region.getSmallestReadPoint());</span> | 
|  | <span class="source-line-no">627</span><span id="line-627"></span> | 
|  | <span class="source-line-no">628</span><span id="line-628">        // make a major compaction</span> | 
|  | <span class="source-line-no">629</span><span id="line-629">        region.compact(true);</span> | 
|  | <span class="source-line-no">630</span><span id="line-630"></span> | 
|  | <span class="source-line-no">631</span><span id="line-631">        // open the third scanner</span> | 
|  | <span class="source-line-no">632</span><span id="line-632">        try (RegionScanner scanner3 = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">633</span><span id="line-633">          // get data from scanner 1, 2, 3 after major compaction</span> | 
|  | <span class="source-line-no">634</span><span id="line-634">          scanner1.next(results);</span> | 
|  | <span class="source-line-no">635</span><span id="line-635">          LOG.info(results.toString());</span> | 
|  | <span class="source-line-no">636</span><span id="line-636">          assertEquals(1, results.size());</span> | 
|  | <span class="source-line-no">637</span><span id="line-637"></span> | 
|  | <span class="source-line-no">638</span><span id="line-638">          results.clear();</span> | 
|  | <span class="source-line-no">639</span><span id="line-639">          scanner2.next(results);</span> | 
|  | <span class="source-line-no">640</span><span id="line-640">          LOG.info(results.toString());</span> | 
|  | <span class="source-line-no">641</span><span id="line-641">          assertEquals(0, results.size());</span> | 
|  | <span class="source-line-no">642</span><span id="line-642"></span> | 
|  | <span class="source-line-no">643</span><span id="line-643">          results.clear();</span> | 
|  | <span class="source-line-no">644</span><span id="line-644">          scanner3.next(results);</span> | 
|  | <span class="source-line-no">645</span><span id="line-645">          LOG.info(results.toString());</span> | 
|  | <span class="source-line-no">646</span><span id="line-646">          assertEquals(0, results.size());</span> | 
|  | <span class="source-line-no">647</span><span id="line-647">        }</span> | 
|  | <span class="source-line-no">648</span><span id="line-648">      }</span> | 
|  | <span class="source-line-no">649</span><span id="line-649">    }</span> | 
|  | <span class="source-line-no">650</span><span id="line-650">  }</span> | 
|  | <span class="source-line-no">651</span><span id="line-651"></span> | 
|  | <span class="source-line-no">652</span><span id="line-652">  @Test</span> | 
|  | <span class="source-line-no">653</span><span id="line-653">  public void testToShowNPEOnRegionScannerReseek() throws Exception {</span> | 
|  | <span class="source-line-no">654</span><span id="line-654">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">655</span><span id="line-655">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">656</span><span id="line-656"></span> | 
|  | <span class="source-line-no">657</span><span id="line-657">    Put put = new Put(Bytes.toBytes("r1"));</span> | 
|  | <span class="source-line-no">658</span><span id="line-658">    put.addColumn(family, Bytes.toBytes("q1"), Bytes.toBytes("v1"));</span> | 
|  | <span class="source-line-no">659</span><span id="line-659">    region.put(put);</span> | 
|  | <span class="source-line-no">660</span><span id="line-660">    put = new Put(Bytes.toBytes("r2"));</span> | 
|  | <span class="source-line-no">661</span><span id="line-661">    put.addColumn(family, Bytes.toBytes("q1"), Bytes.toBytes("v1"));</span> | 
|  | <span class="source-line-no">662</span><span id="line-662">    region.put(put);</span> | 
|  | <span class="source-line-no">663</span><span id="line-663">    region.flush(true);</span> | 
|  | <span class="source-line-no">664</span><span id="line-664"></span> | 
|  | <span class="source-line-no">665</span><span id="line-665">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">666</span><span id="line-666">    scan.readVersions(3);</span> | 
|  | <span class="source-line-no">667</span><span id="line-667">    // open the first scanner</span> | 
|  | <span class="source-line-no">668</span><span id="line-668">    try (RegionScanner scanner1 = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">669</span><span id="line-669">      LOG.info("Smallest read point:" + region.getSmallestReadPoint());</span> | 
|  | <span class="source-line-no">670</span><span id="line-670"></span> | 
|  | <span class="source-line-no">671</span><span id="line-671">      region.compact(true);</span> | 
|  | <span class="source-line-no">672</span><span id="line-672"></span> | 
|  | <span class="source-line-no">673</span><span id="line-673">      scanner1.reseek(Bytes.toBytes("r2"));</span> | 
|  | <span class="source-line-no">674</span><span id="line-674">      List<Cell> results = new ArrayList<>();</span> | 
|  | <span class="source-line-no">675</span><span id="line-675">      scanner1.next(results);</span> | 
|  | <span class="source-line-no">676</span><span id="line-676">      Cell keyValue = results.get(0);</span> | 
|  | <span class="source-line-no">677</span><span id="line-677">      assertTrue(Bytes.compareTo(CellUtil.cloneRow(keyValue), Bytes.toBytes("r2")) == 0);</span> | 
|  | <span class="source-line-no">678</span><span id="line-678">      scanner1.close();</span> | 
|  | <span class="source-line-no">679</span><span id="line-679">    }</span> | 
|  | <span class="source-line-no">680</span><span id="line-680">  }</span> | 
|  | <span class="source-line-no">681</span><span id="line-681"></span> | 
|  | <span class="source-line-no">682</span><span id="line-682">  @Test</span> | 
|  | <span class="source-line-no">683</span><span id="line-683">  public void testArchiveRecoveredEditsReplay() throws Exception {</span> | 
|  | <span class="source-line-no">684</span><span id="line-684">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">685</span><span id="line-685">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">686</span><span id="line-686">    final WALFactory wals = new WALFactory(CONF, method);</span> | 
|  | <span class="source-line-no">687</span><span id="line-687">    try {</span> | 
|  | <span class="source-line-no">688</span><span id="line-688">      Path regiondir = region.getRegionFileSystem().getRegionDir();</span> | 
|  | <span class="source-line-no">689</span><span id="line-689">      FileSystem fs = region.getRegionFileSystem().getFileSystem();</span> | 
|  | <span class="source-line-no">690</span><span id="line-690">      byte[] regionName = region.getRegionInfo().getEncodedNameAsBytes();</span> | 
|  | <span class="source-line-no">691</span><span id="line-691"></span> | 
|  | <span class="source-line-no">692</span><span id="line-692">      Path recoveredEditsDir = WALSplitUtil.getRegionDirRecoveredEditsDir(regiondir);</span> | 
|  | <span class="source-line-no">693</span><span id="line-693"></span> | 
|  | <span class="source-line-no">694</span><span id="line-694">      long maxSeqId = 1050;</span> | 
|  | <span class="source-line-no">695</span><span id="line-695">      long minSeqId = 1000;</span> | 
|  | <span class="source-line-no">696</span><span id="line-696"></span> | 
|  | <span class="source-line-no">697</span><span id="line-697">      for (long i = minSeqId; i <= maxSeqId; i += 10) {</span> | 
|  | <span class="source-line-no">698</span><span id="line-698">        Path recoveredEdits = new Path(recoveredEditsDir, String.format("%019d", i));</span> | 
|  | <span class="source-line-no">699</span><span id="line-699">        fs.create(recoveredEdits);</span> | 
|  | <span class="source-line-no">700</span><span id="line-700">        WALProvider.Writer writer = wals.createRecoveredEditsWriter(fs, recoveredEdits);</span> | 
|  | <span class="source-line-no">701</span><span id="line-701"></span> | 
|  | <span class="source-line-no">702</span><span id="line-702">        long time = System.nanoTime();</span> | 
|  | <span class="source-line-no">703</span><span id="line-703">        WALEdit edit = new WALEdit();</span> | 
|  | <span class="source-line-no">704</span><span id="line-704">        WALEditInternalHelper.addExtendedCell(edit,</span> | 
|  | <span class="source-line-no">705</span><span id="line-705">          new KeyValue(row, family, Bytes.toBytes(i), time, KeyValue.Type.Put, Bytes.toBytes(i)));</span> | 
|  | <span class="source-line-no">706</span><span id="line-706">        writer.append(new WAL.Entry(</span> | 
|  | <span class="source-line-no">707</span><span id="line-707">          new WALKeyImpl(regionName, tableName, i, time, HConstants.DEFAULT_CLUSTER_ID), edit));</span> | 
|  | <span class="source-line-no">708</span><span id="line-708"></span> | 
|  | <span class="source-line-no">709</span><span id="line-709">        writer.close();</span> | 
|  | <span class="source-line-no">710</span><span id="line-710">      }</span> | 
|  | <span class="source-line-no">711</span><span id="line-711">      MonitoredTask status = TaskMonitor.get().createStatus(method);</span> | 
|  | <span class="source-line-no">712</span><span id="line-712">      Map<byte[], Long> maxSeqIdInStores = new TreeMap<>(Bytes.BYTES_COMPARATOR);</span> | 
|  | <span class="source-line-no">713</span><span id="line-713">      for (HStore store : region.getStores()) {</span> | 
|  | <span class="source-line-no">714</span><span id="line-714">        maxSeqIdInStores.put(Bytes.toBytes(store.getColumnFamilyName()), minSeqId - 1);</span> | 
|  | <span class="source-line-no">715</span><span id="line-715">      }</span> | 
|  | <span class="source-line-no">716</span><span id="line-716">      CONF.set("hbase.region.archive.recovered.edits", "true");</span> | 
|  | <span class="source-line-no">717</span><span id="line-717">      CONF.set(CommonFSUtils.HBASE_WAL_DIR, "/custom_wal_dir");</span> | 
|  | <span class="source-line-no">718</span><span id="line-718">      long seqId = region.replayRecoveredEditsIfAny(maxSeqIdInStores, null, status);</span> | 
|  | <span class="source-line-no">719</span><span id="line-719">      assertEquals(maxSeqId, seqId);</span> | 
|  | <span class="source-line-no">720</span><span id="line-720">      region.getMVCC().advanceTo(seqId);</span> | 
|  | <span class="source-line-no">721</span><span id="line-721">      String fakeFamilyName = recoveredEditsDir.getName();</span> | 
|  | <span class="source-line-no">722</span><span id="line-722">      Path rootDir = new Path(CONF.get(HConstants.HBASE_DIR));</span> | 
|  | <span class="source-line-no">723</span><span id="line-723">      Path storeArchiveDir = HFileArchiveUtil.getStoreArchivePathForRootDir(rootDir,</span> | 
|  | <span class="source-line-no">724</span><span id="line-724">        region.getRegionInfo(), Bytes.toBytes(fakeFamilyName));</span> | 
|  | <span class="source-line-no">725</span><span id="line-725">      FileStatus[] list = TEST_UTIL.getTestFileSystem().listStatus(storeArchiveDir);</span> | 
|  | <span class="source-line-no">726</span><span id="line-726">      assertEquals(6, list.length);</span> | 
|  | <span class="source-line-no">727</span><span id="line-727">    } finally {</span> | 
|  | <span class="source-line-no">728</span><span id="line-728">      CONF.set("hbase.region.archive.recovered.edits", "false");</span> | 
|  | <span class="source-line-no">729</span><span id="line-729">      CONF.set(CommonFSUtils.HBASE_WAL_DIR, "");</span> | 
|  | <span class="source-line-no">730</span><span id="line-730">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">731</span><span id="line-731">      this.region = null;</span> | 
|  | <span class="source-line-no">732</span><span id="line-732">      wals.close();</span> | 
|  | <span class="source-line-no">733</span><span id="line-733">    }</span> | 
|  | <span class="source-line-no">734</span><span id="line-734">  }</span> | 
|  | <span class="source-line-no">735</span><span id="line-735"></span> | 
|  | <span class="source-line-no">736</span><span id="line-736">  @Test</span> | 
|  | <span class="source-line-no">737</span><span id="line-737">  public void testSkipRecoveredEditsReplay() throws Exception {</span> | 
|  | <span class="source-line-no">738</span><span id="line-738">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">739</span><span id="line-739">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">740</span><span id="line-740">    final WALFactory wals = new WALFactory(CONF, method);</span> | 
|  | <span class="source-line-no">741</span><span id="line-741">    try {</span> | 
|  | <span class="source-line-no">742</span><span id="line-742">      Path regiondir = region.getRegionFileSystem().getRegionDir();</span> | 
|  | <span class="source-line-no">743</span><span id="line-743">      FileSystem fs = region.getRegionFileSystem().getFileSystem();</span> | 
|  | <span class="source-line-no">744</span><span id="line-744">      byte[] regionName = region.getRegionInfo().getEncodedNameAsBytes();</span> | 
|  | <span class="source-line-no">745</span><span id="line-745"></span> | 
|  | <span class="source-line-no">746</span><span id="line-746">      Path recoveredEditsDir = WALSplitUtil.getRegionDirRecoveredEditsDir(regiondir);</span> | 
|  | <span class="source-line-no">747</span><span id="line-747"></span> | 
|  | <span class="source-line-no">748</span><span id="line-748">      long maxSeqId = 1050;</span> | 
|  | <span class="source-line-no">749</span><span id="line-749">      long minSeqId = 1000;</span> | 
|  | <span class="source-line-no">750</span><span id="line-750"></span> | 
|  | <span class="source-line-no">751</span><span id="line-751">      for (long i = minSeqId; i <= maxSeqId; i += 10) {</span> | 
|  | <span class="source-line-no">752</span><span id="line-752">        Path recoveredEdits = new Path(recoveredEditsDir, String.format("%019d", i));</span> | 
|  | <span class="source-line-no">753</span><span id="line-753">        fs.create(recoveredEdits);</span> | 
|  | <span class="source-line-no">754</span><span id="line-754">        WALProvider.Writer writer = wals.createRecoveredEditsWriter(fs, recoveredEdits);</span> | 
|  | <span class="source-line-no">755</span><span id="line-755"></span> | 
|  | <span class="source-line-no">756</span><span id="line-756">        long time = System.nanoTime();</span> | 
|  | <span class="source-line-no">757</span><span id="line-757">        WALEdit edit = new WALEdit();</span> | 
|  | <span class="source-line-no">758</span><span id="line-758">        WALEditInternalHelper.addExtendedCell(edit,</span> | 
|  | <span class="source-line-no">759</span><span id="line-759">          new KeyValue(row, family, Bytes.toBytes(i), time, KeyValue.Type.Put, Bytes.toBytes(i)));</span> | 
|  | <span class="source-line-no">760</span><span id="line-760">        writer.append(new WAL.Entry(</span> | 
|  | <span class="source-line-no">761</span><span id="line-761">          new WALKeyImpl(regionName, tableName, i, time, HConstants.DEFAULT_CLUSTER_ID), edit));</span> | 
|  | <span class="source-line-no">762</span><span id="line-762"></span> | 
|  | <span class="source-line-no">763</span><span id="line-763">        writer.close();</span> | 
|  | <span class="source-line-no">764</span><span id="line-764">      }</span> | 
|  | <span class="source-line-no">765</span><span id="line-765">      MonitoredTask status = TaskMonitor.get().createStatus(method);</span> | 
|  | <span class="source-line-no">766</span><span id="line-766">      Map<byte[], Long> maxSeqIdInStores = new TreeMap<>(Bytes.BYTES_COMPARATOR);</span> | 
|  | <span class="source-line-no">767</span><span id="line-767">      for (HStore store : region.getStores()) {</span> | 
|  | <span class="source-line-no">768</span><span id="line-768">        maxSeqIdInStores.put(Bytes.toBytes(store.getColumnFamilyName()), minSeqId - 1);</span> | 
|  | <span class="source-line-no">769</span><span id="line-769">      }</span> | 
|  | <span class="source-line-no">770</span><span id="line-770">      long seqId = region.replayRecoveredEditsIfAny(maxSeqIdInStores, null, status);</span> | 
|  | <span class="source-line-no">771</span><span id="line-771">      assertEquals(maxSeqId, seqId);</span> | 
|  | <span class="source-line-no">772</span><span id="line-772">      region.getMVCC().advanceTo(seqId);</span> | 
|  | <span class="source-line-no">773</span><span id="line-773">      Get get = new Get(row);</span> | 
|  | <span class="source-line-no">774</span><span id="line-774">      Result result = region.get(get);</span> | 
|  | <span class="source-line-no">775</span><span id="line-775">      for (long i = minSeqId; i <= maxSeqId; i += 10) {</span> | 
|  | <span class="source-line-no">776</span><span id="line-776">        List<Cell> kvs = result.getColumnCells(family, Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">777</span><span id="line-777">        assertEquals(1, kvs.size());</span> | 
|  | <span class="source-line-no">778</span><span id="line-778">        assertArrayEquals(Bytes.toBytes(i), CellUtil.cloneValue(kvs.get(0)));</span> | 
|  | <span class="source-line-no">779</span><span id="line-779">      }</span> | 
|  | <span class="source-line-no">780</span><span id="line-780">    } finally {</span> | 
|  | <span class="source-line-no">781</span><span id="line-781">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">782</span><span id="line-782">      this.region = null;</span> | 
|  | <span class="source-line-no">783</span><span id="line-783">      wals.close();</span> | 
|  | <span class="source-line-no">784</span><span id="line-784">    }</span> | 
|  | <span class="source-line-no">785</span><span id="line-785">  }</span> | 
|  | <span class="source-line-no">786</span><span id="line-786"></span> | 
|  | <span class="source-line-no">787</span><span id="line-787">  @Test</span> | 
|  | <span class="source-line-no">788</span><span id="line-788">  public void testSkipRecoveredEditsReplaySomeIgnored() throws Exception {</span> | 
|  | <span class="source-line-no">789</span><span id="line-789">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">790</span><span id="line-790">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">791</span><span id="line-791">    final WALFactory wals = new WALFactory(CONF, method);</span> | 
|  | <span class="source-line-no">792</span><span id="line-792">    try {</span> | 
|  | <span class="source-line-no">793</span><span id="line-793">      Path regiondir = region.getRegionFileSystem().getRegionDir();</span> | 
|  | <span class="source-line-no">794</span><span id="line-794">      FileSystem fs = region.getRegionFileSystem().getFileSystem();</span> | 
|  | <span class="source-line-no">795</span><span id="line-795">      byte[] regionName = region.getRegionInfo().getEncodedNameAsBytes();</span> | 
|  | <span class="source-line-no">796</span><span id="line-796"></span> | 
|  | <span class="source-line-no">797</span><span id="line-797">      Path recoveredEditsDir = WALSplitUtil.getRegionDirRecoveredEditsDir(regiondir);</span> | 
|  | <span class="source-line-no">798</span><span id="line-798"></span> | 
|  | <span class="source-line-no">799</span><span id="line-799">      long maxSeqId = 1050;</span> | 
|  | <span class="source-line-no">800</span><span id="line-800">      long minSeqId = 1000;</span> | 
|  | <span class="source-line-no">801</span><span id="line-801"></span> | 
|  | <span class="source-line-no">802</span><span id="line-802">      for (long i = minSeqId; i <= maxSeqId; i += 10) {</span> | 
|  | <span class="source-line-no">803</span><span id="line-803">        Path recoveredEdits = new Path(recoveredEditsDir, String.format("%019d", i));</span> | 
|  | <span class="source-line-no">804</span><span id="line-804">        fs.create(recoveredEdits);</span> | 
|  | <span class="source-line-no">805</span><span id="line-805">        WALProvider.Writer writer = wals.createRecoveredEditsWriter(fs, recoveredEdits);</span> | 
|  | <span class="source-line-no">806</span><span id="line-806"></span> | 
|  | <span class="source-line-no">807</span><span id="line-807">        long time = System.nanoTime();</span> | 
|  | <span class="source-line-no">808</span><span id="line-808">        WALEdit edit = new WALEdit();</span> | 
|  | <span class="source-line-no">809</span><span id="line-809">        WALEditInternalHelper.addExtendedCell(edit,</span> | 
|  | <span class="source-line-no">810</span><span id="line-810">          new KeyValue(row, family, Bytes.toBytes(i), time, KeyValue.Type.Put, Bytes.toBytes(i)));</span> | 
|  | <span class="source-line-no">811</span><span id="line-811">        writer.append(new WAL.Entry(</span> | 
|  | <span class="source-line-no">812</span><span id="line-812">          new WALKeyImpl(regionName, tableName, i, time, HConstants.DEFAULT_CLUSTER_ID), edit));</span> | 
|  | <span class="source-line-no">813</span><span id="line-813"></span> | 
|  | <span class="source-line-no">814</span><span id="line-814">        writer.close();</span> | 
|  | <span class="source-line-no">815</span><span id="line-815">      }</span> | 
|  | <span class="source-line-no">816</span><span id="line-816">      long recoverSeqId = 1030;</span> | 
|  | <span class="source-line-no">817</span><span id="line-817">      MonitoredTask status = TaskMonitor.get().createStatus(method);</span> | 
|  | <span class="source-line-no">818</span><span id="line-818">      Map<byte[], Long> maxSeqIdInStores = new TreeMap<>(Bytes.BYTES_COMPARATOR);</span> | 
|  | <span class="source-line-no">819</span><span id="line-819">      for (HStore store : region.getStores()) {</span> | 
|  | <span class="source-line-no">820</span><span id="line-820">        maxSeqIdInStores.put(Bytes.toBytes(store.getColumnFamilyName()), recoverSeqId - 1);</span> | 
|  | <span class="source-line-no">821</span><span id="line-821">      }</span> | 
|  | <span class="source-line-no">822</span><span id="line-822">      long seqId = region.replayRecoveredEditsIfAny(maxSeqIdInStores, null, status);</span> | 
|  | <span class="source-line-no">823</span><span id="line-823">      assertEquals(maxSeqId, seqId);</span> | 
|  | <span class="source-line-no">824</span><span id="line-824">      region.getMVCC().advanceTo(seqId);</span> | 
|  | <span class="source-line-no">825</span><span id="line-825">      Get get = new Get(row);</span> | 
|  | <span class="source-line-no">826</span><span id="line-826">      Result result = region.get(get);</span> | 
|  | <span class="source-line-no">827</span><span id="line-827">      for (long i = minSeqId; i <= maxSeqId; i += 10) {</span> | 
|  | <span class="source-line-no">828</span><span id="line-828">        List<Cell> kvs = result.getColumnCells(family, Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">829</span><span id="line-829">        if (i < recoverSeqId) {</span> | 
|  | <span class="source-line-no">830</span><span id="line-830">          assertEquals(0, kvs.size());</span> | 
|  | <span class="source-line-no">831</span><span id="line-831">        } else {</span> | 
|  | <span class="source-line-no">832</span><span id="line-832">          assertEquals(1, kvs.size());</span> | 
|  | <span class="source-line-no">833</span><span id="line-833">          assertArrayEquals(Bytes.toBytes(i), CellUtil.cloneValue(kvs.get(0)));</span> | 
|  | <span class="source-line-no">834</span><span id="line-834">        }</span> | 
|  | <span class="source-line-no">835</span><span id="line-835">      }</span> | 
|  | <span class="source-line-no">836</span><span id="line-836">    } finally {</span> | 
|  | <span class="source-line-no">837</span><span id="line-837">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">838</span><span id="line-838">      this.region = null;</span> | 
|  | <span class="source-line-no">839</span><span id="line-839">      wals.close();</span> | 
|  | <span class="source-line-no">840</span><span id="line-840">    }</span> | 
|  | <span class="source-line-no">841</span><span id="line-841">  }</span> | 
|  | <span class="source-line-no">842</span><span id="line-842"></span> | 
|  | <span class="source-line-no">843</span><span id="line-843">  @Test</span> | 
|  | <span class="source-line-no">844</span><span id="line-844">  public void testSkipRecoveredEditsReplayAllIgnored() throws Exception {</span> | 
|  | <span class="source-line-no">845</span><span id="line-845">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">846</span><span id="line-846">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">847</span><span id="line-847">    Path regiondir = region.getRegionFileSystem().getRegionDir();</span> | 
|  | <span class="source-line-no">848</span><span id="line-848">    FileSystem fs = region.getRegionFileSystem().getFileSystem();</span> | 
|  | <span class="source-line-no">849</span><span id="line-849"></span> | 
|  | <span class="source-line-no">850</span><span id="line-850">    Path recoveredEditsDir = WALSplitUtil.getRegionDirRecoveredEditsDir(regiondir);</span> | 
|  | <span class="source-line-no">851</span><span id="line-851">    for (int i = 1000; i < 1050; i += 10) {</span> | 
|  | <span class="source-line-no">852</span><span id="line-852">      Path recoveredEdits = new Path(recoveredEditsDir, String.format("%019d", i));</span> | 
|  | <span class="source-line-no">853</span><span id="line-853">      FSDataOutputStream dos = fs.create(recoveredEdits);</span> | 
|  | <span class="source-line-no">854</span><span id="line-854">      dos.writeInt(i);</span> | 
|  | <span class="source-line-no">855</span><span id="line-855">      dos.close();</span> | 
|  | <span class="source-line-no">856</span><span id="line-856">    }</span> | 
|  | <span class="source-line-no">857</span><span id="line-857">    long minSeqId = 2000;</span> | 
|  | <span class="source-line-no">858</span><span id="line-858">    Path recoveredEdits = new Path(recoveredEditsDir, String.format("%019d", minSeqId - 1));</span> | 
|  | <span class="source-line-no">859</span><span id="line-859">    FSDataOutputStream dos = fs.create(recoveredEdits);</span> | 
|  | <span class="source-line-no">860</span><span id="line-860">    dos.close();</span> | 
|  | <span class="source-line-no">861</span><span id="line-861"></span> | 
|  | <span class="source-line-no">862</span><span id="line-862">    Map<byte[], Long> maxSeqIdInStores = new TreeMap<>(Bytes.BYTES_COMPARATOR);</span> | 
|  | <span class="source-line-no">863</span><span id="line-863">    for (HStore store : region.getStores()) {</span> | 
|  | <span class="source-line-no">864</span><span id="line-864">      maxSeqIdInStores.put(Bytes.toBytes(store.getColumnFamilyName()), minSeqId);</span> | 
|  | <span class="source-line-no">865</span><span id="line-865">    }</span> | 
|  | <span class="source-line-no">866</span><span id="line-866">    long seqId = region.replayRecoveredEditsIfAny(maxSeqIdInStores, null, null);</span> | 
|  | <span class="source-line-no">867</span><span id="line-867">    assertEquals(minSeqId, seqId);</span> | 
|  | <span class="source-line-no">868</span><span id="line-868">  }</span> | 
|  | <span class="source-line-no">869</span><span id="line-869"></span> | 
|  | <span class="source-line-no">870</span><span id="line-870">  @Test</span> | 
|  | <span class="source-line-no">871</span><span id="line-871">  public void testSkipRecoveredEditsReplayTheLastFileIgnored() throws Exception {</span> | 
|  | <span class="source-line-no">872</span><span id="line-872">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">873</span><span id="line-873">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">874</span><span id="line-874">    final WALFactory wals = new WALFactory(CONF, method);</span> | 
|  | <span class="source-line-no">875</span><span id="line-875">    try {</span> | 
|  | <span class="source-line-no">876</span><span id="line-876">      Path regiondir = region.getRegionFileSystem().getRegionDir();</span> | 
|  | <span class="source-line-no">877</span><span id="line-877">      FileSystem fs = region.getRegionFileSystem().getFileSystem();</span> | 
|  | <span class="source-line-no">878</span><span id="line-878">      byte[] regionName = region.getRegionInfo().getEncodedNameAsBytes();</span> | 
|  | <span class="source-line-no">879</span><span id="line-879">      byte[][] columns = region.getTableDescriptor().getColumnFamilyNames().toArray(new byte[0][]);</span> | 
|  | <span class="source-line-no">880</span><span id="line-880"></span> | 
|  | <span class="source-line-no">881</span><span id="line-881">      assertEquals(0, region.getStoreFileList(columns).size());</span> | 
|  | <span class="source-line-no">882</span><span id="line-882"></span> | 
|  | <span class="source-line-no">883</span><span id="line-883">      Path recoveredEditsDir = WALSplitUtil.getRegionDirRecoveredEditsDir(regiondir);</span> | 
|  | <span class="source-line-no">884</span><span id="line-884"></span> | 
|  | <span class="source-line-no">885</span><span id="line-885">      long maxSeqId = 1050;</span> | 
|  | <span class="source-line-no">886</span><span id="line-886">      long minSeqId = 1000;</span> | 
|  | <span class="source-line-no">887</span><span id="line-887"></span> | 
|  | <span class="source-line-no">888</span><span id="line-888">      for (long i = minSeqId; i <= maxSeqId; i += 10) {</span> | 
|  | <span class="source-line-no">889</span><span id="line-889">        Path recoveredEdits = new Path(recoveredEditsDir, String.format("%019d", i));</span> | 
|  | <span class="source-line-no">890</span><span id="line-890">        fs.create(recoveredEdits);</span> | 
|  | <span class="source-line-no">891</span><span id="line-891">        WALProvider.Writer writer = wals.createRecoveredEditsWriter(fs, recoveredEdits);</span> | 
|  | <span class="source-line-no">892</span><span id="line-892"></span> | 
|  | <span class="source-line-no">893</span><span id="line-893">        long time = System.nanoTime();</span> | 
|  | <span class="source-line-no">894</span><span id="line-894">        WALEdit edit = null;</span> | 
|  | <span class="source-line-no">895</span><span id="line-895">        if (i == maxSeqId) {</span> | 
|  | <span class="source-line-no">896</span><span id="line-896">          edit = WALEdit.createCompaction(region.getRegionInfo(),</span> | 
|  | <span class="source-line-no">897</span><span id="line-897">            CompactionDescriptor.newBuilder().setTableName(ByteString.copyFrom(tableName.getName()))</span> | 
|  | <span class="source-line-no">898</span><span id="line-898">              .setFamilyName(ByteString.copyFrom(regionName))</span> | 
|  | <span class="source-line-no">899</span><span id="line-899">              .setEncodedRegionName(ByteString.copyFrom(regionName))</span> | 
|  | <span class="source-line-no">900</span><span id="line-900">              .setStoreHomeDirBytes(ByteString.copyFrom(Bytes.toBytes(regiondir.toString())))</span> | 
|  | <span class="source-line-no">901</span><span id="line-901">              .setRegionName(ByteString.copyFrom(region.getRegionInfo().getRegionName())).build());</span> | 
|  | <span class="source-line-no">902</span><span id="line-902">        } else {</span> | 
|  | <span class="source-line-no">903</span><span id="line-903">          edit = new WALEdit();</span> | 
|  | <span class="source-line-no">904</span><span id="line-904">          WALEditInternalHelper.addExtendedCell(edit,</span> | 
|  | <span class="source-line-no">905</span><span id="line-905">            new KeyValue(row, family, Bytes.toBytes(i), time, KeyValue.Type.Put, Bytes.toBytes(i)));</span> | 
|  | <span class="source-line-no">906</span><span id="line-906">        }</span> | 
|  | <span class="source-line-no">907</span><span id="line-907">        writer.append(new WAL.Entry(</span> | 
|  | <span class="source-line-no">908</span><span id="line-908">          new WALKeyImpl(regionName, tableName, i, time, HConstants.DEFAULT_CLUSTER_ID), edit));</span> | 
|  | <span class="source-line-no">909</span><span id="line-909">        writer.close();</span> | 
|  | <span class="source-line-no">910</span><span id="line-910">      }</span> | 
|  | <span class="source-line-no">911</span><span id="line-911"></span> | 
|  | <span class="source-line-no">912</span><span id="line-912">      long recoverSeqId = 1030;</span> | 
|  | <span class="source-line-no">913</span><span id="line-913">      Map<byte[], Long> maxSeqIdInStores = new TreeMap<>(Bytes.BYTES_COMPARATOR);</span> | 
|  | <span class="source-line-no">914</span><span id="line-914">      MonitoredTask status = TaskMonitor.get().createStatus(method);</span> | 
|  | <span class="source-line-no">915</span><span id="line-915">      for (HStore store : region.getStores()) {</span> | 
|  | <span class="source-line-no">916</span><span id="line-916">        maxSeqIdInStores.put(Bytes.toBytes(store.getColumnFamilyName()), recoverSeqId - 1);</span> | 
|  | <span class="source-line-no">917</span><span id="line-917">      }</span> | 
|  | <span class="source-line-no">918</span><span id="line-918">      long seqId = region.replayRecoveredEditsIfAny(maxSeqIdInStores, null, status);</span> | 
|  | <span class="source-line-no">919</span><span id="line-919">      assertEquals(maxSeqId, seqId);</span> | 
|  | <span class="source-line-no">920</span><span id="line-920"></span> | 
|  | <span class="source-line-no">921</span><span id="line-921">      // assert that the files are flushed</span> | 
|  | <span class="source-line-no">922</span><span id="line-922">      assertEquals(1, region.getStoreFileList(columns).size());</span> | 
|  | <span class="source-line-no">923</span><span id="line-923"></span> | 
|  | <span class="source-line-no">924</span><span id="line-924">    } finally {</span> | 
|  | <span class="source-line-no">925</span><span id="line-925">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">926</span><span id="line-926">      this.region = null;</span> | 
|  | <span class="source-line-no">927</span><span id="line-927">      wals.close();</span> | 
|  | <span class="source-line-no">928</span><span id="line-928">    }</span> | 
|  | <span class="source-line-no">929</span><span id="line-929">  }</span> | 
|  | <span class="source-line-no">930</span><span id="line-930"></span> | 
|  | <span class="source-line-no">931</span><span id="line-931">  @Test</span> | 
|  | <span class="source-line-no">932</span><span id="line-932">  public void testRecoveredEditsReplayCompaction() throws Exception {</span> | 
|  | <span class="source-line-no">933</span><span id="line-933">    testRecoveredEditsReplayCompaction(false);</span> | 
|  | <span class="source-line-no">934</span><span id="line-934">    testRecoveredEditsReplayCompaction(true);</span> | 
|  | <span class="source-line-no">935</span><span id="line-935">  }</span> | 
|  | <span class="source-line-no">936</span><span id="line-936"></span> | 
|  | <span class="source-line-no">937</span><span id="line-937">  public void testRecoveredEditsReplayCompaction(boolean mismatchedRegionName) throws Exception {</span> | 
|  | <span class="source-line-no">938</span><span id="line-938">    CONF.setClass(HConstants.REGION_IMPL, HRegionForTesting.class, Region.class);</span> | 
|  | <span class="source-line-no">939</span><span id="line-939">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">940</span><span id="line-940">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">941</span><span id="line-941">    final WALFactory wals = new WALFactory(CONF, method);</span> | 
|  | <span class="source-line-no">942</span><span id="line-942">    try {</span> | 
|  | <span class="source-line-no">943</span><span id="line-943">      Path regiondir = region.getRegionFileSystem().getRegionDir();</span> | 
|  | <span class="source-line-no">944</span><span id="line-944">      FileSystem fs = region.getRegionFileSystem().getFileSystem();</span> | 
|  | <span class="source-line-no">945</span><span id="line-945">      byte[] regionName = region.getRegionInfo().getEncodedNameAsBytes();</span> | 
|  | <span class="source-line-no">946</span><span id="line-946"></span> | 
|  | <span class="source-line-no">947</span><span id="line-947">      long maxSeqId = 3;</span> | 
|  | <span class="source-line-no">948</span><span id="line-948">      long minSeqId = 0;</span> | 
|  | <span class="source-line-no">949</span><span id="line-949"></span> | 
|  | <span class="source-line-no">950</span><span id="line-950">      for (long i = minSeqId; i < maxSeqId; i++) {</span> | 
|  | <span class="source-line-no">951</span><span id="line-951">        Put put = new Put(Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">952</span><span id="line-952">        put.addColumn(family, Bytes.toBytes(i), Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">953</span><span id="line-953">        region.put(put);</span> | 
|  | <span class="source-line-no">954</span><span id="line-954">        region.flush(true);</span> | 
|  | <span class="source-line-no">955</span><span id="line-955">      }</span> | 
|  | <span class="source-line-no">956</span><span id="line-956"></span> | 
|  | <span class="source-line-no">957</span><span id="line-957">      // this will create a region with 3 files</span> | 
|  | <span class="source-line-no">958</span><span id="line-958">      assertEquals(3, region.getStore(family).getStorefilesCount());</span> | 
|  | <span class="source-line-no">959</span><span id="line-959">      List<Path> storeFiles = new ArrayList<>(3);</span> | 
|  | <span class="source-line-no">960</span><span id="line-960">      for (HStoreFile sf : region.getStore(family).getStorefiles()) {</span> | 
|  | <span class="source-line-no">961</span><span id="line-961">        storeFiles.add(sf.getPath());</span> | 
|  | <span class="source-line-no">962</span><span id="line-962">      }</span> | 
|  | <span class="source-line-no">963</span><span id="line-963"></span> | 
|  | <span class="source-line-no">964</span><span id="line-964">      // disable compaction completion</span> | 
|  | <span class="source-line-no">965</span><span id="line-965">      CONF.setBoolean("hbase.hstore.compaction.complete", false);</span> | 
|  | <span class="source-line-no">966</span><span id="line-966">      region.compactStores();</span> | 
|  | <span class="source-line-no">967</span><span id="line-967"></span> | 
|  | <span class="source-line-no">968</span><span id="line-968">      // ensure that nothing changed</span> | 
|  | <span class="source-line-no">969</span><span id="line-969">      assertEquals(3, region.getStore(family).getStorefilesCount());</span> | 
|  | <span class="source-line-no">970</span><span id="line-970"></span> | 
|  | <span class="source-line-no">971</span><span id="line-971">      // now find the compacted file, and manually add it to the recovered edits</span> | 
|  | <span class="source-line-no">972</span><span id="line-972">      Path tmpDir = new Path(region.getRegionFileSystem().getTempDir(), Bytes.toString(family));</span> | 
|  | <span class="source-line-no">973</span><span id="line-973">      FileStatus[] files = CommonFSUtils.listStatus(fs, tmpDir);</span> | 
|  | <span class="source-line-no">974</span><span id="line-974">      String errorMsg = "Expected to find 1 file in the region temp directory "</span> | 
|  | <span class="source-line-no">975</span><span id="line-975">        + "from the compaction, could not find any";</span> | 
|  | <span class="source-line-no">976</span><span id="line-976">      assertNotNull(errorMsg, files);</span> | 
|  | <span class="source-line-no">977</span><span id="line-977">      assertEquals(errorMsg, 1, files.length);</span> | 
|  | <span class="source-line-no">978</span><span id="line-978">      // move the file inside region dir</span> | 
|  | <span class="source-line-no">979</span><span id="line-979">      Path newFile =</span> | 
|  | <span class="source-line-no">980</span><span id="line-980">        region.getRegionFileSystem().commitStoreFile(Bytes.toString(family), files[0].getPath());</span> | 
|  | <span class="source-line-no">981</span><span id="line-981"></span> | 
|  | <span class="source-line-no">982</span><span id="line-982">      byte[] encodedNameAsBytes = this.region.getRegionInfo().getEncodedNameAsBytes();</span> | 
|  | <span class="source-line-no">983</span><span id="line-983">      byte[] fakeEncodedNameAsBytes = new byte[encodedNameAsBytes.length];</span> | 
|  | <span class="source-line-no">984</span><span id="line-984">      for (int i = 0; i < encodedNameAsBytes.length; i++) {</span> | 
|  | <span class="source-line-no">985</span><span id="line-985">        // Mix the byte array to have a new encodedName</span> | 
|  | <span class="source-line-no">986</span><span id="line-986">        fakeEncodedNameAsBytes[i] = (byte) (encodedNameAsBytes[i] + 1);</span> | 
|  | <span class="source-line-no">987</span><span id="line-987">      }</span> | 
|  | <span class="source-line-no">988</span><span id="line-988"></span> | 
|  | <span class="source-line-no">989</span><span id="line-989">      CompactionDescriptor compactionDescriptor = ProtobufUtil.toCompactionDescriptor(</span> | 
|  | <span class="source-line-no">990</span><span id="line-990">        this.region.getRegionInfo(), mismatchedRegionName ? fakeEncodedNameAsBytes : null, family,</span> | 
|  | <span class="source-line-no">991</span><span id="line-991">        storeFiles, Lists.newArrayList(newFile),</span> | 
|  | <span class="source-line-no">992</span><span id="line-992">        region.getRegionFileSystem().getStoreDir(Bytes.toString(family)));</span> | 
|  | <span class="source-line-no">993</span><span id="line-993"></span> | 
|  | <span class="source-line-no">994</span><span id="line-994">      WALUtil.writeCompactionMarker(region.getWAL(), this.region.getReplicationScope(),</span> | 
|  | <span class="source-line-no">995</span><span id="line-995">        this.region.getRegionInfo(), compactionDescriptor, region.getMVCC(), null);</span> | 
|  | <span class="source-line-no">996</span><span id="line-996"></span> | 
|  | <span class="source-line-no">997</span><span id="line-997">      Path recoveredEditsDir = WALSplitUtil.getRegionDirRecoveredEditsDir(regiondir);</span> | 
|  | <span class="source-line-no">998</span><span id="line-998"></span> | 
|  | <span class="source-line-no">999</span><span id="line-999">      Path recoveredEdits = new Path(recoveredEditsDir, String.format("%019d", 1000));</span> | 
|  | <span class="source-line-no">1000</span><span id="line-1000">      fs.create(recoveredEdits);</span> | 
|  | <span class="source-line-no">1001</span><span id="line-1001">      WALProvider.Writer writer = wals.createRecoveredEditsWriter(fs, recoveredEdits);</span> | 
|  | <span class="source-line-no">1002</span><span id="line-1002"></span> | 
|  | <span class="source-line-no">1003</span><span id="line-1003">      long time = System.nanoTime();</span> | 
|  | <span class="source-line-no">1004</span><span id="line-1004"></span> | 
|  | <span class="source-line-no">1005</span><span id="line-1005">      writer.append(new WAL.Entry(</span> | 
|  | <span class="source-line-no">1006</span><span id="line-1006">        new WALKeyImpl(regionName, tableName, 10, time, HConstants.DEFAULT_CLUSTER_ID),</span> | 
|  | <span class="source-line-no">1007</span><span id="line-1007">        WALEdit.createCompaction(region.getRegionInfo(), compactionDescriptor)));</span> | 
|  | <span class="source-line-no">1008</span><span id="line-1008">      writer.close();</span> | 
|  | <span class="source-line-no">1009</span><span id="line-1009"></span> | 
|  | <span class="source-line-no">1010</span><span id="line-1010">      // close the region now, and reopen again</span> | 
|  | <span class="source-line-no">1011</span><span id="line-1011">      region.getTableDescriptor();</span> | 
|  | <span class="source-line-no">1012</span><span id="line-1012">      region.getRegionInfo();</span> | 
|  | <span class="source-line-no">1013</span><span id="line-1013">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">1014</span><span id="line-1014">      try {</span> | 
|  | <span class="source-line-no">1015</span><span id="line-1015">        region = HRegion.openHRegion(region, null);</span> | 
|  | <span class="source-line-no">1016</span><span id="line-1016">      } catch (WrongRegionException wre) {</span> | 
|  | <span class="source-line-no">1017</span><span id="line-1017">        fail("Matching encoded region name should not have produced WrongRegionException");</span> | 
|  | <span class="source-line-no">1018</span><span id="line-1018">      }</span> | 
|  | <span class="source-line-no">1019</span><span id="line-1019"></span> | 
|  | <span class="source-line-no">1020</span><span id="line-1020">      // now check whether we have only one store file, the compacted one</span> | 
|  | <span class="source-line-no">1021</span><span id="line-1021">      Collection<HStoreFile> sfs = region.getStore(family).getStorefiles();</span> | 
|  | <span class="source-line-no">1022</span><span id="line-1022">      for (HStoreFile sf : sfs) {</span> | 
|  | <span class="source-line-no">1023</span><span id="line-1023">        LOG.info(Objects.toString(sf.getPath()));</span> | 
|  | <span class="source-line-no">1024</span><span id="line-1024">      }</span> | 
|  | <span class="source-line-no">1025</span><span id="line-1025">      if (!mismatchedRegionName) {</span> | 
|  | <span class="source-line-no">1026</span><span id="line-1026">        assertEquals(1, region.getStore(family).getStorefilesCount());</span> | 
|  | <span class="source-line-no">1027</span><span id="line-1027">      }</span> | 
|  | <span class="source-line-no">1028</span><span id="line-1028">      files = CommonFSUtils.listStatus(fs, tmpDir);</span> | 
|  | <span class="source-line-no">1029</span><span id="line-1029">      assertTrue("Expected to find 0 files inside " + tmpDir, files == null || files.length == 0);</span> | 
|  | <span class="source-line-no">1030</span><span id="line-1030"></span> | 
|  | <span class="source-line-no">1031</span><span id="line-1031">      for (long i = minSeqId; i < maxSeqId; i++) {</span> | 
|  | <span class="source-line-no">1032</span><span id="line-1032">        Get get = new Get(Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">1033</span><span id="line-1033">        Result result = region.get(get);</span> | 
|  | <span class="source-line-no">1034</span><span id="line-1034">        byte[] value = result.getValue(family, Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">1035</span><span id="line-1035">        assertArrayEquals(Bytes.toBytes(i), value);</span> | 
|  | <span class="source-line-no">1036</span><span id="line-1036">      }</span> | 
|  | <span class="source-line-no">1037</span><span id="line-1037">    } finally {</span> | 
|  | <span class="source-line-no">1038</span><span id="line-1038">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">1039</span><span id="line-1039">      this.region = null;</span> | 
|  | <span class="source-line-no">1040</span><span id="line-1040">      wals.close();</span> | 
|  | <span class="source-line-no">1041</span><span id="line-1041">      CONF.setClass(HConstants.REGION_IMPL, HRegion.class, Region.class);</span> | 
|  | <span class="source-line-no">1042</span><span id="line-1042">    }</span> | 
|  | <span class="source-line-no">1043</span><span id="line-1043">  }</span> | 
|  | <span class="source-line-no">1044</span><span id="line-1044"></span> | 
|  | <span class="source-line-no">1045</span><span id="line-1045">  @Test</span> | 
|  | <span class="source-line-no">1046</span><span id="line-1046">  public void testFlushMarkers() throws Exception {</span> | 
|  | <span class="source-line-no">1047</span><span id="line-1047">    // tests that flush markers are written to WAL and handled at recovered edits</span> | 
|  | <span class="source-line-no">1048</span><span id="line-1048">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">1049</span><span id="line-1049">    Path logDir = TEST_UTIL.getDataTestDirOnTestFS(method + ".log");</span> | 
|  | <span class="source-line-no">1050</span><span id="line-1050">    final Configuration walConf = new Configuration(TEST_UTIL.getConfiguration());</span> | 
|  | <span class="source-line-no">1051</span><span id="line-1051">    CommonFSUtils.setRootDir(walConf, logDir);</span> | 
|  | <span class="source-line-no">1052</span><span id="line-1052">    final WALFactory wals = new WALFactory(walConf, method);</span> | 
|  | <span class="source-line-no">1053</span><span id="line-1053">    final WAL wal = wals.getWAL(RegionInfoBuilder.newBuilder(tableName).build());</span> | 
|  | <span class="source-line-no">1054</span><span id="line-1054"></span> | 
|  | <span class="source-line-no">1055</span><span id="line-1055">    this.region = initHRegion(tableName, HConstants.EMPTY_START_ROW, HConstants.EMPTY_END_ROW, CONF,</span> | 
|  | <span class="source-line-no">1056</span><span id="line-1056">      false, Durability.USE_DEFAULT, wal, family);</span> | 
|  | <span class="source-line-no">1057</span><span id="line-1057">    try {</span> | 
|  | <span class="source-line-no">1058</span><span id="line-1058">      Path regiondir = region.getRegionFileSystem().getRegionDir();</span> | 
|  | <span class="source-line-no">1059</span><span id="line-1059">      FileSystem fs = region.getRegionFileSystem().getFileSystem();</span> | 
|  | <span class="source-line-no">1060</span><span id="line-1060">      byte[] regionName = region.getRegionInfo().getEncodedNameAsBytes();</span> | 
|  | <span class="source-line-no">1061</span><span id="line-1061"></span> | 
|  | <span class="source-line-no">1062</span><span id="line-1062">      long maxSeqId = 3;</span> | 
|  | <span class="source-line-no">1063</span><span id="line-1063">      long minSeqId = 0;</span> | 
|  | <span class="source-line-no">1064</span><span id="line-1064"></span> | 
|  | <span class="source-line-no">1065</span><span id="line-1065">      for (long i = minSeqId; i < maxSeqId; i++) {</span> | 
|  | <span class="source-line-no">1066</span><span id="line-1066">        Put put = new Put(Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">1067</span><span id="line-1067">        put.addColumn(family, Bytes.toBytes(i), Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">1068</span><span id="line-1068">        region.put(put);</span> | 
|  | <span class="source-line-no">1069</span><span id="line-1069">        region.flush(true);</span> | 
|  | <span class="source-line-no">1070</span><span id="line-1070">      }</span> | 
|  | <span class="source-line-no">1071</span><span id="line-1071"></span> | 
|  | <span class="source-line-no">1072</span><span id="line-1072">      // this will create a region with 3 files from flush</span> | 
|  | <span class="source-line-no">1073</span><span id="line-1073">      assertEquals(3, region.getStore(family).getStorefilesCount());</span> | 
|  | <span class="source-line-no">1074</span><span id="line-1074">      List<String> storeFiles = new ArrayList<>(3);</span> | 
|  | <span class="source-line-no">1075</span><span id="line-1075">      for (HStoreFile sf : region.getStore(family).getStorefiles()) {</span> | 
|  | <span class="source-line-no">1076</span><span id="line-1076">        storeFiles.add(sf.getPath().getName());</span> | 
|  | <span class="source-line-no">1077</span><span id="line-1077">      }</span> | 
|  | <span class="source-line-no">1078</span><span id="line-1078"></span> | 
|  | <span class="source-line-no">1079</span><span id="line-1079">      // now verify that the flush markers are written</span> | 
|  | <span class="source-line-no">1080</span><span id="line-1080">      wal.shutdown();</span> | 
|  | <span class="source-line-no">1081</span><span id="line-1081">      WALStreamReader reader = WALFactory.createStreamReader(fs,</span> | 
|  | <span class="source-line-no">1082</span><span id="line-1082">        AbstractFSWALProvider.getCurrentFileName(wal), TEST_UTIL.getConfiguration());</span> | 
|  | <span class="source-line-no">1083</span><span id="line-1083">      try {</span> | 
|  | <span class="source-line-no">1084</span><span id="line-1084">        List<WAL.Entry> flushDescriptors = new ArrayList<>();</span> | 
|  | <span class="source-line-no">1085</span><span id="line-1085">        long lastFlushSeqId = -1;</span> | 
|  | <span class="source-line-no">1086</span><span id="line-1086">        while (true) {</span> | 
|  | <span class="source-line-no">1087</span><span id="line-1087">          WAL.Entry entry = reader.next();</span> | 
|  | <span class="source-line-no">1088</span><span id="line-1088">          if (entry == null) {</span> | 
|  | <span class="source-line-no">1089</span><span id="line-1089">            break;</span> | 
|  | <span class="source-line-no">1090</span><span id="line-1090">          }</span> | 
|  | <span class="source-line-no">1091</span><span id="line-1091">          Cell cell = entry.getEdit().getCells().get(0);</span> | 
|  | <span class="source-line-no">1092</span><span id="line-1092">          if (WALEdit.isMetaEditFamily(cell)) {</span> | 
|  | <span class="source-line-no">1093</span><span id="line-1093">            FlushDescriptor flushDesc = WALEdit.getFlushDescriptor(cell);</span> | 
|  | <span class="source-line-no">1094</span><span id="line-1094">            assertNotNull(flushDesc);</span> | 
|  | <span class="source-line-no">1095</span><span id="line-1095">            assertArrayEquals(tableName.getName(), flushDesc.getTableName().toByteArray());</span> | 
|  | <span class="source-line-no">1096</span><span id="line-1096">            if (flushDesc.getAction() == FlushAction.START_FLUSH) {</span> | 
|  | <span class="source-line-no">1097</span><span id="line-1097">              assertTrue(flushDesc.getFlushSequenceNumber() > lastFlushSeqId);</span> | 
|  | <span class="source-line-no">1098</span><span id="line-1098">            } else if (flushDesc.getAction() == FlushAction.COMMIT_FLUSH) {</span> | 
|  | <span class="source-line-no">1099</span><span id="line-1099">              assertTrue(flushDesc.getFlushSequenceNumber() == lastFlushSeqId);</span> | 
|  | <span class="source-line-no">1100</span><span id="line-1100">            }</span> | 
|  | <span class="source-line-no">1101</span><span id="line-1101">            lastFlushSeqId = flushDesc.getFlushSequenceNumber();</span> | 
|  | <span class="source-line-no">1102</span><span id="line-1102">            assertArrayEquals(regionName, flushDesc.getEncodedRegionName().toByteArray());</span> | 
|  | <span class="source-line-no">1103</span><span id="line-1103">            assertEquals(1, flushDesc.getStoreFlushesCount()); // only one store</span> | 
|  | <span class="source-line-no">1104</span><span id="line-1104">            StoreFlushDescriptor storeFlushDesc = flushDesc.getStoreFlushes(0);</span> | 
|  | <span class="source-line-no">1105</span><span id="line-1105">            assertArrayEquals(family, storeFlushDesc.getFamilyName().toByteArray());</span> | 
|  | <span class="source-line-no">1106</span><span id="line-1106">            assertEquals("family", storeFlushDesc.getStoreHomeDir());</span> | 
|  | <span class="source-line-no">1107</span><span id="line-1107">            if (flushDesc.getAction() == FlushAction.START_FLUSH) {</span> | 
|  | <span class="source-line-no">1108</span><span id="line-1108">              assertEquals(0, storeFlushDesc.getFlushOutputCount());</span> | 
|  | <span class="source-line-no">1109</span><span id="line-1109">            } else {</span> | 
|  | <span class="source-line-no">1110</span><span id="line-1110">              assertEquals(1, storeFlushDesc.getFlushOutputCount()); // only one file from flush</span> | 
|  | <span class="source-line-no">1111</span><span id="line-1111">              assertTrue(storeFiles.contains(storeFlushDesc.getFlushOutput(0)));</span> | 
|  | <span class="source-line-no">1112</span><span id="line-1112">            }</span> | 
|  | <span class="source-line-no">1113</span><span id="line-1113"></span> | 
|  | <span class="source-line-no">1114</span><span id="line-1114">            flushDescriptors.add(entry);</span> | 
|  | <span class="source-line-no">1115</span><span id="line-1115">          }</span> | 
|  | <span class="source-line-no">1116</span><span id="line-1116">        }</span> | 
|  | <span class="source-line-no">1117</span><span id="line-1117"></span> | 
|  | <span class="source-line-no">1118</span><span id="line-1118">        assertEquals(3 * 2, flushDescriptors.size()); // START_FLUSH and COMMIT_FLUSH per flush</span> | 
|  | <span class="source-line-no">1119</span><span id="line-1119"></span> | 
|  | <span class="source-line-no">1120</span><span id="line-1120">        // now write those markers to the recovered edits again.</span> | 
|  | <span class="source-line-no">1121</span><span id="line-1121"></span> | 
|  | <span class="source-line-no">1122</span><span id="line-1122">        Path recoveredEditsDir = WALSplitUtil.getRegionDirRecoveredEditsDir(regiondir);</span> | 
|  | <span class="source-line-no">1123</span><span id="line-1123"></span> | 
|  | <span class="source-line-no">1124</span><span id="line-1124">        Path recoveredEdits = new Path(recoveredEditsDir, String.format("%019d", 1000));</span> | 
|  | <span class="source-line-no">1125</span><span id="line-1125">        fs.create(recoveredEdits);</span> | 
|  | <span class="source-line-no">1126</span><span id="line-1126">        WALProvider.Writer writer = wals.createRecoveredEditsWriter(fs, recoveredEdits);</span> | 
|  | <span class="source-line-no">1127</span><span id="line-1127"></span> | 
|  | <span class="source-line-no">1128</span><span id="line-1128">        for (WAL.Entry entry : flushDescriptors) {</span> | 
|  | <span class="source-line-no">1129</span><span id="line-1129">          writer.append(entry);</span> | 
|  | <span class="source-line-no">1130</span><span id="line-1130">        }</span> | 
|  | <span class="source-line-no">1131</span><span id="line-1131">        writer.close();</span> | 
|  | <span class="source-line-no">1132</span><span id="line-1132">      } finally {</span> | 
|  | <span class="source-line-no">1133</span><span id="line-1133">        reader.close();</span> | 
|  | <span class="source-line-no">1134</span><span id="line-1134">      }</span> | 
|  | <span class="source-line-no">1135</span><span id="line-1135"></span> | 
|  | <span class="source-line-no">1136</span><span id="line-1136">      // close the region now, and reopen again</span> | 
|  | <span class="source-line-no">1137</span><span id="line-1137">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">1138</span><span id="line-1138">      region = HRegion.openHRegion(region, null);</span> | 
|  | <span class="source-line-no">1139</span><span id="line-1139"></span> | 
|  | <span class="source-line-no">1140</span><span id="line-1140">      // now check whether we have can read back the data from region</span> | 
|  | <span class="source-line-no">1141</span><span id="line-1141">      for (long i = minSeqId; i < maxSeqId; i++) {</span> | 
|  | <span class="source-line-no">1142</span><span id="line-1142">        Get get = new Get(Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">1143</span><span id="line-1143">        Result result = region.get(get);</span> | 
|  | <span class="source-line-no">1144</span><span id="line-1144">        byte[] value = result.getValue(family, Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">1145</span><span id="line-1145">        assertArrayEquals(Bytes.toBytes(i), value);</span> | 
|  | <span class="source-line-no">1146</span><span id="line-1146">      }</span> | 
|  | <span class="source-line-no">1147</span><span id="line-1147">    } finally {</span> | 
|  | <span class="source-line-no">1148</span><span id="line-1148">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">1149</span><span id="line-1149">      this.region = null;</span> | 
|  | <span class="source-line-no">1150</span><span id="line-1150">      wals.close();</span> | 
|  | <span class="source-line-no">1151</span><span id="line-1151">    }</span> | 
|  | <span class="source-line-no">1152</span><span id="line-1152">  }</span> | 
|  | <span class="source-line-no">1153</span><span id="line-1153"></span> | 
|  | <span class="source-line-no">1154</span><span id="line-1154">  static class IsFlushWALMarker implements ArgumentMatcher<WALEdit> {</span> | 
|  | <span class="source-line-no">1155</span><span id="line-1155">    volatile FlushAction[] actions;</span> | 
|  | <span class="source-line-no">1156</span><span id="line-1156"></span> | 
|  | <span class="source-line-no">1157</span><span id="line-1157">    public IsFlushWALMarker(FlushAction... actions) {</span> | 
|  | <span class="source-line-no">1158</span><span id="line-1158">      this.actions = actions;</span> | 
|  | <span class="source-line-no">1159</span><span id="line-1159">    }</span> | 
|  | <span class="source-line-no">1160</span><span id="line-1160"></span> | 
|  | <span class="source-line-no">1161</span><span id="line-1161">    @Override</span> | 
|  | <span class="source-line-no">1162</span><span id="line-1162">    public boolean matches(WALEdit edit) {</span> | 
|  | <span class="source-line-no">1163</span><span id="line-1163">      List<Cell> cells = edit.getCells();</span> | 
|  | <span class="source-line-no">1164</span><span id="line-1164">      if (cells.isEmpty()) {</span> | 
|  | <span class="source-line-no">1165</span><span id="line-1165">        return false;</span> | 
|  | <span class="source-line-no">1166</span><span id="line-1166">      }</span> | 
|  | <span class="source-line-no">1167</span><span id="line-1167">      if (WALEdit.isMetaEditFamily(cells.get(0))) {</span> | 
|  | <span class="source-line-no">1168</span><span id="line-1168">        FlushDescriptor desc;</span> | 
|  | <span class="source-line-no">1169</span><span id="line-1169">        try {</span> | 
|  | <span class="source-line-no">1170</span><span id="line-1170">          desc = WALEdit.getFlushDescriptor(cells.get(0));</span> | 
|  | <span class="source-line-no">1171</span><span id="line-1171">        } catch (IOException e) {</span> | 
|  | <span class="source-line-no">1172</span><span id="line-1172">          LOG.warn(e.toString(), e);</span> | 
|  | <span class="source-line-no">1173</span><span id="line-1173">          return false;</span> | 
|  | <span class="source-line-no">1174</span><span id="line-1174">        }</span> | 
|  | <span class="source-line-no">1175</span><span id="line-1175">        if (desc != null) {</span> | 
|  | <span class="source-line-no">1176</span><span id="line-1176">          for (FlushAction action : actions) {</span> | 
|  | <span class="source-line-no">1177</span><span id="line-1177">            if (desc.getAction() == action) {</span> | 
|  | <span class="source-line-no">1178</span><span id="line-1178">              return true;</span> | 
|  | <span class="source-line-no">1179</span><span id="line-1179">            }</span> | 
|  | <span class="source-line-no">1180</span><span id="line-1180">          }</span> | 
|  | <span class="source-line-no">1181</span><span id="line-1181">        }</span> | 
|  | <span class="source-line-no">1182</span><span id="line-1182">      }</span> | 
|  | <span class="source-line-no">1183</span><span id="line-1183">      return false;</span> | 
|  | <span class="source-line-no">1184</span><span id="line-1184">    }</span> | 
|  | <span class="source-line-no">1185</span><span id="line-1185"></span> | 
|  | <span class="source-line-no">1186</span><span id="line-1186">    public IsFlushWALMarker set(FlushAction... actions) {</span> | 
|  | <span class="source-line-no">1187</span><span id="line-1187">      this.actions = actions;</span> | 
|  | <span class="source-line-no">1188</span><span id="line-1188">      return this;</span> | 
|  | <span class="source-line-no">1189</span><span id="line-1189">    }</span> | 
|  | <span class="source-line-no">1190</span><span id="line-1190">  }</span> | 
|  | <span class="source-line-no">1191</span><span id="line-1191"></span> | 
|  | <span class="source-line-no">1192</span><span id="line-1192">  @Test</span> | 
|  | <span class="source-line-no">1193</span><span id="line-1193">  public void testFlushMarkersWALFail() throws Exception {</span> | 
|  | <span class="source-line-no">1194</span><span id="line-1194">    // test the cases where the WAL append for flush markers fail.</span> | 
|  | <span class="source-line-no">1195</span><span id="line-1195">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">1196</span><span id="line-1196"></span> | 
|  | <span class="source-line-no">1197</span><span id="line-1197">    // spy an actual WAL implementation to throw exception (was not able to mock)</span> | 
|  | <span class="source-line-no">1198</span><span id="line-1198">    Path logDir = TEST_UTIL.getDataTestDirOnTestFS(method + "log");</span> | 
|  | <span class="source-line-no">1199</span><span id="line-1199"></span> | 
|  | <span class="source-line-no">1200</span><span id="line-1200">    final Configuration walConf = new Configuration(TEST_UTIL.getConfiguration());</span> | 
|  | <span class="source-line-no">1201</span><span id="line-1201">    CommonFSUtils.setRootDir(walConf, logDir);</span> | 
|  | <span class="source-line-no">1202</span><span id="line-1202">    // Make up a WAL that we can manipulate at append time.</span> | 
|  | <span class="source-line-no">1203</span><span id="line-1203">    class FailAppendFlushMarkerWAL extends FSHLog {</span> | 
|  | <span class="source-line-no">1204</span><span id="line-1204">      volatile FlushAction[] flushActions = null;</span> | 
|  | <span class="source-line-no">1205</span><span id="line-1205"></span> | 
|  | <span class="source-line-no">1206</span><span id="line-1206">      public FailAppendFlushMarkerWAL(FileSystem fs, Path root, String logDir, Configuration conf)</span> | 
|  | <span class="source-line-no">1207</span><span id="line-1207">        throws IOException {</span> | 
|  | <span class="source-line-no">1208</span><span id="line-1208">        super(fs, root, logDir, conf);</span> | 
|  | <span class="source-line-no">1209</span><span id="line-1209">      }</span> | 
|  | <span class="source-line-no">1210</span><span id="line-1210"></span> | 
|  | <span class="source-line-no">1211</span><span id="line-1211">      @Override</span> | 
|  | <span class="source-line-no">1212</span><span id="line-1212">      protected Writer createWriterInstance(FileSystem fs, Path path) throws IOException {</span> | 
|  | <span class="source-line-no">1213</span><span id="line-1213">        final Writer w = super.createWriterInstance(fs, path);</span> | 
|  | <span class="source-line-no">1214</span><span id="line-1214">        return new Writer() {</span> | 
|  | <span class="source-line-no">1215</span><span id="line-1215">          @Override</span> | 
|  | <span class="source-line-no">1216</span><span id="line-1216">          public void close() throws IOException {</span> | 
|  | <span class="source-line-no">1217</span><span id="line-1217">            w.close();</span> | 
|  | <span class="source-line-no">1218</span><span id="line-1218">          }</span> | 
|  | <span class="source-line-no">1219</span><span id="line-1219"></span> | 
|  | <span class="source-line-no">1220</span><span id="line-1220">          @Override</span> | 
|  | <span class="source-line-no">1221</span><span id="line-1221">          public void sync(boolean forceSync) throws IOException {</span> | 
|  | <span class="source-line-no">1222</span><span id="line-1222">            w.sync(forceSync);</span> | 
|  | <span class="source-line-no">1223</span><span id="line-1223">          }</span> | 
|  | <span class="source-line-no">1224</span><span id="line-1224"></span> | 
|  | <span class="source-line-no">1225</span><span id="line-1225">          @Override</span> | 
|  | <span class="source-line-no">1226</span><span id="line-1226">          public void append(Entry entry) throws IOException {</span> | 
|  | <span class="source-line-no">1227</span><span id="line-1227">            List<Cell> cells = entry.getEdit().getCells();</span> | 
|  | <span class="source-line-no">1228</span><span id="line-1228">            if (WALEdit.isMetaEditFamily(cells.get(0))) {</span> | 
|  | <span class="source-line-no">1229</span><span id="line-1229">              FlushDescriptor desc = WALEdit.getFlushDescriptor(cells.get(0));</span> | 
|  | <span class="source-line-no">1230</span><span id="line-1230">              if (desc != null) {</span> | 
|  | <span class="source-line-no">1231</span><span id="line-1231">                for (FlushAction flushAction : flushActions) {</span> | 
|  | <span class="source-line-no">1232</span><span id="line-1232">                  if (desc.getAction().equals(flushAction)) {</span> | 
|  | <span class="source-line-no">1233</span><span id="line-1233">                    throw new IOException("Failed to append flush marker! " + flushAction);</span> | 
|  | <span class="source-line-no">1234</span><span id="line-1234">                  }</span> | 
|  | <span class="source-line-no">1235</span><span id="line-1235">                }</span> | 
|  | <span class="source-line-no">1236</span><span id="line-1236">              }</span> | 
|  | <span class="source-line-no">1237</span><span id="line-1237">            }</span> | 
|  | <span class="source-line-no">1238</span><span id="line-1238">            w.append(entry);</span> | 
|  | <span class="source-line-no">1239</span><span id="line-1239">          }</span> | 
|  | <span class="source-line-no">1240</span><span id="line-1240"></span> | 
|  | <span class="source-line-no">1241</span><span id="line-1241">          @Override</span> | 
|  | <span class="source-line-no">1242</span><span id="line-1242">          public long getLength() {</span> | 
|  | <span class="source-line-no">1243</span><span id="line-1243">            return w.getLength();</span> | 
|  | <span class="source-line-no">1244</span><span id="line-1244">          }</span> | 
|  | <span class="source-line-no">1245</span><span id="line-1245"></span> | 
|  | <span class="source-line-no">1246</span><span id="line-1246">          @Override</span> | 
|  | <span class="source-line-no">1247</span><span id="line-1247">          public long getSyncedLength() {</span> | 
|  | <span class="source-line-no">1248</span><span id="line-1248">            return w.getSyncedLength();</span> | 
|  | <span class="source-line-no">1249</span><span id="line-1249">          }</span> | 
|  | <span class="source-line-no">1250</span><span id="line-1250">        };</span> | 
|  | <span class="source-line-no">1251</span><span id="line-1251">      }</span> | 
|  | <span class="source-line-no">1252</span><span id="line-1252">    }</span> | 
|  | <span class="source-line-no">1253</span><span id="line-1253">    FailAppendFlushMarkerWAL wal = new FailAppendFlushMarkerWAL(FileSystem.get(walConf),</span> | 
|  | <span class="source-line-no">1254</span><span id="line-1254">      CommonFSUtils.getRootDir(walConf), method, walConf);</span> | 
|  | <span class="source-line-no">1255</span><span id="line-1255">    wal.init();</span> | 
|  | <span class="source-line-no">1256</span><span id="line-1256">    this.region = initHRegion(tableName, HConstants.EMPTY_START_ROW, HConstants.EMPTY_END_ROW, CONF,</span> | 
|  | <span class="source-line-no">1257</span><span id="line-1257">      false, Durability.USE_DEFAULT, wal, family);</span> | 
|  | <span class="source-line-no">1258</span><span id="line-1258">    int i = 0;</span> | 
|  | <span class="source-line-no">1259</span><span id="line-1259">    Put put = new Put(Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">1260</span><span id="line-1260">    put.setDurability(Durability.SKIP_WAL); // have to skip mocked wal</span> | 
|  | <span class="source-line-no">1261</span><span id="line-1261">    put.addColumn(family, Bytes.toBytes(i), Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">1262</span><span id="line-1262">    region.put(put);</span> | 
|  | <span class="source-line-no">1263</span><span id="line-1263"></span> | 
|  | <span class="source-line-no">1264</span><span id="line-1264">    // 1. Test case where START_FLUSH throws exception</span> | 
|  | <span class="source-line-no">1265</span><span id="line-1265">    wal.flushActions = new FlushAction[] { FlushAction.START_FLUSH };</span> | 
|  | <span class="source-line-no">1266</span><span id="line-1266"></span> | 
|  | <span class="source-line-no">1267</span><span id="line-1267">    // start cache flush will throw exception</span> | 
|  | <span class="source-line-no">1268</span><span id="line-1268">    try {</span> | 
|  | <span class="source-line-no">1269</span><span id="line-1269">      region.flush(true);</span> | 
|  | <span class="source-line-no">1270</span><span id="line-1270">      fail("This should have thrown exception");</span> | 
|  | <span class="source-line-no">1271</span><span id="line-1271">    } catch (DroppedSnapshotException unexpected) {</span> | 
|  | <span class="source-line-no">1272</span><span id="line-1272">      // this should not be a dropped snapshot exception. Meaning that RS will not abort</span> | 
|  | <span class="source-line-no">1273</span><span id="line-1273">      throw unexpected;</span> | 
|  | <span class="source-line-no">1274</span><span id="line-1274">    } catch (IOException expected) {</span> | 
|  | <span class="source-line-no">1275</span><span id="line-1275">      // expected</span> | 
|  | <span class="source-line-no">1276</span><span id="line-1276">    }</span> | 
|  | <span class="source-line-no">1277</span><span id="line-1277">    // The WAL is hosed now. It has two edits appended. We cannot roll the log without it</span> | 
|  | <span class="source-line-no">1278</span><span id="line-1278">    // throwing a DroppedSnapshotException to force an abort. Just clean up the mess.</span> | 
|  | <span class="source-line-no">1279</span><span id="line-1279">    region.close(true);</span> | 
|  | <span class="source-line-no">1280</span><span id="line-1280">    wal.close();</span> | 
|  | <span class="source-line-no">1281</span><span id="line-1281">    // release the snapshot and active segment, so netty will not report memory leak</span> | 
|  | <span class="source-line-no">1282</span><span id="line-1282">    for (HStore store : region.getStores()) {</span> | 
|  | <span class="source-line-no">1283</span><span id="line-1283">      AbstractMemStore memstore = (AbstractMemStore) store.memstore;</span> | 
|  | <span class="source-line-no">1284</span><span id="line-1284">      memstore.doClearSnapShot();</span> | 
|  | <span class="source-line-no">1285</span><span id="line-1285">      memstore.close();</span> | 
|  | <span class="source-line-no">1286</span><span id="line-1286">    }</span> | 
|  | <span class="source-line-no">1287</span><span id="line-1287"></span> | 
|  | <span class="source-line-no">1288</span><span id="line-1288">    // 2. Test case where START_FLUSH succeeds but COMMIT_FLUSH will throw exception</span> | 
|  | <span class="source-line-no">1289</span><span id="line-1289">    wal.flushActions = new FlushAction[] { FlushAction.COMMIT_FLUSH };</span> | 
|  | <span class="source-line-no">1290</span><span id="line-1290">    wal = new FailAppendFlushMarkerWAL(FileSystem.get(walConf), CommonFSUtils.getRootDir(walConf),</span> | 
|  | <span class="source-line-no">1291</span><span id="line-1291">      method, walConf);</span> | 
|  | <span class="source-line-no">1292</span><span id="line-1292">    wal.init();</span> | 
|  | <span class="source-line-no">1293</span><span id="line-1293">    this.region = initHRegion(tableName, HConstants.EMPTY_START_ROW, HConstants.EMPTY_END_ROW, CONF,</span> | 
|  | <span class="source-line-no">1294</span><span id="line-1294">      false, Durability.USE_DEFAULT, wal, family);</span> | 
|  | <span class="source-line-no">1295</span><span id="line-1295">    region.put(put);</span> | 
|  | <span class="source-line-no">1296</span><span id="line-1296">    // 3. Test case where ABORT_FLUSH will throw exception.</span> | 
|  | <span class="source-line-no">1297</span><span id="line-1297">    // Even if ABORT_FLUSH throws exception, we should not fail with IOE, but continue with</span> | 
|  | <span class="source-line-no">1298</span><span id="line-1298">    // DroppedSnapshotException. Below COMMIT_FLUSH will cause flush to abort</span> | 
|  | <span class="source-line-no">1299</span><span id="line-1299">    wal.flushActions = new FlushAction[] { FlushAction.COMMIT_FLUSH, FlushAction.ABORT_FLUSH };</span> | 
|  | <span class="source-line-no">1300</span><span id="line-1300"></span> | 
|  | <span class="source-line-no">1301</span><span id="line-1301">    // we expect this exception, since we were able to write the snapshot, but failed to</span> | 
|  | <span class="source-line-no">1302</span><span id="line-1302">    // write the flush marker to WAL</span> | 
|  | <span class="source-line-no">1303</span><span id="line-1303">    assertThrows(DroppedSnapshotException.class, () -> region.flush(true));</span> | 
|  | <span class="source-line-no">1304</span><span id="line-1304"></span> | 
|  | <span class="source-line-no">1305</span><span id="line-1305">    region.close(true);</span> | 
|  | <span class="source-line-no">1306</span><span id="line-1306">    // release the snapshot and active segment, so netty will not report memory leak</span> | 
|  | <span class="source-line-no">1307</span><span id="line-1307">    for (HStore store : region.getStores()) {</span> | 
|  | <span class="source-line-no">1308</span><span id="line-1308">      AbstractMemStore memstore = (AbstractMemStore) store.memstore;</span> | 
|  | <span class="source-line-no">1309</span><span id="line-1309">      memstore.doClearSnapShot();</span> | 
|  | <span class="source-line-no">1310</span><span id="line-1310">      memstore.close();</span> | 
|  | <span class="source-line-no">1311</span><span id="line-1311">    }</span> | 
|  | <span class="source-line-no">1312</span><span id="line-1312">    region = null;</span> | 
|  | <span class="source-line-no">1313</span><span id="line-1313">  }</span> | 
|  | <span class="source-line-no">1314</span><span id="line-1314"></span> | 
|  | <span class="source-line-no">1315</span><span id="line-1315">  @Test</span> | 
|  | <span class="source-line-no">1316</span><span id="line-1316">  public void testGetWhileRegionClose() throws IOException {</span> | 
|  | <span class="source-line-no">1317</span><span id="line-1317">    Configuration hc = initSplit();</span> | 
|  | <span class="source-line-no">1318</span><span id="line-1318">    int numRows = 100;</span> | 
|  | <span class="source-line-no">1319</span><span id="line-1319">    byte[][] families = { fam1, fam2, fam3 };</span> | 
|  | <span class="source-line-no">1320</span><span id="line-1320"></span> | 
|  | <span class="source-line-no">1321</span><span id="line-1321">    // Setting up region</span> | 
|  | <span class="source-line-no">1322</span><span id="line-1322">    this.region = initHRegion(tableName, method, hc, families);</span> | 
|  | <span class="source-line-no">1323</span><span id="line-1323">    // Put data in region</span> | 
|  | <span class="source-line-no">1324</span><span id="line-1324">    final int startRow = 100;</span> | 
|  | <span class="source-line-no">1325</span><span id="line-1325">    putData(startRow, numRows, qual1, families);</span> | 
|  | <span class="source-line-no">1326</span><span id="line-1326">    putData(startRow, numRows, qual2, families);</span> | 
|  | <span class="source-line-no">1327</span><span id="line-1327">    putData(startRow, numRows, qual3, families);</span> | 
|  | <span class="source-line-no">1328</span><span id="line-1328">    final AtomicBoolean done = new AtomicBoolean(false);</span> | 
|  | <span class="source-line-no">1329</span><span id="line-1329">    final AtomicInteger gets = new AtomicInteger(0);</span> | 
|  | <span class="source-line-no">1330</span><span id="line-1330">    GetTillDoneOrException[] threads = new GetTillDoneOrException[10];</span> | 
|  | <span class="source-line-no">1331</span><span id="line-1331">    try {</span> | 
|  | <span class="source-line-no">1332</span><span id="line-1332">      // Set ten threads running concurrently getting from the region.</span> | 
|  | <span class="source-line-no">1333</span><span id="line-1333">      for (int i = 0; i < threads.length / 2; i++) {</span> | 
|  | <span class="source-line-no">1334</span><span id="line-1334">        threads[i] = new GetTillDoneOrException(i, Bytes.toBytes("" + startRow), done, gets);</span> | 
|  | <span class="source-line-no">1335</span><span id="line-1335">        threads[i].setDaemon(true);</span> | 
|  | <span class="source-line-no">1336</span><span id="line-1336">        threads[i].start();</span> | 
|  | <span class="source-line-no">1337</span><span id="line-1337">      }</span> | 
|  | <span class="source-line-no">1338</span><span id="line-1338">      // Artificially make the condition by setting closing flag explicitly.</span> | 
|  | <span class="source-line-no">1339</span><span id="line-1339">      // I can't make the issue happen with a call to region.close().</span> | 
|  | <span class="source-line-no">1340</span><span id="line-1340">      this.region.closing.set(true);</span> | 
|  | <span class="source-line-no">1341</span><span id="line-1341">      for (int i = threads.length / 2; i < threads.length; i++) {</span> | 
|  | <span class="source-line-no">1342</span><span id="line-1342">        threads[i] = new GetTillDoneOrException(i, Bytes.toBytes("" + startRow), done, gets);</span> | 
|  | <span class="source-line-no">1343</span><span id="line-1343">        threads[i].setDaemon(true);</span> | 
|  | <span class="source-line-no">1344</span><span id="line-1344">        threads[i].start();</span> | 
|  | <span class="source-line-no">1345</span><span id="line-1345">      }</span> | 
|  | <span class="source-line-no">1346</span><span id="line-1346">    } finally {</span> | 
|  | <span class="source-line-no">1347</span><span id="line-1347">      if (this.region != null) {</span> | 
|  | <span class="source-line-no">1348</span><span id="line-1348">        HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">1349</span><span id="line-1349">        this.region = null;</span> | 
|  | <span class="source-line-no">1350</span><span id="line-1350">      }</span> | 
|  | <span class="source-line-no">1351</span><span id="line-1351">    }</span> | 
|  | <span class="source-line-no">1352</span><span id="line-1352">    done.set(true);</span> | 
|  | <span class="source-line-no">1353</span><span id="line-1353">    for (GetTillDoneOrException t : threads) {</span> | 
|  | <span class="source-line-no">1354</span><span id="line-1354">      try {</span> | 
|  | <span class="source-line-no">1355</span><span id="line-1355">        t.join();</span> | 
|  | <span class="source-line-no">1356</span><span id="line-1356">      } catch (InterruptedException e) {</span> | 
|  | <span class="source-line-no">1357</span><span id="line-1357">        e.printStackTrace();</span> | 
|  | <span class="source-line-no">1358</span><span id="line-1358">      }</span> | 
|  | <span class="source-line-no">1359</span><span id="line-1359">      if (t.e != null) {</span> | 
|  | <span class="source-line-no">1360</span><span id="line-1360">        LOG.info("Exception=" + t.e);</span> | 
|  | <span class="source-line-no">1361</span><span id="line-1361">        assertFalse("Found a NPE in " + t.getName(), t.e instanceof NullPointerException);</span> | 
|  | <span class="source-line-no">1362</span><span id="line-1362">      }</span> | 
|  | <span class="source-line-no">1363</span><span id="line-1363">    }</span> | 
|  | <span class="source-line-no">1364</span><span id="line-1364">  }</span> | 
|  | <span class="source-line-no">1365</span><span id="line-1365"></span> | 
|  | <span class="source-line-no">1366</span><span id="line-1366">  /*</span> | 
|  | <span class="source-line-no">1367</span><span id="line-1367">   * Thread that does get on single row until 'done' flag is flipped. If an exception causes us to</span> | 
|  | <span class="source-line-no">1368</span><span id="line-1368">   * fail, it records it.</span> | 
|  | <span class="source-line-no">1369</span><span id="line-1369">   */</span> | 
|  | <span class="source-line-no">1370</span><span id="line-1370">  class GetTillDoneOrException extends Thread {</span> | 
|  | <span class="source-line-no">1371</span><span id="line-1371">    private final Get g;</span> | 
|  | <span class="source-line-no">1372</span><span id="line-1372">    private final AtomicBoolean done;</span> | 
|  | <span class="source-line-no">1373</span><span id="line-1373">    private final AtomicInteger count;</span> | 
|  | <span class="source-line-no">1374</span><span id="line-1374">    private Exception e;</span> | 
|  | <span class="source-line-no">1375</span><span id="line-1375"></span> | 
|  | <span class="source-line-no">1376</span><span id="line-1376">    GetTillDoneOrException(final int i, final byte[] r, final AtomicBoolean d,</span> | 
|  | <span class="source-line-no">1377</span><span id="line-1377">      final AtomicInteger c) {</span> | 
|  | <span class="source-line-no">1378</span><span id="line-1378">      super("getter." + i);</span> | 
|  | <span class="source-line-no">1379</span><span id="line-1379">      this.g = new Get(r);</span> | 
|  | <span class="source-line-no">1380</span><span id="line-1380">      this.done = d;</span> | 
|  | <span class="source-line-no">1381</span><span id="line-1381">      this.count = c;</span> | 
|  | <span class="source-line-no">1382</span><span id="line-1382">    }</span> | 
|  | <span class="source-line-no">1383</span><span id="line-1383"></span> | 
|  | <span class="source-line-no">1384</span><span id="line-1384">    @Override</span> | 
|  | <span class="source-line-no">1385</span><span id="line-1385">    public void run() {</span> | 
|  | <span class="source-line-no">1386</span><span id="line-1386">      while (!this.done.get()) {</span> | 
|  | <span class="source-line-no">1387</span><span id="line-1387">        try {</span> | 
|  | <span class="source-line-no">1388</span><span id="line-1388">          assertTrue(region.get(g).size() > 0);</span> | 
|  | <span class="source-line-no">1389</span><span id="line-1389">          this.count.incrementAndGet();</span> | 
|  | <span class="source-line-no">1390</span><span id="line-1390">        } catch (Exception e) {</span> | 
|  | <span class="source-line-no">1391</span><span id="line-1391">          this.e = e;</span> | 
|  | <span class="source-line-no">1392</span><span id="line-1392">          break;</span> | 
|  | <span class="source-line-no">1393</span><span id="line-1393">        }</span> | 
|  | <span class="source-line-no">1394</span><span id="line-1394">      }</span> | 
|  | <span class="source-line-no">1395</span><span id="line-1395">    }</span> | 
|  | <span class="source-line-no">1396</span><span id="line-1396">  }</span> | 
|  | <span class="source-line-no">1397</span><span id="line-1397"></span> | 
|  | <span class="source-line-no">1398</span><span id="line-1398">  /*</span> | 
|  | <span class="source-line-no">1399</span><span id="line-1399">   * An involved filter test. Has multiple column families and deletes in mix.</span> | 
|  | <span class="source-line-no">1400</span><span id="line-1400">   */</span> | 
|  | <span class="source-line-no">1401</span><span id="line-1401">  @Test</span> | 
|  | <span class="source-line-no">1402</span><span id="line-1402">  public void testWeirdCacheBehaviour() throws Exception {</span> | 
|  | <span class="source-line-no">1403</span><span id="line-1403">    final TableName tableName = TableName.valueOf(name.getMethodName());</span> | 
|  | <span class="source-line-no">1404</span><span id="line-1404">    byte[][] FAMILIES = new byte[][] { Bytes.toBytes("trans-blob"), Bytes.toBytes("trans-type"),</span> | 
|  | <span class="source-line-no">1405</span><span id="line-1405">      Bytes.toBytes("trans-date"), Bytes.toBytes("trans-tags"), Bytes.toBytes("trans-group") };</span> | 
|  | <span class="source-line-no">1406</span><span id="line-1406">    this.region = initHRegion(tableName, method, CONF, FAMILIES);</span> | 
|  | <span class="source-line-no">1407</span><span id="line-1407">    String value = "this is the value";</span> | 
|  | <span class="source-line-no">1408</span><span id="line-1408">    String value2 = "this is some other value";</span> | 
|  | <span class="source-line-no">1409</span><span id="line-1409">    String keyPrefix1 = "prefix1";</span> | 
|  | <span class="source-line-no">1410</span><span id="line-1410">    String keyPrefix2 = "prefix2";</span> | 
|  | <span class="source-line-no">1411</span><span id="line-1411">    String keyPrefix3 = "prefix3";</span> | 
|  | <span class="source-line-no">1412</span><span id="line-1412">    putRows(this.region, 3, value, keyPrefix1);</span> | 
|  | <span class="source-line-no">1413</span><span id="line-1413">    putRows(this.region, 3, value, keyPrefix2);</span> | 
|  | <span class="source-line-no">1414</span><span id="line-1414">    putRows(this.region, 3, value, keyPrefix3);</span> | 
|  | <span class="source-line-no">1415</span><span id="line-1415">    putRows(this.region, 3, value2, keyPrefix1);</span> | 
|  | <span class="source-line-no">1416</span><span id="line-1416">    putRows(this.region, 3, value2, keyPrefix2);</span> | 
|  | <span class="source-line-no">1417</span><span id="line-1417">    putRows(this.region, 3, value2, keyPrefix3);</span> | 
|  | <span class="source-line-no">1418</span><span id="line-1418">    System.out.println("Checking values for key: " + keyPrefix1);</span> | 
|  | <span class="source-line-no">1419</span><span id="line-1419">    assertEquals("Got back incorrect number of rows from scan", 3,</span> | 
|  | <span class="source-line-no">1420</span><span id="line-1420">      getNumberOfRows(keyPrefix1, value2, this.region));</span> | 
|  | <span class="source-line-no">1421</span><span id="line-1421">    System.out.println("Checking values for key: " + keyPrefix2);</span> | 
|  | <span class="source-line-no">1422</span><span id="line-1422">    assertEquals("Got back incorrect number of rows from scan", 3,</span> | 
|  | <span class="source-line-no">1423</span><span id="line-1423">      getNumberOfRows(keyPrefix2, value2, this.region));</span> | 
|  | <span class="source-line-no">1424</span><span id="line-1424">    System.out.println("Checking values for key: " + keyPrefix3);</span> | 
|  | <span class="source-line-no">1425</span><span id="line-1425">    assertEquals("Got back incorrect number of rows from scan", 3,</span> | 
|  | <span class="source-line-no">1426</span><span id="line-1426">      getNumberOfRows(keyPrefix3, value2, this.region));</span> | 
|  | <span class="source-line-no">1427</span><span id="line-1427">    deleteColumns(this.region, value2, keyPrefix1);</span> | 
|  | <span class="source-line-no">1428</span><span id="line-1428">    deleteColumns(this.region, value2, keyPrefix2);</span> | 
|  | <span class="source-line-no">1429</span><span id="line-1429">    deleteColumns(this.region, value2, keyPrefix3);</span> | 
|  | <span class="source-line-no">1430</span><span id="line-1430">    System.out.println("Starting important checks.....");</span> | 
|  | <span class="source-line-no">1431</span><span id="line-1431">    assertEquals("Got back incorrect number of rows from scan: " + keyPrefix1, 0,</span> | 
|  | <span class="source-line-no">1432</span><span id="line-1432">      getNumberOfRows(keyPrefix1, value2, this.region));</span> | 
|  | <span class="source-line-no">1433</span><span id="line-1433">    assertEquals("Got back incorrect number of rows from scan: " + keyPrefix2, 0,</span> | 
|  | <span class="source-line-no">1434</span><span id="line-1434">      getNumberOfRows(keyPrefix2, value2, this.region));</span> | 
|  | <span class="source-line-no">1435</span><span id="line-1435">    assertEquals("Got back incorrect number of rows from scan: " + keyPrefix3, 0,</span> | 
|  | <span class="source-line-no">1436</span><span id="line-1436">      getNumberOfRows(keyPrefix3, value2, this.region));</span> | 
|  | <span class="source-line-no">1437</span><span id="line-1437">  }</span> | 
|  | <span class="source-line-no">1438</span><span id="line-1438"></span> | 
|  | <span class="source-line-no">1439</span><span id="line-1439">  @Test</span> | 
|  | <span class="source-line-no">1440</span><span id="line-1440">  public void testAppendWithReadOnlyTable() throws Exception {</span> | 
|  | <span class="source-line-no">1441</span><span id="line-1441">    final TableName tableName = TableName.valueOf(name.getMethodName());</span> | 
|  | <span class="source-line-no">1442</span><span id="line-1442">    this.region = initHRegion(tableName, method, CONF, true, Bytes.toBytes("somefamily"));</span> | 
|  | <span class="source-line-no">1443</span><span id="line-1443">    boolean exceptionCaught = false;</span> | 
|  | <span class="source-line-no">1444</span><span id="line-1444">    Append append = new Append(Bytes.toBytes("somerow"));</span> | 
|  | <span class="source-line-no">1445</span><span id="line-1445">    append.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">1446</span><span id="line-1446">    append.addColumn(Bytes.toBytes("somefamily"), Bytes.toBytes("somequalifier"),</span> | 
|  | <span class="source-line-no">1447</span><span id="line-1447">      Bytes.toBytes("somevalue"));</span> | 
|  | <span class="source-line-no">1448</span><span id="line-1448">    try {</span> | 
|  | <span class="source-line-no">1449</span><span id="line-1449">      region.append(append);</span> | 
|  | <span class="source-line-no">1450</span><span id="line-1450">    } catch (IOException e) {</span> | 
|  | <span class="source-line-no">1451</span><span id="line-1451">      exceptionCaught = true;</span> | 
|  | <span class="source-line-no">1452</span><span id="line-1452">    }</span> | 
|  | <span class="source-line-no">1453</span><span id="line-1453">    assertTrue(exceptionCaught == true);</span> | 
|  | <span class="source-line-no">1454</span><span id="line-1454">  }</span> | 
|  | <span class="source-line-no">1455</span><span id="line-1455"></span> | 
|  | <span class="source-line-no">1456</span><span id="line-1456">  @Test</span> | 
|  | <span class="source-line-no">1457</span><span id="line-1457">  public void testIncrWithReadOnlyTable() throws Exception {</span> | 
|  | <span class="source-line-no">1458</span><span id="line-1458">    final TableName tableName = TableName.valueOf(name.getMethodName());</span> | 
|  | <span class="source-line-no">1459</span><span id="line-1459">    this.region = initHRegion(tableName, method, CONF, true, Bytes.toBytes("somefamily"));</span> | 
|  | <span class="source-line-no">1460</span><span id="line-1460">    boolean exceptionCaught = false;</span> | 
|  | <span class="source-line-no">1461</span><span id="line-1461">    Increment inc = new Increment(Bytes.toBytes("somerow"));</span> | 
|  | <span class="source-line-no">1462</span><span id="line-1462">    inc.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">1463</span><span id="line-1463">    inc.addColumn(Bytes.toBytes("somefamily"), Bytes.toBytes("somequalifier"), 1L);</span> | 
|  | <span class="source-line-no">1464</span><span id="line-1464">    try {</span> | 
|  | <span class="source-line-no">1465</span><span id="line-1465">      region.increment(inc);</span> | 
|  | <span class="source-line-no">1466</span><span id="line-1466">    } catch (IOException e) {</span> | 
|  | <span class="source-line-no">1467</span><span id="line-1467">      exceptionCaught = true;</span> | 
|  | <span class="source-line-no">1468</span><span id="line-1468">    }</span> | 
|  | <span class="source-line-no">1469</span><span id="line-1469">    assertTrue(exceptionCaught == true);</span> | 
|  | <span class="source-line-no">1470</span><span id="line-1470">  }</span> | 
|  | <span class="source-line-no">1471</span><span id="line-1471"></span> | 
|  | <span class="source-line-no">1472</span><span id="line-1472">  private void deleteColumns(HRegion r, String value, String keyPrefix) throws IOException {</span> | 
|  | <span class="source-line-no">1473</span><span id="line-1473">    int count = 0;</span> | 
|  | <span class="source-line-no">1474</span><span id="line-1474">    try (InternalScanner scanner = buildScanner(keyPrefix, value, r)) {</span> | 
|  | <span class="source-line-no">1475</span><span id="line-1475">      boolean more = false;</span> | 
|  | <span class="source-line-no">1476</span><span id="line-1476">      List<Cell> results = new ArrayList<>();</span> | 
|  | <span class="source-line-no">1477</span><span id="line-1477">      do {</span> | 
|  | <span class="source-line-no">1478</span><span id="line-1478">        more = scanner.next(results);</span> | 
|  | <span class="source-line-no">1479</span><span id="line-1479">        if (results != null && !results.isEmpty()) {</span> | 
|  | <span class="source-line-no">1480</span><span id="line-1480">          count++;</span> | 
|  | <span class="source-line-no">1481</span><span id="line-1481">        } else {</span> | 
|  | <span class="source-line-no">1482</span><span id="line-1482">          break;</span> | 
|  | <span class="source-line-no">1483</span><span id="line-1483">        }</span> | 
|  | <span class="source-line-no">1484</span><span id="line-1484">        Delete delete = new Delete(CellUtil.cloneRow(results.get(0)));</span> | 
|  | <span class="source-line-no">1485</span><span id="line-1485">        delete.addColumn(Bytes.toBytes("trans-tags"), Bytes.toBytes("qual2"));</span> | 
|  | <span class="source-line-no">1486</span><span id="line-1486">        r.delete(delete);</span> | 
|  | <span class="source-line-no">1487</span><span id="line-1487">        results.clear();</span> | 
|  | <span class="source-line-no">1488</span><span id="line-1488">      } while (more);</span> | 
|  | <span class="source-line-no">1489</span><span id="line-1489">    }</span> | 
|  | <span class="source-line-no">1490</span><span id="line-1490">    assertEquals("Did not perform correct number of deletes", 3, count);</span> | 
|  | <span class="source-line-no">1491</span><span id="line-1491">  }</span> | 
|  | <span class="source-line-no">1492</span><span id="line-1492"></span> | 
|  | <span class="source-line-no">1493</span><span id="line-1493">  private int getNumberOfRows(String keyPrefix, String value, HRegion r) throws Exception {</span> | 
|  | <span class="source-line-no">1494</span><span id="line-1494">    try (InternalScanner resultScanner = buildScanner(keyPrefix, value, r)) {</span> | 
|  | <span class="source-line-no">1495</span><span id="line-1495">      int numberOfResults = 0;</span> | 
|  | <span class="source-line-no">1496</span><span id="line-1496">      List<Cell> results = new ArrayList<>();</span> | 
|  | <span class="source-line-no">1497</span><span id="line-1497">      boolean more = false;</span> | 
|  | <span class="source-line-no">1498</span><span id="line-1498">      do {</span> | 
|  | <span class="source-line-no">1499</span><span id="line-1499">        more = resultScanner.next(results);</span> | 
|  | <span class="source-line-no">1500</span><span id="line-1500">        if (results != null && !results.isEmpty()) {</span> | 
|  | <span class="source-line-no">1501</span><span id="line-1501">          numberOfResults++;</span> | 
|  | <span class="source-line-no">1502</span><span id="line-1502">        } else {</span> | 
|  | <span class="source-line-no">1503</span><span id="line-1503">          break;</span> | 
|  | <span class="source-line-no">1504</span><span id="line-1504">        }</span> | 
|  | <span class="source-line-no">1505</span><span id="line-1505">        for (Cell kv : results) {</span> | 
|  | <span class="source-line-no">1506</span><span id="line-1506">          LOG.info("kv=" + kv.toString() + ", " + Bytes.toString(CellUtil.cloneValue(kv)));</span> | 
|  | <span class="source-line-no">1507</span><span id="line-1507">        }</span> | 
|  | <span class="source-line-no">1508</span><span id="line-1508">        results.clear();</span> | 
|  | <span class="source-line-no">1509</span><span id="line-1509">      } while (more);</span> | 
|  | <span class="source-line-no">1510</span><span id="line-1510">      return numberOfResults;</span> | 
|  | <span class="source-line-no">1511</span><span id="line-1511">    }</span> | 
|  | <span class="source-line-no">1512</span><span id="line-1512">  }</span> | 
|  | <span class="source-line-no">1513</span><span id="line-1513"></span> | 
|  | <span class="source-line-no">1514</span><span id="line-1514">  private InternalScanner buildScanner(String keyPrefix, String value, HRegion r)</span> | 
|  | <span class="source-line-no">1515</span><span id="line-1515">    throws IOException {</span> | 
|  | <span class="source-line-no">1516</span><span id="line-1516">    // Defaults FilterList.Operator.MUST_PASS_ALL.</span> | 
|  | <span class="source-line-no">1517</span><span id="line-1517">    FilterList allFilters = new FilterList();</span> | 
|  | <span class="source-line-no">1518</span><span id="line-1518">    allFilters.addFilter(new PrefixFilter(Bytes.toBytes(keyPrefix)));</span> | 
|  | <span class="source-line-no">1519</span><span id="line-1519">    // Only return rows where this column value exists in the row.</span> | 
|  | <span class="source-line-no">1520</span><span id="line-1520">    SingleColumnValueFilter filter = new SingleColumnValueFilter(Bytes.toBytes("trans-tags"),</span> | 
|  | <span class="source-line-no">1521</span><span id="line-1521">      Bytes.toBytes("qual2"), CompareOperator.EQUAL, Bytes.toBytes(value));</span> | 
|  | <span class="source-line-no">1522</span><span id="line-1522">    filter.setFilterIfMissing(true);</span> | 
|  | <span class="source-line-no">1523</span><span id="line-1523">    allFilters.addFilter(filter);</span> | 
|  | <span class="source-line-no">1524</span><span id="line-1524">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">1525</span><span id="line-1525">    scan.addFamily(Bytes.toBytes("trans-blob"));</span> | 
|  | <span class="source-line-no">1526</span><span id="line-1526">    scan.addFamily(Bytes.toBytes("trans-type"));</span> | 
|  | <span class="source-line-no">1527</span><span id="line-1527">    scan.addFamily(Bytes.toBytes("trans-date"));</span> | 
|  | <span class="source-line-no">1528</span><span id="line-1528">    scan.addFamily(Bytes.toBytes("trans-tags"));</span> | 
|  | <span class="source-line-no">1529</span><span id="line-1529">    scan.addFamily(Bytes.toBytes("trans-group"));</span> | 
|  | <span class="source-line-no">1530</span><span id="line-1530">    scan.setFilter(allFilters);</span> | 
|  | <span class="source-line-no">1531</span><span id="line-1531">    return r.getScanner(scan);</span> | 
|  | <span class="source-line-no">1532</span><span id="line-1532">  }</span> | 
|  | <span class="source-line-no">1533</span><span id="line-1533"></span> | 
|  | <span class="source-line-no">1534</span><span id="line-1534">  private void putRows(HRegion r, int numRows, String value, String key) throws IOException {</span> | 
|  | <span class="source-line-no">1535</span><span id="line-1535">    for (int i = 0; i < numRows; i++) {</span> | 
|  | <span class="source-line-no">1536</span><span id="line-1536">      String row = key + "_" + i/* UUID.randomUUID().toString() */;</span> | 
|  | <span class="source-line-no">1537</span><span id="line-1537">      System.out.println(String.format("Saving row: %s, with value %s", row, value));</span> | 
|  | <span class="source-line-no">1538</span><span id="line-1538">      Put put = new Put(Bytes.toBytes(row));</span> | 
|  | <span class="source-line-no">1539</span><span id="line-1539">      put.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">1540</span><span id="line-1540">      put.addColumn(Bytes.toBytes("trans-blob"), null, Bytes.toBytes("value for blob"));</span> | 
|  | <span class="source-line-no">1541</span><span id="line-1541">      put.addColumn(Bytes.toBytes("trans-type"), null, Bytes.toBytes("statement"));</span> | 
|  | <span class="source-line-no">1542</span><span id="line-1542">      put.addColumn(Bytes.toBytes("trans-date"), null, Bytes.toBytes("20090921010101999"));</span> | 
|  | <span class="source-line-no">1543</span><span id="line-1543">      put.addColumn(Bytes.toBytes("trans-tags"), Bytes.toBytes("qual2"), Bytes.toBytes(value));</span> | 
|  | <span class="source-line-no">1544</span><span id="line-1544">      put.addColumn(Bytes.toBytes("trans-group"), null, Bytes.toBytes("adhocTransactionGroupId"));</span> | 
|  | <span class="source-line-no">1545</span><span id="line-1545">      r.put(put);</span> | 
|  | <span class="source-line-no">1546</span><span id="line-1546">    }</span> | 
|  | <span class="source-line-no">1547</span><span id="line-1547">  }</span> | 
|  | <span class="source-line-no">1548</span><span id="line-1548"></span> | 
|  | <span class="source-line-no">1549</span><span id="line-1549">  @Test</span> | 
|  | <span class="source-line-no">1550</span><span id="line-1550">  public void testFamilyWithAndWithoutColon() throws Exception {</span> | 
|  | <span class="source-line-no">1551</span><span id="line-1551">    byte[] cf = Bytes.toBytes(COLUMN_FAMILY);</span> | 
|  | <span class="source-line-no">1552</span><span id="line-1552">    this.region = initHRegion(tableName, method, CONF, cf);</span> | 
|  | <span class="source-line-no">1553</span><span id="line-1553">    Put p = new Put(tableName.toBytes());</span> | 
|  | <span class="source-line-no">1554</span><span id="line-1554">    byte[] cfwithcolon = Bytes.toBytes(COLUMN_FAMILY + ":");</span> | 
|  | <span class="source-line-no">1555</span><span id="line-1555">    p.addColumn(cfwithcolon, cfwithcolon, cfwithcolon);</span> | 
|  | <span class="source-line-no">1556</span><span id="line-1556">    boolean exception = false;</span> | 
|  | <span class="source-line-no">1557</span><span id="line-1557">    try {</span> | 
|  | <span class="source-line-no">1558</span><span id="line-1558">      this.region.put(p);</span> | 
|  | <span class="source-line-no">1559</span><span id="line-1559">    } catch (NoSuchColumnFamilyException e) {</span> | 
|  | <span class="source-line-no">1560</span><span id="line-1560">      exception = true;</span> | 
|  | <span class="source-line-no">1561</span><span id="line-1561">    }</span> | 
|  | <span class="source-line-no">1562</span><span id="line-1562">    assertTrue(exception);</span> | 
|  | <span class="source-line-no">1563</span><span id="line-1563">  }</span> | 
|  | <span class="source-line-no">1564</span><span id="line-1564"></span> | 
|  | <span class="source-line-no">1565</span><span id="line-1565">  @Test</span> | 
|  | <span class="source-line-no">1566</span><span id="line-1566">  public void testBatchPut_whileNoRowLocksHeld() throws IOException {</span> | 
|  | <span class="source-line-no">1567</span><span id="line-1567">    final Put[] puts = new Put[10];</span> | 
|  | <span class="source-line-no">1568</span><span id="line-1568">    MetricsWALSource source = CompatibilitySingletonFactory.getInstance(MetricsWALSource.class);</span> | 
|  | <span class="source-line-no">1569</span><span id="line-1569">    long syncs = prepareRegionForBachPut(puts, source, false);</span> | 
|  | <span class="source-line-no">1570</span><span id="line-1570"></span> | 
|  | <span class="source-line-no">1571</span><span id="line-1571">    OperationStatus[] codes = this.region.batchMutate(puts);</span> | 
|  | <span class="source-line-no">1572</span><span id="line-1572">    assertEquals(10, codes.length);</span> | 
|  | <span class="source-line-no">1573</span><span id="line-1573">    for (int i = 0; i < 10; i++) {</span> | 
|  | <span class="source-line-no">1574</span><span id="line-1574">      assertEquals(OperationStatusCode.SUCCESS, codes[i].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">1575</span><span id="line-1575">    }</span> | 
|  | <span class="source-line-no">1576</span><span id="line-1576">    metricsAssertHelper.assertCounter("syncTimeNumOps", syncs + 1, source);</span> | 
|  | <span class="source-line-no">1577</span><span id="line-1577"></span> | 
|  | <span class="source-line-no">1578</span><span id="line-1578">    LOG.info("Next a batch put with one invalid family");</span> | 
|  | <span class="source-line-no">1579</span><span id="line-1579">    puts[5].addColumn(Bytes.toBytes("BAD_CF"), qual, value);</span> | 
|  | <span class="source-line-no">1580</span><span id="line-1580">    codes = this.region.batchMutate(puts);</span> | 
|  | <span class="source-line-no">1581</span><span id="line-1581">    assertEquals(10, codes.length);</span> | 
|  | <span class="source-line-no">1582</span><span id="line-1582">    for (int i = 0; i < 10; i++) {</span> | 
|  | <span class="source-line-no">1583</span><span id="line-1583">      assertEquals((i == 5) ? OperationStatusCode.BAD_FAMILY : OperationStatusCode.SUCCESS,</span> | 
|  | <span class="source-line-no">1584</span><span id="line-1584">        codes[i].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">1585</span><span id="line-1585">    }</span> | 
|  | <span class="source-line-no">1586</span><span id="line-1586"></span> | 
|  | <span class="source-line-no">1587</span><span id="line-1587">    metricsAssertHelper.assertCounter("syncTimeNumOps", syncs + 2, source);</span> | 
|  | <span class="source-line-no">1588</span><span id="line-1588">  }</span> | 
|  | <span class="source-line-no">1589</span><span id="line-1589"></span> | 
|  | <span class="source-line-no">1590</span><span id="line-1590">  @Test</span> | 
|  | <span class="source-line-no">1591</span><span id="line-1591">  public void testBatchPut_whileMultipleRowLocksHeld() throws Exception {</span> | 
|  | <span class="source-line-no">1592</span><span id="line-1592">    final Put[] puts = new Put[10];</span> | 
|  | <span class="source-line-no">1593</span><span id="line-1593">    MetricsWALSource source = CompatibilitySingletonFactory.getInstance(MetricsWALSource.class);</span> | 
|  | <span class="source-line-no">1594</span><span id="line-1594">    long syncs = prepareRegionForBachPut(puts, source, false);</span> | 
|  | <span class="source-line-no">1595</span><span id="line-1595"></span> | 
|  | <span class="source-line-no">1596</span><span id="line-1596">    puts[5].addColumn(Bytes.toBytes("BAD_CF"), qual, value);</span> | 
|  | <span class="source-line-no">1597</span><span id="line-1597"></span> | 
|  | <span class="source-line-no">1598</span><span id="line-1598">    LOG.info("batchPut will have to break into four batches to avoid row locks");</span> | 
|  | <span class="source-line-no">1599</span><span id="line-1599">    RowLock rowLock1 = region.getRowLock(Bytes.toBytes("row_2"));</span> | 
|  | <span class="source-line-no">1600</span><span id="line-1600">    RowLock rowLock2 = region.getRowLock(Bytes.toBytes("row_1"));</span> | 
|  | <span class="source-line-no">1601</span><span id="line-1601">    RowLock rowLock3 = region.getRowLock(Bytes.toBytes("row_3"));</span> | 
|  | <span class="source-line-no">1602</span><span id="line-1602">    RowLock rowLock4 = region.getRowLock(Bytes.toBytes("row_3"), true);</span> | 
|  | <span class="source-line-no">1603</span><span id="line-1603"></span> | 
|  | <span class="source-line-no">1604</span><span id="line-1604">    MultithreadedTestUtil.TestContext ctx = new MultithreadedTestUtil.TestContext(CONF);</span> | 
|  | <span class="source-line-no">1605</span><span id="line-1605">    final AtomicReference<OperationStatus[]> retFromThread = new AtomicReference<>();</span> | 
|  | <span class="source-line-no">1606</span><span id="line-1606">    final CountDownLatch startingPuts = new CountDownLatch(1);</span> | 
|  | <span class="source-line-no">1607</span><span id="line-1607">    final CountDownLatch startingClose = new CountDownLatch(1);</span> | 
|  | <span class="source-line-no">1608</span><span id="line-1608">    TestThread putter = new TestThread(ctx) {</span> | 
|  | <span class="source-line-no">1609</span><span id="line-1609">      @Override</span> | 
|  | <span class="source-line-no">1610</span><span id="line-1610">      public void doWork() throws IOException {</span> | 
|  | <span class="source-line-no">1611</span><span id="line-1611">        startingPuts.countDown();</span> | 
|  | <span class="source-line-no">1612</span><span id="line-1612">        retFromThread.set(region.batchMutate(puts));</span> | 
|  | <span class="source-line-no">1613</span><span id="line-1613">      }</span> | 
|  | <span class="source-line-no">1614</span><span id="line-1614">    };</span> | 
|  | <span class="source-line-no">1615</span><span id="line-1615">    LOG.info("...starting put thread while holding locks");</span> | 
|  | <span class="source-line-no">1616</span><span id="line-1616">    ctx.addThread(putter);</span> | 
|  | <span class="source-line-no">1617</span><span id="line-1617">    ctx.startThreads();</span> | 
|  | <span class="source-line-no">1618</span><span id="line-1618"></span> | 
|  | <span class="source-line-no">1619</span><span id="line-1619">    // Now attempt to close the region from another thread. Prior to HBASE-12565</span> | 
|  | <span class="source-line-no">1620</span><span id="line-1620">    // this would cause the in-progress batchMutate operation to to fail with</span> | 
|  | <span class="source-line-no">1621</span><span id="line-1621">    // exception because it use to release and re-acquire the close-guard lock</span> | 
|  | <span class="source-line-no">1622</span><span id="line-1622">    // between batches. Caller then didn't get status indicating which writes succeeded.</span> | 
|  | <span class="source-line-no">1623</span><span id="line-1623">    // We now expect this thread to block until the batchMutate call finishes.</span> | 
|  | <span class="source-line-no">1624</span><span id="line-1624">    Thread regionCloseThread = new TestThread(ctx) {</span> | 
|  | <span class="source-line-no">1625</span><span id="line-1625">      @Override</span> | 
|  | <span class="source-line-no">1626</span><span id="line-1626">      public void doWork() {</span> | 
|  | <span class="source-line-no">1627</span><span id="line-1627">        try {</span> | 
|  | <span class="source-line-no">1628</span><span id="line-1628">          startingPuts.await();</span> | 
|  | <span class="source-line-no">1629</span><span id="line-1629">          // Give some time for the batch mutate to get in.</span> | 
|  | <span class="source-line-no">1630</span><span id="line-1630">          // We don't want to race with the mutate</span> | 
|  | <span class="source-line-no">1631</span><span id="line-1631">          Thread.sleep(10);</span> | 
|  | <span class="source-line-no">1632</span><span id="line-1632">          startingClose.countDown();</span> | 
|  | <span class="source-line-no">1633</span><span id="line-1633">          HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">1634</span><span id="line-1634">          region = null;</span> | 
|  | <span class="source-line-no">1635</span><span id="line-1635">        } catch (IOException e) {</span> | 
|  | <span class="source-line-no">1636</span><span id="line-1636">          throw new RuntimeException(e);</span> | 
|  | <span class="source-line-no">1637</span><span id="line-1637">        } catch (InterruptedException e) {</span> | 
|  | <span class="source-line-no">1638</span><span id="line-1638">          throw new RuntimeException(e);</span> | 
|  | <span class="source-line-no">1639</span><span id="line-1639">        }</span> | 
|  | <span class="source-line-no">1640</span><span id="line-1640">      }</span> | 
|  | <span class="source-line-no">1641</span><span id="line-1641">    };</span> | 
|  | <span class="source-line-no">1642</span><span id="line-1642">    regionCloseThread.start();</span> | 
|  | <span class="source-line-no">1643</span><span id="line-1643"></span> | 
|  | <span class="source-line-no">1644</span><span id="line-1644">    startingClose.await();</span> | 
|  | <span class="source-line-no">1645</span><span id="line-1645">    startingPuts.await();</span> | 
|  | <span class="source-line-no">1646</span><span id="line-1646">    Thread.sleep(100);</span> | 
|  | <span class="source-line-no">1647</span><span id="line-1647">    LOG.info("...releasing row lock 1, which should let put thread continue");</span> | 
|  | <span class="source-line-no">1648</span><span id="line-1648">    rowLock1.release();</span> | 
|  | <span class="source-line-no">1649</span><span id="line-1649">    rowLock2.release();</span> | 
|  | <span class="source-line-no">1650</span><span id="line-1650">    rowLock3.release();</span> | 
|  | <span class="source-line-no">1651</span><span id="line-1651">    waitForCounter(source, "syncTimeNumOps", syncs + 1);</span> | 
|  | <span class="source-line-no">1652</span><span id="line-1652"></span> | 
|  | <span class="source-line-no">1653</span><span id="line-1653">    LOG.info("...joining on put thread");</span> | 
|  | <span class="source-line-no">1654</span><span id="line-1654">    ctx.stop();</span> | 
|  | <span class="source-line-no">1655</span><span id="line-1655">    regionCloseThread.join();</span> | 
|  | <span class="source-line-no">1656</span><span id="line-1656"></span> | 
|  | <span class="source-line-no">1657</span><span id="line-1657">    OperationStatus[] codes = retFromThread.get();</span> | 
|  | <span class="source-line-no">1658</span><span id="line-1658">    for (int i = 0; i < codes.length; i++) {</span> | 
|  | <span class="source-line-no">1659</span><span id="line-1659">      assertEquals((i == 5) ? OperationStatusCode.BAD_FAMILY : OperationStatusCode.SUCCESS,</span> | 
|  | <span class="source-line-no">1660</span><span id="line-1660">        codes[i].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">1661</span><span id="line-1661">    }</span> | 
|  | <span class="source-line-no">1662</span><span id="line-1662">    rowLock4.release();</span> | 
|  | <span class="source-line-no">1663</span><span id="line-1663">  }</span> | 
|  | <span class="source-line-no">1664</span><span id="line-1664"></span> | 
|  | <span class="source-line-no">1665</span><span id="line-1665">  private void waitForCounter(MetricsWALSource source, String metricName, long expectedCount)</span> | 
|  | <span class="source-line-no">1666</span><span id="line-1666">    throws InterruptedException {</span> | 
|  | <span class="source-line-no">1667</span><span id="line-1667">    long startWait = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">1668</span><span id="line-1668">    long currentCount;</span> | 
|  | <span class="source-line-no">1669</span><span id="line-1669">    while ((currentCount = metricsAssertHelper.getCounter(metricName, source)) < expectedCount) {</span> | 
|  | <span class="source-line-no">1670</span><span id="line-1670">      Thread.sleep(100);</span> | 
|  | <span class="source-line-no">1671</span><span id="line-1671">      if (EnvironmentEdgeManager.currentTime() - startWait > 10000) {</span> | 
|  | <span class="source-line-no">1672</span><span id="line-1672">        fail(String.format("Timed out waiting for '%s' >= '%s', currentCount=%s", metricName,</span> | 
|  | <span class="source-line-no">1673</span><span id="line-1673">          expectedCount, currentCount));</span> | 
|  | <span class="source-line-no">1674</span><span id="line-1674">      }</span> | 
|  | <span class="source-line-no">1675</span><span id="line-1675">    }</span> | 
|  | <span class="source-line-no">1676</span><span id="line-1676">  }</span> | 
|  | <span class="source-line-no">1677</span><span id="line-1677"></span> | 
|  | <span class="source-line-no">1678</span><span id="line-1678">  @Test</span> | 
|  | <span class="source-line-no">1679</span><span id="line-1679">  public void testAtomicBatchPut() throws IOException {</span> | 
|  | <span class="source-line-no">1680</span><span id="line-1680">    final Put[] puts = new Put[10];</span> | 
|  | <span class="source-line-no">1681</span><span id="line-1681">    MetricsWALSource source = CompatibilitySingletonFactory.getInstance(MetricsWALSource.class);</span> | 
|  | <span class="source-line-no">1682</span><span id="line-1682">    long syncs = prepareRegionForBachPut(puts, source, false);</span> | 
|  | <span class="source-line-no">1683</span><span id="line-1683"></span> | 
|  | <span class="source-line-no">1684</span><span id="line-1684">    // 1. Straight forward case, should succeed</span> | 
|  | <span class="source-line-no">1685</span><span id="line-1685">    OperationStatus[] codes = this.region.batchMutate(puts, true);</span> | 
|  | <span class="source-line-no">1686</span><span id="line-1686">    assertEquals(10, codes.length);</span> | 
|  | <span class="source-line-no">1687</span><span id="line-1687">    for (int i = 0; i < 10; i++) {</span> | 
|  | <span class="source-line-no">1688</span><span id="line-1688">      assertEquals(OperationStatusCode.SUCCESS, codes[i].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">1689</span><span id="line-1689">    }</span> | 
|  | <span class="source-line-no">1690</span><span id="line-1690">    metricsAssertHelper.assertCounter("syncTimeNumOps", syncs + 1, source);</span> | 
|  | <span class="source-line-no">1691</span><span id="line-1691"></span> | 
|  | <span class="source-line-no">1692</span><span id="line-1692">    // 2. Failed to get lock</span> | 
|  | <span class="source-line-no">1693</span><span id="line-1693">    RowLock lock = region.getRowLock(Bytes.toBytes("row_" + 3));</span> | 
|  | <span class="source-line-no">1694</span><span id="line-1694">    // Method {@link HRegion#getRowLock(byte[])} is reentrant. As 'row_3' is locked in this</span> | 
|  | <span class="source-line-no">1695</span><span id="line-1695">    // thread, need to run {@link HRegion#batchMutate(HRegion.BatchOperation)} in different thread</span> | 
|  | <span class="source-line-no">1696</span><span id="line-1696">    MultithreadedTestUtil.TestContext ctx = new MultithreadedTestUtil.TestContext(CONF);</span> | 
|  | <span class="source-line-no">1697</span><span id="line-1697">    final AtomicReference<IOException> retFromThread = new AtomicReference<>();</span> | 
|  | <span class="source-line-no">1698</span><span id="line-1698">    final CountDownLatch finishedPuts = new CountDownLatch(1);</span> | 
|  | <span class="source-line-no">1699</span><span id="line-1699">    TestThread putter = new TestThread(ctx) {</span> | 
|  | <span class="source-line-no">1700</span><span id="line-1700">      @Override</span> | 
|  | <span class="source-line-no">1701</span><span id="line-1701">      public void doWork() throws IOException {</span> | 
|  | <span class="source-line-no">1702</span><span id="line-1702">        try {</span> | 
|  | <span class="source-line-no">1703</span><span id="line-1703">          region.batchMutate(puts, true);</span> | 
|  | <span class="source-line-no">1704</span><span id="line-1704">        } catch (IOException ioe) {</span> | 
|  | <span class="source-line-no">1705</span><span id="line-1705">          LOG.error("test failed!", ioe);</span> | 
|  | <span class="source-line-no">1706</span><span id="line-1706">          retFromThread.set(ioe);</span> | 
|  | <span class="source-line-no">1707</span><span id="line-1707">        }</span> | 
|  | <span class="source-line-no">1708</span><span id="line-1708">        finishedPuts.countDown();</span> | 
|  | <span class="source-line-no">1709</span><span id="line-1709">      }</span> | 
|  | <span class="source-line-no">1710</span><span id="line-1710">    };</span> | 
|  | <span class="source-line-no">1711</span><span id="line-1711">    LOG.info("...starting put thread while holding locks");</span> | 
|  | <span class="source-line-no">1712</span><span id="line-1712">    ctx.addThread(putter);</span> | 
|  | <span class="source-line-no">1713</span><span id="line-1713">    ctx.startThreads();</span> | 
|  | <span class="source-line-no">1714</span><span id="line-1714">    LOG.info("...waiting for batch puts while holding locks");</span> | 
|  | <span class="source-line-no">1715</span><span id="line-1715">    try {</span> | 
|  | <span class="source-line-no">1716</span><span id="line-1716">      finishedPuts.await();</span> | 
|  | <span class="source-line-no">1717</span><span id="line-1717">    } catch (InterruptedException e) {</span> | 
|  | <span class="source-line-no">1718</span><span id="line-1718">      LOG.error("Interrupted!", e);</span> | 
|  | <span class="source-line-no">1719</span><span id="line-1719">    } finally {</span> | 
|  | <span class="source-line-no">1720</span><span id="line-1720">      if (lock != null) {</span> | 
|  | <span class="source-line-no">1721</span><span id="line-1721">        lock.release();</span> | 
|  | <span class="source-line-no">1722</span><span id="line-1722">      }</span> | 
|  | <span class="source-line-no">1723</span><span id="line-1723">    }</span> | 
|  | <span class="source-line-no">1724</span><span id="line-1724">    assertNotNull(retFromThread.get());</span> | 
|  | <span class="source-line-no">1725</span><span id="line-1725">    metricsAssertHelper.assertCounter("syncTimeNumOps", syncs + 1, source);</span> | 
|  | <span class="source-line-no">1726</span><span id="line-1726"></span> | 
|  | <span class="source-line-no">1727</span><span id="line-1727">    // 3. Exception thrown in validation</span> | 
|  | <span class="source-line-no">1728</span><span id="line-1728">    LOG.info("Next a batch put with one invalid family");</span> | 
|  | <span class="source-line-no">1729</span><span id="line-1729">    puts[5].addColumn(Bytes.toBytes("BAD_CF"), qual, value);</span> | 
|  | <span class="source-line-no">1730</span><span id="line-1730">    thrown.expect(NoSuchColumnFamilyException.class);</span> | 
|  | <span class="source-line-no">1731</span><span id="line-1731">    this.region.batchMutate(puts, true);</span> | 
|  | <span class="source-line-no">1732</span><span id="line-1732">  }</span> | 
|  | <span class="source-line-no">1733</span><span id="line-1733"></span> | 
|  | <span class="source-line-no">1734</span><span id="line-1734">  @Test</span> | 
|  | <span class="source-line-no">1735</span><span id="line-1735">  public void testBatchPutWithTsSlop() throws Exception {</span> | 
|  | <span class="source-line-no">1736</span><span id="line-1736">    // add data with a timestamp that is too recent for range. Ensure assert</span> | 
|  | <span class="source-line-no">1737</span><span id="line-1737">    CONF.setInt("hbase.hregion.keyvalue.timestamp.slop.millisecs", 1000);</span> | 
|  | <span class="source-line-no">1738</span><span id="line-1738">    final Put[] puts = new Put[10];</span> | 
|  | <span class="source-line-no">1739</span><span id="line-1739">    MetricsWALSource source = CompatibilitySingletonFactory.getInstance(MetricsWALSource.class);</span> | 
|  | <span class="source-line-no">1740</span><span id="line-1740"></span> | 
|  | <span class="source-line-no">1741</span><span id="line-1741">    long syncs = prepareRegionForBachPut(puts, source, true);</span> | 
|  | <span class="source-line-no">1742</span><span id="line-1742"></span> | 
|  | <span class="source-line-no">1743</span><span id="line-1743">    OperationStatus[] codes = this.region.batchMutate(puts);</span> | 
|  | <span class="source-line-no">1744</span><span id="line-1744">    assertEquals(10, codes.length);</span> | 
|  | <span class="source-line-no">1745</span><span id="line-1745">    for (int i = 0; i < 10; i++) {</span> | 
|  | <span class="source-line-no">1746</span><span id="line-1746">      assertEquals(OperationStatusCode.SANITY_CHECK_FAILURE, codes[i].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">1747</span><span id="line-1747">    }</span> | 
|  | <span class="source-line-no">1748</span><span id="line-1748">    metricsAssertHelper.assertCounter("syncTimeNumOps", syncs, source);</span> | 
|  | <span class="source-line-no">1749</span><span id="line-1749">  }</span> | 
|  | <span class="source-line-no">1750</span><span id="line-1750"></span> | 
|  | <span class="source-line-no">1751</span><span id="line-1751">  /** Returns syncs initial syncTimeNumOps */</span> | 
|  | <span class="source-line-no">1752</span><span id="line-1752">  private long prepareRegionForBachPut(final Put[] puts, final MetricsWALSource source,</span> | 
|  | <span class="source-line-no">1753</span><span id="line-1753">    boolean slop) throws IOException {</span> | 
|  | <span class="source-line-no">1754</span><span id="line-1754">    this.region = initHRegion(tableName, method, CONF, COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">1755</span><span id="line-1755"></span> | 
|  | <span class="source-line-no">1756</span><span id="line-1756">    LOG.info("First a batch put with all valid puts");</span> | 
|  | <span class="source-line-no">1757</span><span id="line-1757">    for (int i = 0; i < puts.length; i++) {</span> | 
|  | <span class="source-line-no">1758</span><span id="line-1758">      puts[i] = slop</span> | 
|  | <span class="source-line-no">1759</span><span id="line-1759">        ? new Put(Bytes.toBytes("row_" + i), Long.MAX_VALUE - 100)</span> | 
|  | <span class="source-line-no">1760</span><span id="line-1760">        : new Put(Bytes.toBytes("row_" + i));</span> | 
|  | <span class="source-line-no">1761</span><span id="line-1761">      puts[i].addColumn(COLUMN_FAMILY_BYTES, qual, value);</span> | 
|  | <span class="source-line-no">1762</span><span id="line-1762">    }</span> | 
|  | <span class="source-line-no">1763</span><span id="line-1763"></span> | 
|  | <span class="source-line-no">1764</span><span id="line-1764">    long syncs = metricsAssertHelper.getCounter("syncTimeNumOps", source);</span> | 
|  | <span class="source-line-no">1765</span><span id="line-1765">    metricsAssertHelper.assertCounter("syncTimeNumOps", syncs, source);</span> | 
|  | <span class="source-line-no">1766</span><span id="line-1766">    return syncs;</span> | 
|  | <span class="source-line-no">1767</span><span id="line-1767">  }</span> | 
|  | <span class="source-line-no">1768</span><span id="line-1768"></span> | 
|  | <span class="source-line-no">1769</span><span id="line-1769">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">1770</span><span id="line-1770">  // checkAndMutate tests</span> | 
|  | <span class="source-line-no">1771</span><span id="line-1771">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">1772</span><span id="line-1772">  @Test</span> | 
|  | <span class="source-line-no">1773</span><span id="line-1773">  @Deprecated</span> | 
|  | <span class="source-line-no">1774</span><span id="line-1774">  public void testCheckAndMutate_WithEmptyRowValue() throws IOException {</span> | 
|  | <span class="source-line-no">1775</span><span id="line-1775">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">1776</span><span id="line-1776">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">1777</span><span id="line-1777">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">1778</span><span id="line-1778">    byte[] emptyVal = new byte[] {};</span> | 
|  | <span class="source-line-no">1779</span><span id="line-1779">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">1780</span><span id="line-1780">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">1781</span><span id="line-1781"></span> | 
|  | <span class="source-line-no">1782</span><span id="line-1782">    // Setting up region</span> | 
|  | <span class="source-line-no">1783</span><span id="line-1783">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">1784</span><span id="line-1784">    // Putting empty data in key</span> | 
|  | <span class="source-line-no">1785</span><span id="line-1785">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">1786</span><span id="line-1786">    put.addColumn(fam1, qf1, emptyVal);</span> | 
|  | <span class="source-line-no">1787</span><span id="line-1787"></span> | 
|  | <span class="source-line-no">1788</span><span id="line-1788">    // checkAndPut with empty value</span> | 
|  | <span class="source-line-no">1789</span><span id="line-1789">    boolean res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1790</span><span id="line-1790">      new BinaryComparator(emptyVal), put);</span> | 
|  | <span class="source-line-no">1791</span><span id="line-1791">    assertTrue(res);</span> | 
|  | <span class="source-line-no">1792</span><span id="line-1792"></span> | 
|  | <span class="source-line-no">1793</span><span id="line-1793">    // Putting data in key</span> | 
|  | <span class="source-line-no">1794</span><span id="line-1794">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">1795</span><span id="line-1795">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">1796</span><span id="line-1796"></span> | 
|  | <span class="source-line-no">1797</span><span id="line-1797">    // checkAndPut with correct value</span> | 
|  | <span class="source-line-no">1798</span><span id="line-1798">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1799</span><span id="line-1799">      new BinaryComparator(emptyVal), put);</span> | 
|  | <span class="source-line-no">1800</span><span id="line-1800">    assertTrue(res);</span> | 
|  | <span class="source-line-no">1801</span><span id="line-1801"></span> | 
|  | <span class="source-line-no">1802</span><span id="line-1802">    // not empty anymore</span> | 
|  | <span class="source-line-no">1803</span><span id="line-1803">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1804</span><span id="line-1804">      new BinaryComparator(emptyVal), put);</span> | 
|  | <span class="source-line-no">1805</span><span id="line-1805">    assertFalse(res);</span> | 
|  | <span class="source-line-no">1806</span><span id="line-1806"></span> | 
|  | <span class="source-line-no">1807</span><span id="line-1807">    Delete delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">1808</span><span id="line-1808">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">1809</span><span id="line-1809">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1810</span><span id="line-1810">      new BinaryComparator(emptyVal), delete);</span> | 
|  | <span class="source-line-no">1811</span><span id="line-1811">    assertFalse(res);</span> | 
|  | <span class="source-line-no">1812</span><span id="line-1812"></span> | 
|  | <span class="source-line-no">1813</span><span id="line-1813">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">1814</span><span id="line-1814">    put.addColumn(fam1, qf1, val2);</span> | 
|  | <span class="source-line-no">1815</span><span id="line-1815">    // checkAndPut with correct value</span> | 
|  | <span class="source-line-no">1816</span><span id="line-1816">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL, new BinaryComparator(val1),</span> | 
|  | <span class="source-line-no">1817</span><span id="line-1817">      put);</span> | 
|  | <span class="source-line-no">1818</span><span id="line-1818">    assertTrue(res);</span> | 
|  | <span class="source-line-no">1819</span><span id="line-1819"></span> | 
|  | <span class="source-line-no">1820</span><span id="line-1820">    // checkAndDelete with correct value</span> | 
|  | <span class="source-line-no">1821</span><span id="line-1821">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">1822</span><span id="line-1822">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">1823</span><span id="line-1823">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">1824</span><span id="line-1824">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL, new BinaryComparator(val2),</span> | 
|  | <span class="source-line-no">1825</span><span id="line-1825">      delete);</span> | 
|  | <span class="source-line-no">1826</span><span id="line-1826">    assertTrue(res);</span> | 
|  | <span class="source-line-no">1827</span><span id="line-1827"></span> | 
|  | <span class="source-line-no">1828</span><span id="line-1828">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">1829</span><span id="line-1829">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1830</span><span id="line-1830">      new BinaryComparator(emptyVal), delete);</span> | 
|  | <span class="source-line-no">1831</span><span id="line-1831">    assertTrue(res);</span> | 
|  | <span class="source-line-no">1832</span><span id="line-1832"></span> | 
|  | <span class="source-line-no">1833</span><span id="line-1833">    // checkAndPut looking for a null value</span> | 
|  | <span class="source-line-no">1834</span><span id="line-1834">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">1835</span><span id="line-1835">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">1836</span><span id="line-1836"></span> | 
|  | <span class="source-line-no">1837</span><span id="line-1837">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL, new NullComparator(), put);</span> | 
|  | <span class="source-line-no">1838</span><span id="line-1838">    assertTrue(res);</span> | 
|  | <span class="source-line-no">1839</span><span id="line-1839">  }</span> | 
|  | <span class="source-line-no">1840</span><span id="line-1840"></span> | 
|  | <span class="source-line-no">1841</span><span id="line-1841">  @Test</span> | 
|  | <span class="source-line-no">1842</span><span id="line-1842">  @Deprecated</span> | 
|  | <span class="source-line-no">1843</span><span id="line-1843">  public void testCheckAndMutate_WithWrongValue() throws IOException {</span> | 
|  | <span class="source-line-no">1844</span><span id="line-1844">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">1845</span><span id="line-1845">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">1846</span><span id="line-1846">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">1847</span><span id="line-1847">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">1848</span><span id="line-1848">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">1849</span><span id="line-1849">    BigDecimal bd1 = new BigDecimal(Double.MAX_VALUE);</span> | 
|  | <span class="source-line-no">1850</span><span id="line-1850">    BigDecimal bd2 = new BigDecimal(Double.MIN_VALUE);</span> | 
|  | <span class="source-line-no">1851</span><span id="line-1851"></span> | 
|  | <span class="source-line-no">1852</span><span id="line-1852">    // Setting up region</span> | 
|  | <span class="source-line-no">1853</span><span id="line-1853">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">1854</span><span id="line-1854">    // Putting data in key</span> | 
|  | <span class="source-line-no">1855</span><span id="line-1855">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">1856</span><span id="line-1856">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">1857</span><span id="line-1857">    region.put(put);</span> | 
|  | <span class="source-line-no">1858</span><span id="line-1858"></span> | 
|  | <span class="source-line-no">1859</span><span id="line-1859">    // checkAndPut with wrong value</span> | 
|  | <span class="source-line-no">1860</span><span id="line-1860">    boolean res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1861</span><span id="line-1861">      new BinaryComparator(val2), put);</span> | 
|  | <span class="source-line-no">1862</span><span id="line-1862">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">1863</span><span id="line-1863"></span> | 
|  | <span class="source-line-no">1864</span><span id="line-1864">    // checkAndDelete with wrong value</span> | 
|  | <span class="source-line-no">1865</span><span id="line-1865">    Delete delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">1866</span><span id="line-1866">    delete.addFamily(fam1);</span> | 
|  | <span class="source-line-no">1867</span><span id="line-1867">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL, new BinaryComparator(val2),</span> | 
|  | <span class="source-line-no">1868</span><span id="line-1868">      put);</span> | 
|  | <span class="source-line-no">1869</span><span id="line-1869">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">1870</span><span id="line-1870"></span> | 
|  | <span class="source-line-no">1871</span><span id="line-1871">    // Putting data in key</span> | 
|  | <span class="source-line-no">1872</span><span id="line-1872">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">1873</span><span id="line-1873">    put.addColumn(fam1, qf1, Bytes.toBytes(bd1));</span> | 
|  | <span class="source-line-no">1874</span><span id="line-1874">    region.put(put);</span> | 
|  | <span class="source-line-no">1875</span><span id="line-1875"></span> | 
|  | <span class="source-line-no">1876</span><span id="line-1876">    // checkAndPut with wrong value</span> | 
|  | <span class="source-line-no">1877</span><span id="line-1877">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1878</span><span id="line-1878">      new BigDecimalComparator(bd2), put);</span> | 
|  | <span class="source-line-no">1879</span><span id="line-1879">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">1880</span><span id="line-1880"></span> | 
|  | <span class="source-line-no">1881</span><span id="line-1881">    // checkAndDelete with wrong value</span> | 
|  | <span class="source-line-no">1882</span><span id="line-1882">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">1883</span><span id="line-1883">    delete.addFamily(fam1);</span> | 
|  | <span class="source-line-no">1884</span><span id="line-1884">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1885</span><span id="line-1885">      new BigDecimalComparator(bd2), put);</span> | 
|  | <span class="source-line-no">1886</span><span id="line-1886">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">1887</span><span id="line-1887">  }</span> | 
|  | <span class="source-line-no">1888</span><span id="line-1888"></span> | 
|  | <span class="source-line-no">1889</span><span id="line-1889">  @Test</span> | 
|  | <span class="source-line-no">1890</span><span id="line-1890">  @Deprecated</span> | 
|  | <span class="source-line-no">1891</span><span id="line-1891">  public void testCheckAndMutate_WithCorrectValue() throws IOException {</span> | 
|  | <span class="source-line-no">1892</span><span id="line-1892">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">1893</span><span id="line-1893">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">1894</span><span id="line-1894">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">1895</span><span id="line-1895">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">1896</span><span id="line-1896">    BigDecimal bd1 = new BigDecimal(Double.MIN_VALUE);</span> | 
|  | <span class="source-line-no">1897</span><span id="line-1897"></span> | 
|  | <span class="source-line-no">1898</span><span id="line-1898">    // Setting up region</span> | 
|  | <span class="source-line-no">1899</span><span id="line-1899">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">1900</span><span id="line-1900">    // Putting data in key</span> | 
|  | <span class="source-line-no">1901</span><span id="line-1901">    long now = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">1902</span><span id="line-1902">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">1903</span><span id="line-1903">    put.addColumn(fam1, qf1, now, val1);</span> | 
|  | <span class="source-line-no">1904</span><span id="line-1904">    region.put(put);</span> | 
|  | <span class="source-line-no">1905</span><span id="line-1905"></span> | 
|  | <span class="source-line-no">1906</span><span id="line-1906">    // checkAndPut with correct value</span> | 
|  | <span class="source-line-no">1907</span><span id="line-1907">    boolean res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1908</span><span id="line-1908">      new BinaryComparator(val1), put);</span> | 
|  | <span class="source-line-no">1909</span><span id="line-1909">    assertEquals("First", true, res);</span> | 
|  | <span class="source-line-no">1910</span><span id="line-1910"></span> | 
|  | <span class="source-line-no">1911</span><span id="line-1911">    // checkAndDelete with correct value</span> | 
|  | <span class="source-line-no">1912</span><span id="line-1912">    Delete delete = new Delete(row1, now + 1);</span> | 
|  | <span class="source-line-no">1913</span><span id="line-1913">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">1914</span><span id="line-1914">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL, new BinaryComparator(val1),</span> | 
|  | <span class="source-line-no">1915</span><span id="line-1915">      delete);</span> | 
|  | <span class="source-line-no">1916</span><span id="line-1916">    assertEquals("Delete", true, res);</span> | 
|  | <span class="source-line-no">1917</span><span id="line-1917"></span> | 
|  | <span class="source-line-no">1918</span><span id="line-1918">    // Putting data in key</span> | 
|  | <span class="source-line-no">1919</span><span id="line-1919">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">1920</span><span id="line-1920">    put.addColumn(fam1, qf1, now + 2, Bytes.toBytes(bd1));</span> | 
|  | <span class="source-line-no">1921</span><span id="line-1921">    region.put(put);</span> | 
|  | <span class="source-line-no">1922</span><span id="line-1922"></span> | 
|  | <span class="source-line-no">1923</span><span id="line-1923">    // checkAndPut with correct value</span> | 
|  | <span class="source-line-no">1924</span><span id="line-1924">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1925</span><span id="line-1925">      new BigDecimalComparator(bd1), put);</span> | 
|  | <span class="source-line-no">1926</span><span id="line-1926">    assertEquals("Second put", true, res);</span> | 
|  | <span class="source-line-no">1927</span><span id="line-1927"></span> | 
|  | <span class="source-line-no">1928</span><span id="line-1928">    // checkAndDelete with correct value</span> | 
|  | <span class="source-line-no">1929</span><span id="line-1929">    delete = new Delete(row1, now + 3);</span> | 
|  | <span class="source-line-no">1930</span><span id="line-1930">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">1931</span><span id="line-1931">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">1932</span><span id="line-1932">      new BigDecimalComparator(bd1), delete);</span> | 
|  | <span class="source-line-no">1933</span><span id="line-1933">    assertEquals("Second delete", true, res);</span> | 
|  | <span class="source-line-no">1934</span><span id="line-1934">  }</span> | 
|  | <span class="source-line-no">1935</span><span id="line-1935"></span> | 
|  | <span class="source-line-no">1936</span><span id="line-1936">  @Test</span> | 
|  | <span class="source-line-no">1937</span><span id="line-1937">  @Deprecated</span> | 
|  | <span class="source-line-no">1938</span><span id="line-1938">  public void testCheckAndMutate_WithNonEqualCompareOp() throws IOException {</span> | 
|  | <span class="source-line-no">1939</span><span id="line-1939">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">1940</span><span id="line-1940">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">1941</span><span id="line-1941">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">1942</span><span id="line-1942">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">1943</span><span id="line-1943">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">1944</span><span id="line-1944">    byte[] val3 = Bytes.toBytes("value3");</span> | 
|  | <span class="source-line-no">1945</span><span id="line-1945">    byte[] val4 = Bytes.toBytes("value4");</span> | 
|  | <span class="source-line-no">1946</span><span id="line-1946"></span> | 
|  | <span class="source-line-no">1947</span><span id="line-1947">    // Setting up region</span> | 
|  | <span class="source-line-no">1948</span><span id="line-1948">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">1949</span><span id="line-1949">    // Putting val3 in key</span> | 
|  | <span class="source-line-no">1950</span><span id="line-1950">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">1951</span><span id="line-1951">    put.addColumn(fam1, qf1, val3);</span> | 
|  | <span class="source-line-no">1952</span><span id="line-1952">    region.put(put);</span> | 
|  | <span class="source-line-no">1953</span><span id="line-1953"></span> | 
|  | <span class="source-line-no">1954</span><span id="line-1954">    // Test CompareOp.LESS: original = val3, compare with val3, fail</span> | 
|  | <span class="source-line-no">1955</span><span id="line-1955">    boolean res =</span> | 
|  | <span class="source-line-no">1956</span><span id="line-1956">      region.checkAndMutate(row1, fam1, qf1, CompareOperator.LESS, new BinaryComparator(val3), put);</span> | 
|  | <span class="source-line-no">1957</span><span id="line-1957">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">1958</span><span id="line-1958"></span> | 
|  | <span class="source-line-no">1959</span><span id="line-1959">    // Test CompareOp.LESS: original = val3, compare with val4, fail</span> | 
|  | <span class="source-line-no">1960</span><span id="line-1960">    res =</span> | 
|  | <span class="source-line-no">1961</span><span id="line-1961">      region.checkAndMutate(row1, fam1, qf1, CompareOperator.LESS, new BinaryComparator(val4), put);</span> | 
|  | <span class="source-line-no">1962</span><span id="line-1962">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">1963</span><span id="line-1963"></span> | 
|  | <span class="source-line-no">1964</span><span id="line-1964">    // Test CompareOp.LESS: original = val3, compare with val2,</span> | 
|  | <span class="source-line-no">1965</span><span id="line-1965">    // succeed (now value = val2)</span> | 
|  | <span class="source-line-no">1966</span><span id="line-1966">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">1967</span><span id="line-1967">    put.addColumn(fam1, qf1, val2);</span> | 
|  | <span class="source-line-no">1968</span><span id="line-1968">    res =</span> | 
|  | <span class="source-line-no">1969</span><span id="line-1969">      region.checkAndMutate(row1, fam1, qf1, CompareOperator.LESS, new BinaryComparator(val2), put);</span> | 
|  | <span class="source-line-no">1970</span><span id="line-1970">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">1971</span><span id="line-1971"></span> | 
|  | <span class="source-line-no">1972</span><span id="line-1972">    // Test CompareOp.LESS_OR_EQUAL: original = val2, compare with val3, fail</span> | 
|  | <span class="source-line-no">1973</span><span id="line-1973">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.LESS_OR_EQUAL,</span> | 
|  | <span class="source-line-no">1974</span><span id="line-1974">      new BinaryComparator(val3), put);</span> | 
|  | <span class="source-line-no">1975</span><span id="line-1975">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">1976</span><span id="line-1976"></span> | 
|  | <span class="source-line-no">1977</span><span id="line-1977">    // Test CompareOp.LESS_OR_EQUAL: original = val2, compare with val2,</span> | 
|  | <span class="source-line-no">1978</span><span id="line-1978">    // succeed (value still = val2)</span> | 
|  | <span class="source-line-no">1979</span><span id="line-1979">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.LESS_OR_EQUAL,</span> | 
|  | <span class="source-line-no">1980</span><span id="line-1980">      new BinaryComparator(val2), put);</span> | 
|  | <span class="source-line-no">1981</span><span id="line-1981">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">1982</span><span id="line-1982"></span> | 
|  | <span class="source-line-no">1983</span><span id="line-1983">    // Test CompareOp.LESS_OR_EQUAL: original = val2, compare with val1,</span> | 
|  | <span class="source-line-no">1984</span><span id="line-1984">    // succeed (now value = val3)</span> | 
|  | <span class="source-line-no">1985</span><span id="line-1985">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">1986</span><span id="line-1986">    put.addColumn(fam1, qf1, val3);</span> | 
|  | <span class="source-line-no">1987</span><span id="line-1987">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.LESS_OR_EQUAL,</span> | 
|  | <span class="source-line-no">1988</span><span id="line-1988">      new BinaryComparator(val1), put);</span> | 
|  | <span class="source-line-no">1989</span><span id="line-1989">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">1990</span><span id="line-1990"></span> | 
|  | <span class="source-line-no">1991</span><span id="line-1991">    // Test CompareOp.GREATER: original = val3, compare with val3, fail</span> | 
|  | <span class="source-line-no">1992</span><span id="line-1992">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.GREATER,</span> | 
|  | <span class="source-line-no">1993</span><span id="line-1993">      new BinaryComparator(val3), put);</span> | 
|  | <span class="source-line-no">1994</span><span id="line-1994">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">1995</span><span id="line-1995"></span> | 
|  | <span class="source-line-no">1996</span><span id="line-1996">    // Test CompareOp.GREATER: original = val3, compare with val2, fail</span> | 
|  | <span class="source-line-no">1997</span><span id="line-1997">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.GREATER,</span> | 
|  | <span class="source-line-no">1998</span><span id="line-1998">      new BinaryComparator(val2), put);</span> | 
|  | <span class="source-line-no">1999</span><span id="line-1999">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">2000</span><span id="line-2000"></span> | 
|  | <span class="source-line-no">2001</span><span id="line-2001">    // Test CompareOp.GREATER: original = val3, compare with val4,</span> | 
|  | <span class="source-line-no">2002</span><span id="line-2002">    // succeed (now value = val2)</span> | 
|  | <span class="source-line-no">2003</span><span id="line-2003">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2004</span><span id="line-2004">    put.addColumn(fam1, qf1, val2);</span> | 
|  | <span class="source-line-no">2005</span><span id="line-2005">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.GREATER,</span> | 
|  | <span class="source-line-no">2006</span><span id="line-2006">      new BinaryComparator(val4), put);</span> | 
|  | <span class="source-line-no">2007</span><span id="line-2007">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">2008</span><span id="line-2008"></span> | 
|  | <span class="source-line-no">2009</span><span id="line-2009">    // Test CompareOp.GREATER_OR_EQUAL: original = val2, compare with val1, fail</span> | 
|  | <span class="source-line-no">2010</span><span id="line-2010">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.GREATER_OR_EQUAL,</span> | 
|  | <span class="source-line-no">2011</span><span id="line-2011">      new BinaryComparator(val1), put);</span> | 
|  | <span class="source-line-no">2012</span><span id="line-2012">    assertEquals(false, res);</span> | 
|  | <span class="source-line-no">2013</span><span id="line-2013"></span> | 
|  | <span class="source-line-no">2014</span><span id="line-2014">    // Test CompareOp.GREATER_OR_EQUAL: original = val2, compare with val2,</span> | 
|  | <span class="source-line-no">2015</span><span id="line-2015">    // succeed (value still = val2)</span> | 
|  | <span class="source-line-no">2016</span><span id="line-2016">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.GREATER_OR_EQUAL,</span> | 
|  | <span class="source-line-no">2017</span><span id="line-2017">      new BinaryComparator(val2), put);</span> | 
|  | <span class="source-line-no">2018</span><span id="line-2018">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">2019</span><span id="line-2019"></span> | 
|  | <span class="source-line-no">2020</span><span id="line-2020">    // Test CompareOp.GREATER_OR_EQUAL: original = val2, compare with val3, succeed</span> | 
|  | <span class="source-line-no">2021</span><span id="line-2021">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.GREATER_OR_EQUAL,</span> | 
|  | <span class="source-line-no">2022</span><span id="line-2022">      new BinaryComparator(val3), put);</span> | 
|  | <span class="source-line-no">2023</span><span id="line-2023">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">2024</span><span id="line-2024">  }</span> | 
|  | <span class="source-line-no">2025</span><span id="line-2025"></span> | 
|  | <span class="source-line-no">2026</span><span id="line-2026">  @Test</span> | 
|  | <span class="source-line-no">2027</span><span id="line-2027">  @Deprecated</span> | 
|  | <span class="source-line-no">2028</span><span id="line-2028">  public void testCheckAndPut_ThatPutWasWritten() throws IOException {</span> | 
|  | <span class="source-line-no">2029</span><span id="line-2029">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">2030</span><span id="line-2030">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">2031</span><span id="line-2031">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">2032</span><span id="line-2032">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">2033</span><span id="line-2033">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">2034</span><span id="line-2034">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">2035</span><span id="line-2035"></span> | 
|  | <span class="source-line-no">2036</span><span id="line-2036">    byte[][] families = { fam1, fam2 };</span> | 
|  | <span class="source-line-no">2037</span><span id="line-2037"></span> | 
|  | <span class="source-line-no">2038</span><span id="line-2038">    // Setting up region</span> | 
|  | <span class="source-line-no">2039</span><span id="line-2039">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">2040</span><span id="line-2040">    // Putting data in the key to check</span> | 
|  | <span class="source-line-no">2041</span><span id="line-2041">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">2042</span><span id="line-2042">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">2043</span><span id="line-2043">    region.put(put);</span> | 
|  | <span class="source-line-no">2044</span><span id="line-2044"></span> | 
|  | <span class="source-line-no">2045</span><span id="line-2045">    // Creating put to add</span> | 
|  | <span class="source-line-no">2046</span><span id="line-2046">    long ts = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">2047</span><span id="line-2047">    KeyValue kv = new KeyValue(row1, fam2, qf1, ts, KeyValue.Type.Put, val2);</span> | 
|  | <span class="source-line-no">2048</span><span id="line-2048">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2049</span><span id="line-2049">    put.add(kv);</span> | 
|  | <span class="source-line-no">2050</span><span id="line-2050"></span> | 
|  | <span class="source-line-no">2051</span><span id="line-2051">    // checkAndPut with wrong value</span> | 
|  | <span class="source-line-no">2052</span><span id="line-2052">    boolean res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2053</span><span id="line-2053">      new BinaryComparator(val1), put);</span> | 
|  | <span class="source-line-no">2054</span><span id="line-2054">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">2055</span><span id="line-2055"></span> | 
|  | <span class="source-line-no">2056</span><span id="line-2056">    Get get = new Get(row1);</span> | 
|  | <span class="source-line-no">2057</span><span id="line-2057">    get.addColumn(fam2, qf1);</span> | 
|  | <span class="source-line-no">2058</span><span id="line-2058">    Cell[] actual = region.get(get).rawCells();</span> | 
|  | <span class="source-line-no">2059</span><span id="line-2059"></span> | 
|  | <span class="source-line-no">2060</span><span id="line-2060">    Cell[] expected = { kv };</span> | 
|  | <span class="source-line-no">2061</span><span id="line-2061"></span> | 
|  | <span class="source-line-no">2062</span><span id="line-2062">    assertEquals(expected.length, actual.length);</span> | 
|  | <span class="source-line-no">2063</span><span id="line-2063">    for (int i = 0; i < actual.length; i++) {</span> | 
|  | <span class="source-line-no">2064</span><span id="line-2064">      assertEquals(expected[i], actual[i]);</span> | 
|  | <span class="source-line-no">2065</span><span id="line-2065">    }</span> | 
|  | <span class="source-line-no">2066</span><span id="line-2066">  }</span> | 
|  | <span class="source-line-no">2067</span><span id="line-2067"></span> | 
|  | <span class="source-line-no">2068</span><span id="line-2068">  @Test</span> | 
|  | <span class="source-line-no">2069</span><span id="line-2069">  @Deprecated</span> | 
|  | <span class="source-line-no">2070</span><span id="line-2070">  public void testCheckAndPut_wrongRowInPut() throws IOException {</span> | 
|  | <span class="source-line-no">2071</span><span id="line-2071">    this.region = initHRegion(tableName, method, CONF, COLUMNS);</span> | 
|  | <span class="source-line-no">2072</span><span id="line-2072">    Put put = new Put(row2);</span> | 
|  | <span class="source-line-no">2073</span><span id="line-2073">    put.addColumn(fam1, qual1, value1);</span> | 
|  | <span class="source-line-no">2074</span><span id="line-2074">    try {</span> | 
|  | <span class="source-line-no">2075</span><span id="line-2075">      region.checkAndMutate(row, fam1, qual1, CompareOperator.EQUAL, new BinaryComparator(value2),</span> | 
|  | <span class="source-line-no">2076</span><span id="line-2076">        put);</span> | 
|  | <span class="source-line-no">2077</span><span id="line-2077">      fail();</span> | 
|  | <span class="source-line-no">2078</span><span id="line-2078">    } catch (org.apache.hadoop.hbase.DoNotRetryIOException expected) {</span> | 
|  | <span class="source-line-no">2079</span><span id="line-2079">      // expected exception.</span> | 
|  | <span class="source-line-no">2080</span><span id="line-2080">    }</span> | 
|  | <span class="source-line-no">2081</span><span id="line-2081">  }</span> | 
|  | <span class="source-line-no">2082</span><span id="line-2082"></span> | 
|  | <span class="source-line-no">2083</span><span id="line-2083">  @Test</span> | 
|  | <span class="source-line-no">2084</span><span id="line-2084">  @Deprecated</span> | 
|  | <span class="source-line-no">2085</span><span id="line-2085">  public void testCheckAndDelete_ThatDeleteWasWritten() throws IOException {</span> | 
|  | <span class="source-line-no">2086</span><span id="line-2086">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">2087</span><span id="line-2087">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">2088</span><span id="line-2088">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">2089</span><span id="line-2089">    byte[] qf1 = Bytes.toBytes("qualifier1");</span> | 
|  | <span class="source-line-no">2090</span><span id="line-2090">    byte[] qf2 = Bytes.toBytes("qualifier2");</span> | 
|  | <span class="source-line-no">2091</span><span id="line-2091">    byte[] qf3 = Bytes.toBytes("qualifier3");</span> | 
|  | <span class="source-line-no">2092</span><span id="line-2092">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">2093</span><span id="line-2093">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">2094</span><span id="line-2094">    byte[] val3 = Bytes.toBytes("value3");</span> | 
|  | <span class="source-line-no">2095</span><span id="line-2095">    byte[] emptyVal = new byte[] {};</span> | 
|  | <span class="source-line-no">2096</span><span id="line-2096"></span> | 
|  | <span class="source-line-no">2097</span><span id="line-2097">    byte[][] families = { fam1, fam2 };</span> | 
|  | <span class="source-line-no">2098</span><span id="line-2098"></span> | 
|  | <span class="source-line-no">2099</span><span id="line-2099">    // Setting up region</span> | 
|  | <span class="source-line-no">2100</span><span id="line-2100">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">2101</span><span id="line-2101">    // Put content</span> | 
|  | <span class="source-line-no">2102</span><span id="line-2102">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">2103</span><span id="line-2103">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">2104</span><span id="line-2104">    region.put(put);</span> | 
|  | <span class="source-line-no">2105</span><span id="line-2105">    Threads.sleep(2);</span> | 
|  | <span class="source-line-no">2106</span><span id="line-2106"></span> | 
|  | <span class="source-line-no">2107</span><span id="line-2107">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2108</span><span id="line-2108">    put.addColumn(fam1, qf1, val2);</span> | 
|  | <span class="source-line-no">2109</span><span id="line-2109">    put.addColumn(fam2, qf1, val3);</span> | 
|  | <span class="source-line-no">2110</span><span id="line-2110">    put.addColumn(fam2, qf2, val2);</span> | 
|  | <span class="source-line-no">2111</span><span id="line-2111">    put.addColumn(fam2, qf3, val1);</span> | 
|  | <span class="source-line-no">2112</span><span id="line-2112">    put.addColumn(fam1, qf3, val1);</span> | 
|  | <span class="source-line-no">2113</span><span id="line-2113">    region.put(put);</span> | 
|  | <span class="source-line-no">2114</span><span id="line-2114"></span> | 
|  | <span class="source-line-no">2115</span><span id="line-2115">    LOG.info("get={}", region.get(new Get(row1).addColumn(fam1, qf1)).toString());</span> | 
|  | <span class="source-line-no">2116</span><span id="line-2116"></span> | 
|  | <span class="source-line-no">2117</span><span id="line-2117">    // Multi-column delete</span> | 
|  | <span class="source-line-no">2118</span><span id="line-2118">    Delete delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2119</span><span id="line-2119">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">2120</span><span id="line-2120">    delete.addColumn(fam2, qf1);</span> | 
|  | <span class="source-line-no">2121</span><span id="line-2121">    delete.addColumn(fam1, qf3);</span> | 
|  | <span class="source-line-no">2122</span><span id="line-2122">    boolean res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2123</span><span id="line-2123">      new BinaryComparator(val2), delete);</span> | 
|  | <span class="source-line-no">2124</span><span id="line-2124">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">2125</span><span id="line-2125"></span> | 
|  | <span class="source-line-no">2126</span><span id="line-2126">    Get get = new Get(row1);</span> | 
|  | <span class="source-line-no">2127</span><span id="line-2127">    get.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">2128</span><span id="line-2128">    get.addColumn(fam1, qf3);</span> | 
|  | <span class="source-line-no">2129</span><span id="line-2129">    get.addColumn(fam2, qf2);</span> | 
|  | <span class="source-line-no">2130</span><span id="line-2130">    Result r = region.get(get);</span> | 
|  | <span class="source-line-no">2131</span><span id="line-2131">    assertEquals(2, r.size());</span> | 
|  | <span class="source-line-no">2132</span><span id="line-2132">    assertArrayEquals(val1, r.getValue(fam1, qf1));</span> | 
|  | <span class="source-line-no">2133</span><span id="line-2133">    assertArrayEquals(val2, r.getValue(fam2, qf2));</span> | 
|  | <span class="source-line-no">2134</span><span id="line-2134"></span> | 
|  | <span class="source-line-no">2135</span><span id="line-2135">    // Family delete</span> | 
|  | <span class="source-line-no">2136</span><span id="line-2136">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2137</span><span id="line-2137">    delete.addFamily(fam2);</span> | 
|  | <span class="source-line-no">2138</span><span id="line-2138">    res = region.checkAndMutate(row1, fam2, qf1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2139</span><span id="line-2139">      new BinaryComparator(emptyVal), delete);</span> | 
|  | <span class="source-line-no">2140</span><span id="line-2140">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">2141</span><span id="line-2141"></span> | 
|  | <span class="source-line-no">2142</span><span id="line-2142">    get = new Get(row1);</span> | 
|  | <span class="source-line-no">2143</span><span id="line-2143">    r = region.get(get);</span> | 
|  | <span class="source-line-no">2144</span><span id="line-2144">    assertEquals(1, r.size());</span> | 
|  | <span class="source-line-no">2145</span><span id="line-2145">    assertArrayEquals(val1, r.getValue(fam1, qf1));</span> | 
|  | <span class="source-line-no">2146</span><span id="line-2146"></span> | 
|  | <span class="source-line-no">2147</span><span id="line-2147">    // Row delete</span> | 
|  | <span class="source-line-no">2148</span><span id="line-2148">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2149</span><span id="line-2149">    res = region.checkAndMutate(row1, fam1, qf1, CompareOperator.EQUAL, new BinaryComparator(val1),</span> | 
|  | <span class="source-line-no">2150</span><span id="line-2150">      delete);</span> | 
|  | <span class="source-line-no">2151</span><span id="line-2151">    assertEquals(true, res);</span> | 
|  | <span class="source-line-no">2152</span><span id="line-2152">    get = new Get(row1);</span> | 
|  | <span class="source-line-no">2153</span><span id="line-2153">    r = region.get(get);</span> | 
|  | <span class="source-line-no">2154</span><span id="line-2154">    assertEquals(0, r.size());</span> | 
|  | <span class="source-line-no">2155</span><span id="line-2155">  }</span> | 
|  | <span class="source-line-no">2156</span><span id="line-2156"></span> | 
|  | <span class="source-line-no">2157</span><span id="line-2157">  @Test</span> | 
|  | <span class="source-line-no">2158</span><span id="line-2158">  @Deprecated</span> | 
|  | <span class="source-line-no">2159</span><span id="line-2159">  public void testCheckAndMutate_WithFilters() throws Throwable {</span> | 
|  | <span class="source-line-no">2160</span><span id="line-2160">    final byte[] FAMILY = Bytes.toBytes("fam");</span> | 
|  | <span class="source-line-no">2161</span><span id="line-2161"></span> | 
|  | <span class="source-line-no">2162</span><span id="line-2162">    // Setting up region</span> | 
|  | <span class="source-line-no">2163</span><span id="line-2163">    this.region = initHRegion(tableName, method, CONF, FAMILY);</span> | 
|  | <span class="source-line-no">2164</span><span id="line-2164"></span> | 
|  | <span class="source-line-no">2165</span><span id="line-2165">    // Put one row</span> | 
|  | <span class="source-line-no">2166</span><span id="line-2166">    Put put = new Put(row);</span> | 
|  | <span class="source-line-no">2167</span><span id="line-2167">    put.addColumn(FAMILY, Bytes.toBytes("A"), Bytes.toBytes("a"));</span> | 
|  | <span class="source-line-no">2168</span><span id="line-2168">    put.addColumn(FAMILY, Bytes.toBytes("B"), Bytes.toBytes("b"));</span> | 
|  | <span class="source-line-no">2169</span><span id="line-2169">    put.addColumn(FAMILY, Bytes.toBytes("C"), Bytes.toBytes("c"));</span> | 
|  | <span class="source-line-no">2170</span><span id="line-2170">    region.put(put);</span> | 
|  | <span class="source-line-no">2171</span><span id="line-2171"></span> | 
|  | <span class="source-line-no">2172</span><span id="line-2172">    // Put with success</span> | 
|  | <span class="source-line-no">2173</span><span id="line-2173">    boolean ok = region.checkAndMutate(row,</span> | 
|  | <span class="source-line-no">2174</span><span id="line-2174">      new FilterList(</span> | 
|  | <span class="source-line-no">2175</span><span id="line-2175">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2176</span><span id="line-2176">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2177</span><span id="line-2177">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("B"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2178</span><span id="line-2178">          Bytes.toBytes("b"))),</span> | 
|  | <span class="source-line-no">2179</span><span id="line-2179">      new Put(row).addColumn(FAMILY, Bytes.toBytes("D"), Bytes.toBytes("d")));</span> | 
|  | <span class="source-line-no">2180</span><span id="line-2180">    assertTrue(ok);</span> | 
|  | <span class="source-line-no">2181</span><span id="line-2181"></span> | 
|  | <span class="source-line-no">2182</span><span id="line-2182">    Result result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("D")));</span> | 
|  | <span class="source-line-no">2183</span><span id="line-2183">    assertEquals("d", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("D"))));</span> | 
|  | <span class="source-line-no">2184</span><span id="line-2184"></span> | 
|  | <span class="source-line-no">2185</span><span id="line-2185">    // Put with failure</span> | 
|  | <span class="source-line-no">2186</span><span id="line-2186">    ok = region.checkAndMutate(row,</span> | 
|  | <span class="source-line-no">2187</span><span id="line-2187">      new FilterList(</span> | 
|  | <span class="source-line-no">2188</span><span id="line-2188">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2189</span><span id="line-2189">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2190</span><span id="line-2190">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("B"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2191</span><span id="line-2191">          Bytes.toBytes("c"))),</span> | 
|  | <span class="source-line-no">2192</span><span id="line-2192">      new Put(row).addColumn(FAMILY, Bytes.toBytes("E"), Bytes.toBytes("e")));</span> | 
|  | <span class="source-line-no">2193</span><span id="line-2193">    assertFalse(ok);</span> | 
|  | <span class="source-line-no">2194</span><span id="line-2194"></span> | 
|  | <span class="source-line-no">2195</span><span id="line-2195">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("E"))).isEmpty());</span> | 
|  | <span class="source-line-no">2196</span><span id="line-2196"></span> | 
|  | <span class="source-line-no">2197</span><span id="line-2197">    // Delete with success</span> | 
|  | <span class="source-line-no">2198</span><span id="line-2198">    ok = region.checkAndMutate(row,</span> | 
|  | <span class="source-line-no">2199</span><span id="line-2199">      new FilterList(</span> | 
|  | <span class="source-line-no">2200</span><span id="line-2200">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2201</span><span id="line-2201">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2202</span><span id="line-2202">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("B"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2203</span><span id="line-2203">          Bytes.toBytes("b"))),</span> | 
|  | <span class="source-line-no">2204</span><span id="line-2204">      new Delete(row).addColumns(FAMILY, Bytes.toBytes("D")));</span> | 
|  | <span class="source-line-no">2205</span><span id="line-2205">    assertTrue(ok);</span> | 
|  | <span class="source-line-no">2206</span><span id="line-2206"></span> | 
|  | <span class="source-line-no">2207</span><span id="line-2207">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("D"))).isEmpty());</span> | 
|  | <span class="source-line-no">2208</span><span id="line-2208"></span> | 
|  | <span class="source-line-no">2209</span><span id="line-2209">    // Mutate with success</span> | 
|  | <span class="source-line-no">2210</span><span id="line-2210">    ok = region.checkAndRowMutate(row,</span> | 
|  | <span class="source-line-no">2211</span><span id="line-2211">      new FilterList(</span> | 
|  | <span class="source-line-no">2212</span><span id="line-2212">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2213</span><span id="line-2213">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2214</span><span id="line-2214">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("B"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2215</span><span id="line-2215">          Bytes.toBytes("b"))),</span> | 
|  | <span class="source-line-no">2216</span><span id="line-2216">      new RowMutations(row)</span> | 
|  | <span class="source-line-no">2217</span><span id="line-2217">        .add((Mutation) new Put(row).addColumn(FAMILY, Bytes.toBytes("E"), Bytes.toBytes("e")))</span> | 
|  | <span class="source-line-no">2218</span><span id="line-2218">        .add((Mutation) new Delete(row).addColumns(FAMILY, Bytes.toBytes("A"))));</span> | 
|  | <span class="source-line-no">2219</span><span id="line-2219">    assertTrue(ok);</span> | 
|  | <span class="source-line-no">2220</span><span id="line-2220"></span> | 
|  | <span class="source-line-no">2221</span><span id="line-2221">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("E")));</span> | 
|  | <span class="source-line-no">2222</span><span id="line-2222">    assertEquals("e", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("E"))));</span> | 
|  | <span class="source-line-no">2223</span><span id="line-2223"></span> | 
|  | <span class="source-line-no">2224</span><span id="line-2224">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("A"))).isEmpty());</span> | 
|  | <span class="source-line-no">2225</span><span id="line-2225">  }</span> | 
|  | <span class="source-line-no">2226</span><span id="line-2226"></span> | 
|  | <span class="source-line-no">2227</span><span id="line-2227">  @Test</span> | 
|  | <span class="source-line-no">2228</span><span id="line-2228">  @Deprecated</span> | 
|  | <span class="source-line-no">2229</span><span id="line-2229">  public void testCheckAndMutate_WithFiltersAndTimeRange() throws Throwable {</span> | 
|  | <span class="source-line-no">2230</span><span id="line-2230">    final byte[] FAMILY = Bytes.toBytes("fam");</span> | 
|  | <span class="source-line-no">2231</span><span id="line-2231"></span> | 
|  | <span class="source-line-no">2232</span><span id="line-2232">    // Setting up region</span> | 
|  | <span class="source-line-no">2233</span><span id="line-2233">    this.region = initHRegion(tableName, method, CONF, FAMILY);</span> | 
|  | <span class="source-line-no">2234</span><span id="line-2234"></span> | 
|  | <span class="source-line-no">2235</span><span id="line-2235">    // Put with specifying the timestamp</span> | 
|  | <span class="source-line-no">2236</span><span id="line-2236">    region.put(new Put(row).addColumn(FAMILY, Bytes.toBytes("A"), 100, Bytes.toBytes("a")));</span> | 
|  | <span class="source-line-no">2237</span><span id="line-2237"></span> | 
|  | <span class="source-line-no">2238</span><span id="line-2238">    // Put with success</span> | 
|  | <span class="source-line-no">2239</span><span id="line-2239">    boolean ok = region.checkAndMutate(row,</span> | 
|  | <span class="source-line-no">2240</span><span id="line-2240">      new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2241</span><span id="line-2241">        Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2242</span><span id="line-2242">      TimeRange.between(0, 101),</span> | 
|  | <span class="source-line-no">2243</span><span id="line-2243">      new Put(row).addColumn(FAMILY, Bytes.toBytes("B"), Bytes.toBytes("b")));</span> | 
|  | <span class="source-line-no">2244</span><span id="line-2244">    assertTrue(ok);</span> | 
|  | <span class="source-line-no">2245</span><span id="line-2245"></span> | 
|  | <span class="source-line-no">2246</span><span id="line-2246">    Result result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2247</span><span id="line-2247">    assertEquals("b", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2248</span><span id="line-2248"></span> | 
|  | <span class="source-line-no">2249</span><span id="line-2249">    // Put with failure</span> | 
|  | <span class="source-line-no">2250</span><span id="line-2250">    ok = region.checkAndMutate(row,</span> | 
|  | <span class="source-line-no">2251</span><span id="line-2251">      new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2252</span><span id="line-2252">        Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2253</span><span id="line-2253">      TimeRange.between(0, 100),</span> | 
|  | <span class="source-line-no">2254</span><span id="line-2254">      new Put(row).addColumn(FAMILY, Bytes.toBytes("C"), Bytes.toBytes("c")));</span> | 
|  | <span class="source-line-no">2255</span><span id="line-2255">    assertFalse(ok);</span> | 
|  | <span class="source-line-no">2256</span><span id="line-2256"></span> | 
|  | <span class="source-line-no">2257</span><span id="line-2257">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("C"))).isEmpty());</span> | 
|  | <span class="source-line-no">2258</span><span id="line-2258"></span> | 
|  | <span class="source-line-no">2259</span><span id="line-2259">    // Mutate with success</span> | 
|  | <span class="source-line-no">2260</span><span id="line-2260">    ok = region.checkAndRowMutate(row,</span> | 
|  | <span class="source-line-no">2261</span><span id="line-2261">      new SingleColumnValueFilter(</span> | 
|  | <span class="source-line-no">2262</span><span id="line-2262">        FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL, Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2263</span><span id="line-2263">      TimeRange.between(0, 101),</span> | 
|  | <span class="source-line-no">2264</span><span id="line-2264">      new RowMutations(row)</span> | 
|  | <span class="source-line-no">2265</span><span id="line-2265">        .add((Mutation) new Put(row).addColumn(FAMILY, Bytes.toBytes("D"), Bytes.toBytes("d")))</span> | 
|  | <span class="source-line-no">2266</span><span id="line-2266">        .add((Mutation) new Delete(row).addColumns(FAMILY, Bytes.toBytes("A"))));</span> | 
|  | <span class="source-line-no">2267</span><span id="line-2267">    assertTrue(ok);</span> | 
|  | <span class="source-line-no">2268</span><span id="line-2268"></span> | 
|  | <span class="source-line-no">2269</span><span id="line-2269">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("D")));</span> | 
|  | <span class="source-line-no">2270</span><span id="line-2270">    assertEquals("d", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("D"))));</span> | 
|  | <span class="source-line-no">2271</span><span id="line-2271"></span> | 
|  | <span class="source-line-no">2272</span><span id="line-2272">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("A"))).isEmpty());</span> | 
|  | <span class="source-line-no">2273</span><span id="line-2273">  }</span> | 
|  | <span class="source-line-no">2274</span><span id="line-2274"></span> | 
|  | <span class="source-line-no">2275</span><span id="line-2275">  @Test</span> | 
|  | <span class="source-line-no">2276</span><span id="line-2276">  @Deprecated</span> | 
|  | <span class="source-line-no">2277</span><span id="line-2277">  public void testCheckAndMutate_wrongMutationType() throws Throwable {</span> | 
|  | <span class="source-line-no">2278</span><span id="line-2278">    // Setting up region</span> | 
|  | <span class="source-line-no">2279</span><span id="line-2279">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">2280</span><span id="line-2280"></span> | 
|  | <span class="source-line-no">2281</span><span id="line-2281">    try {</span> | 
|  | <span class="source-line-no">2282</span><span id="line-2282">      region.checkAndMutate(row, fam1, qual1, CompareOperator.EQUAL, new BinaryComparator(value1),</span> | 
|  | <span class="source-line-no">2283</span><span id="line-2283">        new Increment(row).addColumn(fam1, qual1, 1));</span> | 
|  | <span class="source-line-no">2284</span><span id="line-2284">      fail("should throw DoNotRetryIOException");</span> | 
|  | <span class="source-line-no">2285</span><span id="line-2285">    } catch (DoNotRetryIOException e) {</span> | 
|  | <span class="source-line-no">2286</span><span id="line-2286">      assertEquals("Unsupported mutate type: INCREMENT", e.getMessage());</span> | 
|  | <span class="source-line-no">2287</span><span id="line-2287">    }</span> | 
|  | <span class="source-line-no">2288</span><span id="line-2288"></span> | 
|  | <span class="source-line-no">2289</span><span id="line-2289">    try {</span> | 
|  | <span class="source-line-no">2290</span><span id="line-2290">      region.checkAndMutate(row,</span> | 
|  | <span class="source-line-no">2291</span><span id="line-2291">        new SingleColumnValueFilter(fam1, qual1, CompareOperator.EQUAL, value1),</span> | 
|  | <span class="source-line-no">2292</span><span id="line-2292">        new Increment(row).addColumn(fam1, qual1, 1));</span> | 
|  | <span class="source-line-no">2293</span><span id="line-2293">      fail("should throw DoNotRetryIOException");</span> | 
|  | <span class="source-line-no">2294</span><span id="line-2294">    } catch (DoNotRetryIOException e) {</span> | 
|  | <span class="source-line-no">2295</span><span id="line-2295">      assertEquals("Unsupported mutate type: INCREMENT", e.getMessage());</span> | 
|  | <span class="source-line-no">2296</span><span id="line-2296">    }</span> | 
|  | <span class="source-line-no">2297</span><span id="line-2297">  }</span> | 
|  | <span class="source-line-no">2298</span><span id="line-2298"></span> | 
|  | <span class="source-line-no">2299</span><span id="line-2299">  @Test</span> | 
|  | <span class="source-line-no">2300</span><span id="line-2300">  @Deprecated</span> | 
|  | <span class="source-line-no">2301</span><span id="line-2301">  public void testCheckAndMutate_wrongRow() throws Throwable {</span> | 
|  | <span class="source-line-no">2302</span><span id="line-2302">    final byte[] wrongRow = Bytes.toBytes("wrongRow");</span> | 
|  | <span class="source-line-no">2303</span><span id="line-2303"></span> | 
|  | <span class="source-line-no">2304</span><span id="line-2304">    // Setting up region</span> | 
|  | <span class="source-line-no">2305</span><span id="line-2305">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">2306</span><span id="line-2306"></span> | 
|  | <span class="source-line-no">2307</span><span id="line-2307">    try {</span> | 
|  | <span class="source-line-no">2308</span><span id="line-2308">      region.checkAndMutate(row, fam1, qual1, CompareOperator.EQUAL, new BinaryComparator(value1),</span> | 
|  | <span class="source-line-no">2309</span><span id="line-2309">        new Put(wrongRow).addColumn(fam1, qual1, value1));</span> | 
|  | <span class="source-line-no">2310</span><span id="line-2310">      fail("should throw DoNotRetryIOException");</span> | 
|  | <span class="source-line-no">2311</span><span id="line-2311">    } catch (DoNotRetryIOException e) {</span> | 
|  | <span class="source-line-no">2312</span><span id="line-2312">      assertEquals("The row of the action <wrongRow> doesn't match the original one <rowA>",</span> | 
|  | <span class="source-line-no">2313</span><span id="line-2313">        e.getMessage());</span> | 
|  | <span class="source-line-no">2314</span><span id="line-2314">    }</span> | 
|  | <span class="source-line-no">2315</span><span id="line-2315"></span> | 
|  | <span class="source-line-no">2316</span><span id="line-2316">    try {</span> | 
|  | <span class="source-line-no">2317</span><span id="line-2317">      region.checkAndMutate(row,</span> | 
|  | <span class="source-line-no">2318</span><span id="line-2318">        new SingleColumnValueFilter(fam1, qual1, CompareOperator.EQUAL, value1),</span> | 
|  | <span class="source-line-no">2319</span><span id="line-2319">        new Put(wrongRow).addColumn(fam1, qual1, value1));</span> | 
|  | <span class="source-line-no">2320</span><span id="line-2320">      fail("should throw DoNotRetryIOException");</span> | 
|  | <span class="source-line-no">2321</span><span id="line-2321">    } catch (DoNotRetryIOException e) {</span> | 
|  | <span class="source-line-no">2322</span><span id="line-2322">      assertEquals("The row of the action <wrongRow> doesn't match the original one <rowA>",</span> | 
|  | <span class="source-line-no">2323</span><span id="line-2323">        e.getMessage());</span> | 
|  | <span class="source-line-no">2324</span><span id="line-2324">    }</span> | 
|  | <span class="source-line-no">2325</span><span id="line-2325"></span> | 
|  | <span class="source-line-no">2326</span><span id="line-2326">    try {</span> | 
|  | <span class="source-line-no">2327</span><span id="line-2327">      region.checkAndRowMutate(row, fam1, qual1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2328</span><span id="line-2328">        new BinaryComparator(value1),</span> | 
|  | <span class="source-line-no">2329</span><span id="line-2329">        new RowMutations(wrongRow).add((Mutation) new Put(wrongRow).addColumn(fam1, qual1, value1))</span> | 
|  | <span class="source-line-no">2330</span><span id="line-2330">          .add((Mutation) new Delete(wrongRow).addColumns(fam1, qual2)));</span> | 
|  | <span class="source-line-no">2331</span><span id="line-2331">      fail("should throw DoNotRetryIOException");</span> | 
|  | <span class="source-line-no">2332</span><span id="line-2332">    } catch (DoNotRetryIOException e) {</span> | 
|  | <span class="source-line-no">2333</span><span id="line-2333">      assertEquals("The row of the action <wrongRow> doesn't match the original one <rowA>",</span> | 
|  | <span class="source-line-no">2334</span><span id="line-2334">        e.getMessage());</span> | 
|  | <span class="source-line-no">2335</span><span id="line-2335">    }</span> | 
|  | <span class="source-line-no">2336</span><span id="line-2336"></span> | 
|  | <span class="source-line-no">2337</span><span id="line-2337">    try {</span> | 
|  | <span class="source-line-no">2338</span><span id="line-2338">      region.checkAndRowMutate(row,</span> | 
|  | <span class="source-line-no">2339</span><span id="line-2339">        new SingleColumnValueFilter(fam1, qual1, CompareOperator.EQUAL, value1),</span> | 
|  | <span class="source-line-no">2340</span><span id="line-2340">        new RowMutations(wrongRow).add((Mutation) new Put(wrongRow).addColumn(fam1, qual1, value1))</span> | 
|  | <span class="source-line-no">2341</span><span id="line-2341">          .add((Mutation) new Delete(wrongRow).addColumns(fam1, qual2)));</span> | 
|  | <span class="source-line-no">2342</span><span id="line-2342">      fail("should throw DoNotRetryIOException");</span> | 
|  | <span class="source-line-no">2343</span><span id="line-2343">    } catch (DoNotRetryIOException e) {</span> | 
|  | <span class="source-line-no">2344</span><span id="line-2344">      assertEquals("The row of the action <wrongRow> doesn't match the original one <rowA>",</span> | 
|  | <span class="source-line-no">2345</span><span id="line-2345">        e.getMessage());</span> | 
|  | <span class="source-line-no">2346</span><span id="line-2346">    }</span> | 
|  | <span class="source-line-no">2347</span><span id="line-2347">  }</span> | 
|  | <span class="source-line-no">2348</span><span id="line-2348"></span> | 
|  | <span class="source-line-no">2349</span><span id="line-2349">  @Test</span> | 
|  | <span class="source-line-no">2350</span><span id="line-2350">  public void testCheckAndMutateWithEmptyRowValue() throws IOException {</span> | 
|  | <span class="source-line-no">2351</span><span id="line-2351">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">2352</span><span id="line-2352">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">2353</span><span id="line-2353">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">2354</span><span id="line-2354">    byte[] emptyVal = new byte[] {};</span> | 
|  | <span class="source-line-no">2355</span><span id="line-2355">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">2356</span><span id="line-2356">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">2357</span><span id="line-2357"></span> | 
|  | <span class="source-line-no">2358</span><span id="line-2358">    // Setting up region</span> | 
|  | <span class="source-line-no">2359</span><span id="line-2359">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">2360</span><span id="line-2360">    // Putting empty data in key</span> | 
|  | <span class="source-line-no">2361</span><span id="line-2361">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">2362</span><span id="line-2362">    put.addColumn(fam1, qf1, emptyVal);</span> | 
|  | <span class="source-line-no">2363</span><span id="line-2363"></span> | 
|  | <span class="source-line-no">2364</span><span id="line-2364">    // checkAndPut with empty value</span> | 
|  | <span class="source-line-no">2365</span><span id="line-2365">    CheckAndMutateResult res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2366</span><span id="line-2366">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, emptyVal).build(put));</span> | 
|  | <span class="source-line-no">2367</span><span id="line-2367">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2368</span><span id="line-2368">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2369</span><span id="line-2369"></span> | 
|  | <span class="source-line-no">2370</span><span id="line-2370">    // Putting data in key</span> | 
|  | <span class="source-line-no">2371</span><span id="line-2371">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2372</span><span id="line-2372">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">2373</span><span id="line-2373"></span> | 
|  | <span class="source-line-no">2374</span><span id="line-2374">    // checkAndPut with correct value</span> | 
|  | <span class="source-line-no">2375</span><span id="line-2375">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2376</span><span id="line-2376">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, emptyVal).build(put));</span> | 
|  | <span class="source-line-no">2377</span><span id="line-2377">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2378</span><span id="line-2378">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2379</span><span id="line-2379"></span> | 
|  | <span class="source-line-no">2380</span><span id="line-2380">    // not empty anymore</span> | 
|  | <span class="source-line-no">2381</span><span id="line-2381">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2382</span><span id="line-2382">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, emptyVal).build(put));</span> | 
|  | <span class="source-line-no">2383</span><span id="line-2383">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2384</span><span id="line-2384">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2385</span><span id="line-2385"></span> | 
|  | <span class="source-line-no">2386</span><span id="line-2386">    Delete delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2387</span><span id="line-2387">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">2388</span><span id="line-2388">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2389</span><span id="line-2389">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, emptyVal).build(delete));</span> | 
|  | <span class="source-line-no">2390</span><span id="line-2390">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2391</span><span id="line-2391">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2392</span><span id="line-2392"></span> | 
|  | <span class="source-line-no">2393</span><span id="line-2393">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2394</span><span id="line-2394">    put.addColumn(fam1, qf1, val2);</span> | 
|  | <span class="source-line-no">2395</span><span id="line-2395">    // checkAndPut with correct value</span> | 
|  | <span class="source-line-no">2396</span><span id="line-2396">    res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2397</span><span id="line-2397">      CheckAndMutate.newBuilder(row1).ifMatches(fam1, qf1, CompareOperator.EQUAL, val1).build(put));</span> | 
|  | <span class="source-line-no">2398</span><span id="line-2398">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2399</span><span id="line-2399">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2400</span><span id="line-2400"></span> | 
|  | <span class="source-line-no">2401</span><span id="line-2401">    // checkAndDelete with correct value</span> | 
|  | <span class="source-line-no">2402</span><span id="line-2402">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2403</span><span id="line-2403">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">2404</span><span id="line-2404">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">2405</span><span id="line-2405">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2406</span><span id="line-2406">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, val2).build(delete));</span> | 
|  | <span class="source-line-no">2407</span><span id="line-2407">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2408</span><span id="line-2408">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2409</span><span id="line-2409"></span> | 
|  | <span class="source-line-no">2410</span><span id="line-2410">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2411</span><span id="line-2411">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2412</span><span id="line-2412">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, emptyVal).build(delete));</span> | 
|  | <span class="source-line-no">2413</span><span id="line-2413">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2414</span><span id="line-2414">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2415</span><span id="line-2415"></span> | 
|  | <span class="source-line-no">2416</span><span id="line-2416">    // checkAndPut looking for a null value</span> | 
|  | <span class="source-line-no">2417</span><span id="line-2417">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2418</span><span id="line-2418">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">2419</span><span id="line-2419"></span> | 
|  | <span class="source-line-no">2420</span><span id="line-2420">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1).ifNotExists(fam1, qf1).build(put));</span> | 
|  | <span class="source-line-no">2421</span><span id="line-2421">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2422</span><span id="line-2422">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2423</span><span id="line-2423">  }</span> | 
|  | <span class="source-line-no">2424</span><span id="line-2424"></span> | 
|  | <span class="source-line-no">2425</span><span id="line-2425">  @Test</span> | 
|  | <span class="source-line-no">2426</span><span id="line-2426">  public void testCheckAndMutateWithWrongValue() throws IOException {</span> | 
|  | <span class="source-line-no">2427</span><span id="line-2427">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">2428</span><span id="line-2428">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">2429</span><span id="line-2429">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">2430</span><span id="line-2430">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">2431</span><span id="line-2431">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">2432</span><span id="line-2432">    BigDecimal bd1 = new BigDecimal(Double.MAX_VALUE);</span> | 
|  | <span class="source-line-no">2433</span><span id="line-2433">    BigDecimal bd2 = new BigDecimal(Double.MIN_VALUE);</span> | 
|  | <span class="source-line-no">2434</span><span id="line-2434"></span> | 
|  | <span class="source-line-no">2435</span><span id="line-2435">    // Setting up region</span> | 
|  | <span class="source-line-no">2436</span><span id="line-2436">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">2437</span><span id="line-2437">    // Putting data in key</span> | 
|  | <span class="source-line-no">2438</span><span id="line-2438">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">2439</span><span id="line-2439">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">2440</span><span id="line-2440">    region.put(put);</span> | 
|  | <span class="source-line-no">2441</span><span id="line-2441"></span> | 
|  | <span class="source-line-no">2442</span><span id="line-2442">    // checkAndPut with wrong value</span> | 
|  | <span class="source-line-no">2443</span><span id="line-2443">    CheckAndMutateResult res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2444</span><span id="line-2444">      CheckAndMutate.newBuilder(row1).ifMatches(fam1, qf1, CompareOperator.EQUAL, val2).build(put));</span> | 
|  | <span class="source-line-no">2445</span><span id="line-2445">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2446</span><span id="line-2446">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2447</span><span id="line-2447"></span> | 
|  | <span class="source-line-no">2448</span><span id="line-2448">    // checkAndDelete with wrong value</span> | 
|  | <span class="source-line-no">2449</span><span id="line-2449">    Delete delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2450</span><span id="line-2450">    delete.addFamily(fam1);</span> | 
|  | <span class="source-line-no">2451</span><span id="line-2451">    res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2452</span><span id="line-2452">      CheckAndMutate.newBuilder(row1).ifMatches(fam1, qf1, CompareOperator.EQUAL, val2).build(put));</span> | 
|  | <span class="source-line-no">2453</span><span id="line-2453">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2454</span><span id="line-2454">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2455</span><span id="line-2455"></span> | 
|  | <span class="source-line-no">2456</span><span id="line-2456">    // Putting data in key</span> | 
|  | <span class="source-line-no">2457</span><span id="line-2457">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2458</span><span id="line-2458">    put.addColumn(fam1, qf1, Bytes.toBytes(bd1));</span> | 
|  | <span class="source-line-no">2459</span><span id="line-2459">    region.put(put);</span> | 
|  | <span class="source-line-no">2460</span><span id="line-2460"></span> | 
|  | <span class="source-line-no">2461</span><span id="line-2461">    // checkAndPut with wrong value</span> | 
|  | <span class="source-line-no">2462</span><span id="line-2462">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2463</span><span id="line-2463">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, Bytes.toBytes(bd2)).build(put));</span> | 
|  | <span class="source-line-no">2464</span><span id="line-2464">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2465</span><span id="line-2465">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2466</span><span id="line-2466"></span> | 
|  | <span class="source-line-no">2467</span><span id="line-2467">    // checkAndDelete with wrong value</span> | 
|  | <span class="source-line-no">2468</span><span id="line-2468">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2469</span><span id="line-2469">    delete.addFamily(fam1);</span> | 
|  | <span class="source-line-no">2470</span><span id="line-2470">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2471</span><span id="line-2471">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, Bytes.toBytes(bd2)).build(delete));</span> | 
|  | <span class="source-line-no">2472</span><span id="line-2472">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2473</span><span id="line-2473">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2474</span><span id="line-2474">  }</span> | 
|  | <span class="source-line-no">2475</span><span id="line-2475"></span> | 
|  | <span class="source-line-no">2476</span><span id="line-2476">  @Test</span> | 
|  | <span class="source-line-no">2477</span><span id="line-2477">  public void testCheckAndMutateWithCorrectValue() throws IOException {</span> | 
|  | <span class="source-line-no">2478</span><span id="line-2478">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">2479</span><span id="line-2479">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">2480</span><span id="line-2480">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">2481</span><span id="line-2481">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">2482</span><span id="line-2482">    BigDecimal bd1 = new BigDecimal(Double.MIN_VALUE);</span> | 
|  | <span class="source-line-no">2483</span><span id="line-2483"></span> | 
|  | <span class="source-line-no">2484</span><span id="line-2484">    // Setting up region</span> | 
|  | <span class="source-line-no">2485</span><span id="line-2485">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">2486</span><span id="line-2486">    // Putting data in key</span> | 
|  | <span class="source-line-no">2487</span><span id="line-2487">    long now = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">2488</span><span id="line-2488">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">2489</span><span id="line-2489">    put.addColumn(fam1, qf1, now, val1);</span> | 
|  | <span class="source-line-no">2490</span><span id="line-2490">    region.put(put);</span> | 
|  | <span class="source-line-no">2491</span><span id="line-2491"></span> | 
|  | <span class="source-line-no">2492</span><span id="line-2492">    // checkAndPut with correct value</span> | 
|  | <span class="source-line-no">2493</span><span id="line-2493">    CheckAndMutateResult res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2494</span><span id="line-2494">      CheckAndMutate.newBuilder(row1).ifMatches(fam1, qf1, CompareOperator.EQUAL, val1).build(put));</span> | 
|  | <span class="source-line-no">2495</span><span id="line-2495">    assertTrue("First", res.isSuccess());</span> | 
|  | <span class="source-line-no">2496</span><span id="line-2496"></span> | 
|  | <span class="source-line-no">2497</span><span id="line-2497">    // checkAndDelete with correct value</span> | 
|  | <span class="source-line-no">2498</span><span id="line-2498">    Delete delete = new Delete(row1, now + 1);</span> | 
|  | <span class="source-line-no">2499</span><span id="line-2499">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">2500</span><span id="line-2500">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2501</span><span id="line-2501">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, val1).build(delete));</span> | 
|  | <span class="source-line-no">2502</span><span id="line-2502">    assertTrue("Delete", res.isSuccess());</span> | 
|  | <span class="source-line-no">2503</span><span id="line-2503">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2504</span><span id="line-2504"></span> | 
|  | <span class="source-line-no">2505</span><span id="line-2505">    // Putting data in key</span> | 
|  | <span class="source-line-no">2506</span><span id="line-2506">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2507</span><span id="line-2507">    put.addColumn(fam1, qf1, now + 2, Bytes.toBytes(bd1));</span> | 
|  | <span class="source-line-no">2508</span><span id="line-2508">    region.put(put);</span> | 
|  | <span class="source-line-no">2509</span><span id="line-2509"></span> | 
|  | <span class="source-line-no">2510</span><span id="line-2510">    // checkAndPut with correct value</span> | 
|  | <span class="source-line-no">2511</span><span id="line-2511">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2512</span><span id="line-2512">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, Bytes.toBytes(bd1)).build(put));</span> | 
|  | <span class="source-line-no">2513</span><span id="line-2513">    assertTrue("Second put", res.isSuccess());</span> | 
|  | <span class="source-line-no">2514</span><span id="line-2514">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2515</span><span id="line-2515"></span> | 
|  | <span class="source-line-no">2516</span><span id="line-2516">    // checkAndDelete with correct value</span> | 
|  | <span class="source-line-no">2517</span><span id="line-2517">    delete = new Delete(row1, now + 3);</span> | 
|  | <span class="source-line-no">2518</span><span id="line-2518">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">2519</span><span id="line-2519">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2520</span><span id="line-2520">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, Bytes.toBytes(bd1)).build(delete));</span> | 
|  | <span class="source-line-no">2521</span><span id="line-2521">    assertTrue("Second delete", res.isSuccess());</span> | 
|  | <span class="source-line-no">2522</span><span id="line-2522">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2523</span><span id="line-2523">  }</span> | 
|  | <span class="source-line-no">2524</span><span id="line-2524"></span> | 
|  | <span class="source-line-no">2525</span><span id="line-2525">  @Test</span> | 
|  | <span class="source-line-no">2526</span><span id="line-2526">  public void testCheckAndMutateWithNonEqualCompareOp() throws IOException {</span> | 
|  | <span class="source-line-no">2527</span><span id="line-2527">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">2528</span><span id="line-2528">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">2529</span><span id="line-2529">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">2530</span><span id="line-2530">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">2531</span><span id="line-2531">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">2532</span><span id="line-2532">    byte[] val3 = Bytes.toBytes("value3");</span> | 
|  | <span class="source-line-no">2533</span><span id="line-2533">    byte[] val4 = Bytes.toBytes("value4");</span> | 
|  | <span class="source-line-no">2534</span><span id="line-2534"></span> | 
|  | <span class="source-line-no">2535</span><span id="line-2535">    // Setting up region</span> | 
|  | <span class="source-line-no">2536</span><span id="line-2536">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">2537</span><span id="line-2537">    // Putting val3 in key</span> | 
|  | <span class="source-line-no">2538</span><span id="line-2538">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">2539</span><span id="line-2539">    put.addColumn(fam1, qf1, val3);</span> | 
|  | <span class="source-line-no">2540</span><span id="line-2540">    region.put(put);</span> | 
|  | <span class="source-line-no">2541</span><span id="line-2541"></span> | 
|  | <span class="source-line-no">2542</span><span id="line-2542">    // Test CompareOp.LESS: original = val3, compare with val3, fail</span> | 
|  | <span class="source-line-no">2543</span><span id="line-2543">    CheckAndMutateResult res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2544</span><span id="line-2544">      CheckAndMutate.newBuilder(row1).ifMatches(fam1, qf1, CompareOperator.LESS, val3).build(put));</span> | 
|  | <span class="source-line-no">2545</span><span id="line-2545">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2546</span><span id="line-2546">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2547</span><span id="line-2547"></span> | 
|  | <span class="source-line-no">2548</span><span id="line-2548">    // Test CompareOp.LESS: original = val3, compare with val4, fail</span> | 
|  | <span class="source-line-no">2549</span><span id="line-2549">    res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2550</span><span id="line-2550">      CheckAndMutate.newBuilder(row1).ifMatches(fam1, qf1, CompareOperator.LESS, val4).build(put));</span> | 
|  | <span class="source-line-no">2551</span><span id="line-2551">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2552</span><span id="line-2552">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2553</span><span id="line-2553"></span> | 
|  | <span class="source-line-no">2554</span><span id="line-2554">    // Test CompareOp.LESS: original = val3, compare with val2,</span> | 
|  | <span class="source-line-no">2555</span><span id="line-2555">    // succeed (now value = val2)</span> | 
|  | <span class="source-line-no">2556</span><span id="line-2556">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2557</span><span id="line-2557">    put.addColumn(fam1, qf1, val2);</span> | 
|  | <span class="source-line-no">2558</span><span id="line-2558">    res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2559</span><span id="line-2559">      CheckAndMutate.newBuilder(row1).ifMatches(fam1, qf1, CompareOperator.LESS, val2).build(put));</span> | 
|  | <span class="source-line-no">2560</span><span id="line-2560">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2561</span><span id="line-2561">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2562</span><span id="line-2562"></span> | 
|  | <span class="source-line-no">2563</span><span id="line-2563">    // Test CompareOp.LESS_OR_EQUAL: original = val2, compare with val3, fail</span> | 
|  | <span class="source-line-no">2564</span><span id="line-2564">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2565</span><span id="line-2565">      .ifMatches(fam1, qf1, CompareOperator.LESS_OR_EQUAL, val3).build(put));</span> | 
|  | <span class="source-line-no">2566</span><span id="line-2566">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2567</span><span id="line-2567">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2568</span><span id="line-2568"></span> | 
|  | <span class="source-line-no">2569</span><span id="line-2569">    // Test CompareOp.LESS_OR_EQUAL: original = val2, compare with val2,</span> | 
|  | <span class="source-line-no">2570</span><span id="line-2570">    // succeed (value still = val2)</span> | 
|  | <span class="source-line-no">2571</span><span id="line-2571">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2572</span><span id="line-2572">      .ifMatches(fam1, qf1, CompareOperator.LESS_OR_EQUAL, val2).build(put));</span> | 
|  | <span class="source-line-no">2573</span><span id="line-2573">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2574</span><span id="line-2574">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2575</span><span id="line-2575"></span> | 
|  | <span class="source-line-no">2576</span><span id="line-2576">    // Test CompareOp.LESS_OR_EQUAL: original = val2, compare with val1,</span> | 
|  | <span class="source-line-no">2577</span><span id="line-2577">    // succeed (now value = val3)</span> | 
|  | <span class="source-line-no">2578</span><span id="line-2578">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2579</span><span id="line-2579">    put.addColumn(fam1, qf1, val3);</span> | 
|  | <span class="source-line-no">2580</span><span id="line-2580">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2581</span><span id="line-2581">      .ifMatches(fam1, qf1, CompareOperator.LESS_OR_EQUAL, val1).build(put));</span> | 
|  | <span class="source-line-no">2582</span><span id="line-2582">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2583</span><span id="line-2583">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2584</span><span id="line-2584"></span> | 
|  | <span class="source-line-no">2585</span><span id="line-2585">    // Test CompareOp.GREATER: original = val3, compare with val3, fail</span> | 
|  | <span class="source-line-no">2586</span><span id="line-2586">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2587</span><span id="line-2587">      .ifMatches(fam1, qf1, CompareOperator.GREATER, val3).build(put));</span> | 
|  | <span class="source-line-no">2588</span><span id="line-2588">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2589</span><span id="line-2589">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2590</span><span id="line-2590"></span> | 
|  | <span class="source-line-no">2591</span><span id="line-2591">    // Test CompareOp.GREATER: original = val3, compare with val2, fail</span> | 
|  | <span class="source-line-no">2592</span><span id="line-2592">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2593</span><span id="line-2593">      .ifMatches(fam1, qf1, CompareOperator.GREATER, val2).build(put));</span> | 
|  | <span class="source-line-no">2594</span><span id="line-2594">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2595</span><span id="line-2595">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2596</span><span id="line-2596"></span> | 
|  | <span class="source-line-no">2597</span><span id="line-2597">    // Test CompareOp.GREATER: original = val3, compare with val4,</span> | 
|  | <span class="source-line-no">2598</span><span id="line-2598">    // succeed (now value = val2)</span> | 
|  | <span class="source-line-no">2599</span><span id="line-2599">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2600</span><span id="line-2600">    put.addColumn(fam1, qf1, val2);</span> | 
|  | <span class="source-line-no">2601</span><span id="line-2601">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2602</span><span id="line-2602">      .ifMatches(fam1, qf1, CompareOperator.GREATER, val4).build(put));</span> | 
|  | <span class="source-line-no">2603</span><span id="line-2603">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2604</span><span id="line-2604">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2605</span><span id="line-2605"></span> | 
|  | <span class="source-line-no">2606</span><span id="line-2606">    // Test CompareOp.GREATER_OR_EQUAL: original = val2, compare with val1, fail</span> | 
|  | <span class="source-line-no">2607</span><span id="line-2607">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2608</span><span id="line-2608">      .ifMatches(fam1, qf1, CompareOperator.GREATER_OR_EQUAL, val1).build(put));</span> | 
|  | <span class="source-line-no">2609</span><span id="line-2609">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2610</span><span id="line-2610">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2611</span><span id="line-2611"></span> | 
|  | <span class="source-line-no">2612</span><span id="line-2612">    // Test CompareOp.GREATER_OR_EQUAL: original = val2, compare with val2,</span> | 
|  | <span class="source-line-no">2613</span><span id="line-2613">    // succeed (value still = val2)</span> | 
|  | <span class="source-line-no">2614</span><span id="line-2614">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2615</span><span id="line-2615">      .ifMatches(fam1, qf1, CompareOperator.GREATER_OR_EQUAL, val2).build(put));</span> | 
|  | <span class="source-line-no">2616</span><span id="line-2616">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2617</span><span id="line-2617">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2618</span><span id="line-2618"></span> | 
|  | <span class="source-line-no">2619</span><span id="line-2619">    // Test CompareOp.GREATER_OR_EQUAL: original = val2, compare with val3, succeed</span> | 
|  | <span class="source-line-no">2620</span><span id="line-2620">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2621</span><span id="line-2621">      .ifMatches(fam1, qf1, CompareOperator.GREATER_OR_EQUAL, val3).build(put));</span> | 
|  | <span class="source-line-no">2622</span><span id="line-2622">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2623</span><span id="line-2623">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2624</span><span id="line-2624">  }</span> | 
|  | <span class="source-line-no">2625</span><span id="line-2625"></span> | 
|  | <span class="source-line-no">2626</span><span id="line-2626">  @Test</span> | 
|  | <span class="source-line-no">2627</span><span id="line-2627">  public void testCheckAndPutThatPutWasWritten() throws IOException {</span> | 
|  | <span class="source-line-no">2628</span><span id="line-2628">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">2629</span><span id="line-2629">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">2630</span><span id="line-2630">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">2631</span><span id="line-2631">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">2632</span><span id="line-2632">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">2633</span><span id="line-2633">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">2634</span><span id="line-2634"></span> | 
|  | <span class="source-line-no">2635</span><span id="line-2635">    byte[][] families = { fam1, fam2 };</span> | 
|  | <span class="source-line-no">2636</span><span id="line-2636"></span> | 
|  | <span class="source-line-no">2637</span><span id="line-2637">    // Setting up region</span> | 
|  | <span class="source-line-no">2638</span><span id="line-2638">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">2639</span><span id="line-2639">    // Putting data in the key to check</span> | 
|  | <span class="source-line-no">2640</span><span id="line-2640">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">2641</span><span id="line-2641">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">2642</span><span id="line-2642">    region.put(put);</span> | 
|  | <span class="source-line-no">2643</span><span id="line-2643"></span> | 
|  | <span class="source-line-no">2644</span><span id="line-2644">    // Creating put to add</span> | 
|  | <span class="source-line-no">2645</span><span id="line-2645">    long ts = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">2646</span><span id="line-2646">    KeyValue kv = new KeyValue(row1, fam2, qf1, ts, KeyValue.Type.Put, val2);</span> | 
|  | <span class="source-line-no">2647</span><span id="line-2647">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2648</span><span id="line-2648">    put.add(kv);</span> | 
|  | <span class="source-line-no">2649</span><span id="line-2649"></span> | 
|  | <span class="source-line-no">2650</span><span id="line-2650">    // checkAndPut with wrong value</span> | 
|  | <span class="source-line-no">2651</span><span id="line-2651">    CheckAndMutateResult res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2652</span><span id="line-2652">      CheckAndMutate.newBuilder(row1).ifMatches(fam1, qf1, CompareOperator.EQUAL, val1).build(put));</span> | 
|  | <span class="source-line-no">2653</span><span id="line-2653">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2654</span><span id="line-2654">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2655</span><span id="line-2655"></span> | 
|  | <span class="source-line-no">2656</span><span id="line-2656">    Get get = new Get(row1);</span> | 
|  | <span class="source-line-no">2657</span><span id="line-2657">    get.addColumn(fam2, qf1);</span> | 
|  | <span class="source-line-no">2658</span><span id="line-2658">    Cell[] actual = region.get(get).rawCells();</span> | 
|  | <span class="source-line-no">2659</span><span id="line-2659"></span> | 
|  | <span class="source-line-no">2660</span><span id="line-2660">    Cell[] expected = { kv };</span> | 
|  | <span class="source-line-no">2661</span><span id="line-2661"></span> | 
|  | <span class="source-line-no">2662</span><span id="line-2662">    assertEquals(expected.length, actual.length);</span> | 
|  | <span class="source-line-no">2663</span><span id="line-2663">    for (int i = 0; i < actual.length; i++) {</span> | 
|  | <span class="source-line-no">2664</span><span id="line-2664">      assertEquals(expected[i], actual[i]);</span> | 
|  | <span class="source-line-no">2665</span><span id="line-2665">    }</span> | 
|  | <span class="source-line-no">2666</span><span id="line-2666">  }</span> | 
|  | <span class="source-line-no">2667</span><span id="line-2667"></span> | 
|  | <span class="source-line-no">2668</span><span id="line-2668">  @Test</span> | 
|  | <span class="source-line-no">2669</span><span id="line-2669">  public void testCheckAndDeleteThatDeleteWasWritten() throws IOException {</span> | 
|  | <span class="source-line-no">2670</span><span id="line-2670">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">2671</span><span id="line-2671">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">2672</span><span id="line-2672">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">2673</span><span id="line-2673">    byte[] qf1 = Bytes.toBytes("qualifier1");</span> | 
|  | <span class="source-line-no">2674</span><span id="line-2674">    byte[] qf2 = Bytes.toBytes("qualifier2");</span> | 
|  | <span class="source-line-no">2675</span><span id="line-2675">    byte[] qf3 = Bytes.toBytes("qualifier3");</span> | 
|  | <span class="source-line-no">2676</span><span id="line-2676">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">2677</span><span id="line-2677">    byte[] val2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">2678</span><span id="line-2678">    byte[] val3 = Bytes.toBytes("value3");</span> | 
|  | <span class="source-line-no">2679</span><span id="line-2679">    byte[] emptyVal = new byte[] {};</span> | 
|  | <span class="source-line-no">2680</span><span id="line-2680"></span> | 
|  | <span class="source-line-no">2681</span><span id="line-2681">    byte[][] families = { fam1, fam2 };</span> | 
|  | <span class="source-line-no">2682</span><span id="line-2682"></span> | 
|  | <span class="source-line-no">2683</span><span id="line-2683">    // Setting up region</span> | 
|  | <span class="source-line-no">2684</span><span id="line-2684">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">2685</span><span id="line-2685">    // Put content</span> | 
|  | <span class="source-line-no">2686</span><span id="line-2686">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">2687</span><span id="line-2687">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">2688</span><span id="line-2688">    region.put(put);</span> | 
|  | <span class="source-line-no">2689</span><span id="line-2689">    Threads.sleep(2);</span> | 
|  | <span class="source-line-no">2690</span><span id="line-2690"></span> | 
|  | <span class="source-line-no">2691</span><span id="line-2691">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">2692</span><span id="line-2692">    put.addColumn(fam1, qf1, val2);</span> | 
|  | <span class="source-line-no">2693</span><span id="line-2693">    put.addColumn(fam2, qf1, val3);</span> | 
|  | <span class="source-line-no">2694</span><span id="line-2694">    put.addColumn(fam2, qf2, val2);</span> | 
|  | <span class="source-line-no">2695</span><span id="line-2695">    put.addColumn(fam2, qf3, val1);</span> | 
|  | <span class="source-line-no">2696</span><span id="line-2696">    put.addColumn(fam1, qf3, val1);</span> | 
|  | <span class="source-line-no">2697</span><span id="line-2697">    region.put(put);</span> | 
|  | <span class="source-line-no">2698</span><span id="line-2698"></span> | 
|  | <span class="source-line-no">2699</span><span id="line-2699">    LOG.info("get={}", region.get(new Get(row1).addColumn(fam1, qf1)).toString());</span> | 
|  | <span class="source-line-no">2700</span><span id="line-2700"></span> | 
|  | <span class="source-line-no">2701</span><span id="line-2701">    // Multi-column delete</span> | 
|  | <span class="source-line-no">2702</span><span id="line-2702">    Delete delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2703</span><span id="line-2703">    delete.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">2704</span><span id="line-2704">    delete.addColumn(fam2, qf1);</span> | 
|  | <span class="source-line-no">2705</span><span id="line-2705">    delete.addColumn(fam1, qf3);</span> | 
|  | <span class="source-line-no">2706</span><span id="line-2706">    CheckAndMutateResult res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2707</span><span id="line-2707">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, val2).build(delete));</span> | 
|  | <span class="source-line-no">2708</span><span id="line-2708">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2709</span><span id="line-2709">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2710</span><span id="line-2710"></span> | 
|  | <span class="source-line-no">2711</span><span id="line-2711">    Get get = new Get(row1);</span> | 
|  | <span class="source-line-no">2712</span><span id="line-2712">    get.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">2713</span><span id="line-2713">    get.addColumn(fam1, qf3);</span> | 
|  | <span class="source-line-no">2714</span><span id="line-2714">    get.addColumn(fam2, qf2);</span> | 
|  | <span class="source-line-no">2715</span><span id="line-2715">    Result r = region.get(get);</span> | 
|  | <span class="source-line-no">2716</span><span id="line-2716">    assertEquals(2, r.size());</span> | 
|  | <span class="source-line-no">2717</span><span id="line-2717">    assertArrayEquals(val1, r.getValue(fam1, qf1));</span> | 
|  | <span class="source-line-no">2718</span><span id="line-2718">    assertArrayEquals(val2, r.getValue(fam2, qf2));</span> | 
|  | <span class="source-line-no">2719</span><span id="line-2719"></span> | 
|  | <span class="source-line-no">2720</span><span id="line-2720">    // Family delete</span> | 
|  | <span class="source-line-no">2721</span><span id="line-2721">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2722</span><span id="line-2722">    delete.addFamily(fam2);</span> | 
|  | <span class="source-line-no">2723</span><span id="line-2723">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2724</span><span id="line-2724">      .ifMatches(fam2, qf1, CompareOperator.EQUAL, emptyVal).build(delete));</span> | 
|  | <span class="source-line-no">2725</span><span id="line-2725">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2726</span><span id="line-2726">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2727</span><span id="line-2727"></span> | 
|  | <span class="source-line-no">2728</span><span id="line-2728">    get = new Get(row1);</span> | 
|  | <span class="source-line-no">2729</span><span id="line-2729">    r = region.get(get);</span> | 
|  | <span class="source-line-no">2730</span><span id="line-2730">    assertEquals(1, r.size());</span> | 
|  | <span class="source-line-no">2731</span><span id="line-2731">    assertArrayEquals(val1, r.getValue(fam1, qf1));</span> | 
|  | <span class="source-line-no">2732</span><span id="line-2732"></span> | 
|  | <span class="source-line-no">2733</span><span id="line-2733">    // Row delete</span> | 
|  | <span class="source-line-no">2734</span><span id="line-2734">    delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">2735</span><span id="line-2735">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row1)</span> | 
|  | <span class="source-line-no">2736</span><span id="line-2736">      .ifMatches(fam1, qf1, CompareOperator.EQUAL, val1).build(delete));</span> | 
|  | <span class="source-line-no">2737</span><span id="line-2737">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2738</span><span id="line-2738">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2739</span><span id="line-2739"></span> | 
|  | <span class="source-line-no">2740</span><span id="line-2740">    get = new Get(row1);</span> | 
|  | <span class="source-line-no">2741</span><span id="line-2741">    r = region.get(get);</span> | 
|  | <span class="source-line-no">2742</span><span id="line-2742">    assertEquals(0, r.size());</span> | 
|  | <span class="source-line-no">2743</span><span id="line-2743">  }</span> | 
|  | <span class="source-line-no">2744</span><span id="line-2744"></span> | 
|  | <span class="source-line-no">2745</span><span id="line-2745">  @Test</span> | 
|  | <span class="source-line-no">2746</span><span id="line-2746">  public void testCheckAndMutateWithFilters() throws Throwable {</span> | 
|  | <span class="source-line-no">2747</span><span id="line-2747">    final byte[] FAMILY = Bytes.toBytes("fam");</span> | 
|  | <span class="source-line-no">2748</span><span id="line-2748"></span> | 
|  | <span class="source-line-no">2749</span><span id="line-2749">    // Setting up region</span> | 
|  | <span class="source-line-no">2750</span><span id="line-2750">    this.region = initHRegion(tableName, method, CONF, FAMILY);</span> | 
|  | <span class="source-line-no">2751</span><span id="line-2751"></span> | 
|  | <span class="source-line-no">2752</span><span id="line-2752">    // Put one row</span> | 
|  | <span class="source-line-no">2753</span><span id="line-2753">    Put put = new Put(row);</span> | 
|  | <span class="source-line-no">2754</span><span id="line-2754">    put.addColumn(FAMILY, Bytes.toBytes("A"), Bytes.toBytes("a"));</span> | 
|  | <span class="source-line-no">2755</span><span id="line-2755">    put.addColumn(FAMILY, Bytes.toBytes("B"), Bytes.toBytes("b"));</span> | 
|  | <span class="source-line-no">2756</span><span id="line-2756">    put.addColumn(FAMILY, Bytes.toBytes("C"), Bytes.toBytes("c"));</span> | 
|  | <span class="source-line-no">2757</span><span id="line-2757">    region.put(put);</span> | 
|  | <span class="source-line-no">2758</span><span id="line-2758"></span> | 
|  | <span class="source-line-no">2759</span><span id="line-2759">    // Put with success</span> | 
|  | <span class="source-line-no">2760</span><span id="line-2760">    CheckAndMutateResult res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2761</span><span id="line-2761">      .ifMatches(new FilterList(</span> | 
|  | <span class="source-line-no">2762</span><span id="line-2762">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2763</span><span id="line-2763">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2764</span><span id="line-2764">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("B"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2765</span><span id="line-2765">          Bytes.toBytes("b"))))</span> | 
|  | <span class="source-line-no">2766</span><span id="line-2766">      .build(new Put(row).addColumn(FAMILY, Bytes.toBytes("D"), Bytes.toBytes("d"))));</span> | 
|  | <span class="source-line-no">2767</span><span id="line-2767">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2768</span><span id="line-2768">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2769</span><span id="line-2769"></span> | 
|  | <span class="source-line-no">2770</span><span id="line-2770">    Result result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("D")));</span> | 
|  | <span class="source-line-no">2771</span><span id="line-2771">    assertEquals("d", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("D"))));</span> | 
|  | <span class="source-line-no">2772</span><span id="line-2772"></span> | 
|  | <span class="source-line-no">2773</span><span id="line-2773">    // Put with failure</span> | 
|  | <span class="source-line-no">2774</span><span id="line-2774">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2775</span><span id="line-2775">      .ifMatches(new FilterList(</span> | 
|  | <span class="source-line-no">2776</span><span id="line-2776">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2777</span><span id="line-2777">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2778</span><span id="line-2778">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("B"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2779</span><span id="line-2779">          Bytes.toBytes("c"))))</span> | 
|  | <span class="source-line-no">2780</span><span id="line-2780">      .build(new Put(row).addColumn(FAMILY, Bytes.toBytes("E"), Bytes.toBytes("e"))));</span> | 
|  | <span class="source-line-no">2781</span><span id="line-2781">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2782</span><span id="line-2782">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2783</span><span id="line-2783"></span> | 
|  | <span class="source-line-no">2784</span><span id="line-2784">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("E"))).isEmpty());</span> | 
|  | <span class="source-line-no">2785</span><span id="line-2785"></span> | 
|  | <span class="source-line-no">2786</span><span id="line-2786">    // Delete with success</span> | 
|  | <span class="source-line-no">2787</span><span id="line-2787">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2788</span><span id="line-2788">      .ifMatches(new FilterList(</span> | 
|  | <span class="source-line-no">2789</span><span id="line-2789">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2790</span><span id="line-2790">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2791</span><span id="line-2791">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("B"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2792</span><span id="line-2792">          Bytes.toBytes("b"))))</span> | 
|  | <span class="source-line-no">2793</span><span id="line-2793">      .build(new Delete(row).addColumns(FAMILY, Bytes.toBytes("D"))));</span> | 
|  | <span class="source-line-no">2794</span><span id="line-2794">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2795</span><span id="line-2795">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2796</span><span id="line-2796"></span> | 
|  | <span class="source-line-no">2797</span><span id="line-2797">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("D"))).isEmpty());</span> | 
|  | <span class="source-line-no">2798</span><span id="line-2798"></span> | 
|  | <span class="source-line-no">2799</span><span id="line-2799">    // Mutate with success</span> | 
|  | <span class="source-line-no">2800</span><span id="line-2800">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2801</span><span id="line-2801">      .ifMatches(new FilterList(</span> | 
|  | <span class="source-line-no">2802</span><span id="line-2802">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2803</span><span id="line-2803">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2804</span><span id="line-2804">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("B"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2805</span><span id="line-2805">          Bytes.toBytes("b"))))</span> | 
|  | <span class="source-line-no">2806</span><span id="line-2806">      .build(new RowMutations(row)</span> | 
|  | <span class="source-line-no">2807</span><span id="line-2807">        .add((Mutation) new Put(row).addColumn(FAMILY, Bytes.toBytes("E"), Bytes.toBytes("e")))</span> | 
|  | <span class="source-line-no">2808</span><span id="line-2808">        .add((Mutation) new Delete(row).addColumns(FAMILY, Bytes.toBytes("A")))));</span> | 
|  | <span class="source-line-no">2809</span><span id="line-2809">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2810</span><span id="line-2810">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2811</span><span id="line-2811"></span> | 
|  | <span class="source-line-no">2812</span><span id="line-2812">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("E")));</span> | 
|  | <span class="source-line-no">2813</span><span id="line-2813">    assertEquals("e", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("E"))));</span> | 
|  | <span class="source-line-no">2814</span><span id="line-2814"></span> | 
|  | <span class="source-line-no">2815</span><span id="line-2815">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("A"))).isEmpty());</span> | 
|  | <span class="source-line-no">2816</span><span id="line-2816">  }</span> | 
|  | <span class="source-line-no">2817</span><span id="line-2817"></span> | 
|  | <span class="source-line-no">2818</span><span id="line-2818">  @Test</span> | 
|  | <span class="source-line-no">2819</span><span id="line-2819">  public void testCheckAndMutateWithFiltersAndTimeRange() throws Throwable {</span> | 
|  | <span class="source-line-no">2820</span><span id="line-2820">    final byte[] FAMILY = Bytes.toBytes("fam");</span> | 
|  | <span class="source-line-no">2821</span><span id="line-2821"></span> | 
|  | <span class="source-line-no">2822</span><span id="line-2822">    // Setting up region</span> | 
|  | <span class="source-line-no">2823</span><span id="line-2823">    this.region = initHRegion(tableName, method, CONF, FAMILY);</span> | 
|  | <span class="source-line-no">2824</span><span id="line-2824"></span> | 
|  | <span class="source-line-no">2825</span><span id="line-2825">    // Put with specifying the timestamp</span> | 
|  | <span class="source-line-no">2826</span><span id="line-2826">    region.put(new Put(row).addColumn(FAMILY, Bytes.toBytes("A"), 100, Bytes.toBytes("a")));</span> | 
|  | <span class="source-line-no">2827</span><span id="line-2827"></span> | 
|  | <span class="source-line-no">2828</span><span id="line-2828">    // Put with success</span> | 
|  | <span class="source-line-no">2829</span><span id="line-2829">    CheckAndMutateResult res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2830</span><span id="line-2830">      .ifMatches(new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2831</span><span id="line-2831">        Bytes.toBytes("a")))</span> | 
|  | <span class="source-line-no">2832</span><span id="line-2832">      .timeRange(TimeRange.between(0, 101))</span> | 
|  | <span class="source-line-no">2833</span><span id="line-2833">      .build(new Put(row).addColumn(FAMILY, Bytes.toBytes("B"), Bytes.toBytes("b"))));</span> | 
|  | <span class="source-line-no">2834</span><span id="line-2834">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2835</span><span id="line-2835">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2836</span><span id="line-2836"></span> | 
|  | <span class="source-line-no">2837</span><span id="line-2837">    Result result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2838</span><span id="line-2838">    assertEquals("b", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2839</span><span id="line-2839"></span> | 
|  | <span class="source-line-no">2840</span><span id="line-2840">    // Put with failure</span> | 
|  | <span class="source-line-no">2841</span><span id="line-2841">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2842</span><span id="line-2842">      .ifMatches(new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2843</span><span id="line-2843">        Bytes.toBytes("a")))</span> | 
|  | <span class="source-line-no">2844</span><span id="line-2844">      .timeRange(TimeRange.between(0, 100))</span> | 
|  | <span class="source-line-no">2845</span><span id="line-2845">      .build(new Put(row).addColumn(FAMILY, Bytes.toBytes("C"), Bytes.toBytes("c"))));</span> | 
|  | <span class="source-line-no">2846</span><span id="line-2846">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2847</span><span id="line-2847">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2848</span><span id="line-2848"></span> | 
|  | <span class="source-line-no">2849</span><span id="line-2849">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("C"))).isEmpty());</span> | 
|  | <span class="source-line-no">2850</span><span id="line-2850"></span> | 
|  | <span class="source-line-no">2851</span><span id="line-2851">    // RowMutations with success</span> | 
|  | <span class="source-line-no">2852</span><span id="line-2852">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2853</span><span id="line-2853">      .ifMatches(new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2854</span><span id="line-2854">        Bytes.toBytes("a")))</span> | 
|  | <span class="source-line-no">2855</span><span id="line-2855">      .timeRange(TimeRange.between(0, 101))</span> | 
|  | <span class="source-line-no">2856</span><span id="line-2856">      .build(new RowMutations(row)</span> | 
|  | <span class="source-line-no">2857</span><span id="line-2857">        .add((Mutation) new Put(row).addColumn(FAMILY, Bytes.toBytes("D"), Bytes.toBytes("d")))</span> | 
|  | <span class="source-line-no">2858</span><span id="line-2858">        .add((Mutation) new Delete(row).addColumns(FAMILY, Bytes.toBytes("A")))));</span> | 
|  | <span class="source-line-no">2859</span><span id="line-2859">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2860</span><span id="line-2860">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2861</span><span id="line-2861"></span> | 
|  | <span class="source-line-no">2862</span><span id="line-2862">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("D")));</span> | 
|  | <span class="source-line-no">2863</span><span id="line-2863">    assertEquals("d", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("D"))));</span> | 
|  | <span class="source-line-no">2864</span><span id="line-2864"></span> | 
|  | <span class="source-line-no">2865</span><span id="line-2865">    assertTrue(region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("A"))).isEmpty());</span> | 
|  | <span class="source-line-no">2866</span><span id="line-2866">  }</span> | 
|  | <span class="source-line-no">2867</span><span id="line-2867"></span> | 
|  | <span class="source-line-no">2868</span><span id="line-2868">  @Test</span> | 
|  | <span class="source-line-no">2869</span><span id="line-2869">  public void testCheckAndIncrement() throws Throwable {</span> | 
|  | <span class="source-line-no">2870</span><span id="line-2870">    final byte[] FAMILY = Bytes.toBytes("fam");</span> | 
|  | <span class="source-line-no">2871</span><span id="line-2871"></span> | 
|  | <span class="source-line-no">2872</span><span id="line-2872">    // Setting up region</span> | 
|  | <span class="source-line-no">2873</span><span id="line-2873">    this.region = initHRegion(tableName, method, CONF, FAMILY);</span> | 
|  | <span class="source-line-no">2874</span><span id="line-2874"></span> | 
|  | <span class="source-line-no">2875</span><span id="line-2875">    region.put(new Put(row).addColumn(FAMILY, Bytes.toBytes("A"), Bytes.toBytes("a")));</span> | 
|  | <span class="source-line-no">2876</span><span id="line-2876"></span> | 
|  | <span class="source-line-no">2877</span><span id="line-2877">    // CheckAndIncrement with correct value</span> | 
|  | <span class="source-line-no">2878</span><span id="line-2878">    CheckAndMutateResult res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2879</span><span id="line-2879">      CheckAndMutate.newBuilder(row).ifEquals(FAMILY, Bytes.toBytes("A"), Bytes.toBytes("a"))</span> | 
|  | <span class="source-line-no">2880</span><span id="line-2880">        .build(new Increment(row).addColumn(FAMILY, Bytes.toBytes("B"), 1)));</span> | 
|  | <span class="source-line-no">2881</span><span id="line-2881">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2882</span><span id="line-2882">    assertEquals(1, Bytes.toLong(res.getResult().getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2883</span><span id="line-2883"></span> | 
|  | <span class="source-line-no">2884</span><span id="line-2884">    Result result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2885</span><span id="line-2885">    assertEquals(1, Bytes.toLong(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2886</span><span id="line-2886"></span> | 
|  | <span class="source-line-no">2887</span><span id="line-2887">    // CheckAndIncrement with wrong value</span> | 
|  | <span class="source-line-no">2888</span><span id="line-2888">    res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2889</span><span id="line-2889">      CheckAndMutate.newBuilder(row).ifEquals(FAMILY, Bytes.toBytes("A"), Bytes.toBytes("b"))</span> | 
|  | <span class="source-line-no">2890</span><span id="line-2890">        .build(new Increment(row).addColumn(FAMILY, Bytes.toBytes("B"), 1)));</span> | 
|  | <span class="source-line-no">2891</span><span id="line-2891">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2892</span><span id="line-2892">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2893</span><span id="line-2893"></span> | 
|  | <span class="source-line-no">2894</span><span id="line-2894">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2895</span><span id="line-2895">    assertEquals(1, Bytes.toLong(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2896</span><span id="line-2896"></span> | 
|  | <span class="source-line-no">2897</span><span id="line-2897">    region.put(new Put(row).addColumn(FAMILY, Bytes.toBytes("C"), Bytes.toBytes("c")));</span> | 
|  | <span class="source-line-no">2898</span><span id="line-2898"></span> | 
|  | <span class="source-line-no">2899</span><span id="line-2899">    // CheckAndIncrement with a filter and correct value</span> | 
|  | <span class="source-line-no">2900</span><span id="line-2900">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2901</span><span id="line-2901">      .ifMatches(new FilterList(</span> | 
|  | <span class="source-line-no">2902</span><span id="line-2902">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2903</span><span id="line-2903">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2904</span><span id="line-2904">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("C"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2905</span><span id="line-2905">          Bytes.toBytes("c"))))</span> | 
|  | <span class="source-line-no">2906</span><span id="line-2906">      .build(new Increment(row).addColumn(FAMILY, Bytes.toBytes("B"), 2)));</span> | 
|  | <span class="source-line-no">2907</span><span id="line-2907">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2908</span><span id="line-2908">    assertEquals(3, Bytes.toLong(res.getResult().getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2909</span><span id="line-2909"></span> | 
|  | <span class="source-line-no">2910</span><span id="line-2910">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2911</span><span id="line-2911">    assertEquals(3, Bytes.toLong(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2912</span><span id="line-2912"></span> | 
|  | <span class="source-line-no">2913</span><span id="line-2913">    // CheckAndIncrement with a filter and correct value</span> | 
|  | <span class="source-line-no">2914</span><span id="line-2914">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2915</span><span id="line-2915">      .ifMatches(new FilterList(</span> | 
|  | <span class="source-line-no">2916</span><span id="line-2916">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2917</span><span id="line-2917">          Bytes.toBytes("b")),</span> | 
|  | <span class="source-line-no">2918</span><span id="line-2918">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("C"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2919</span><span id="line-2919">          Bytes.toBytes("d"))))</span> | 
|  | <span class="source-line-no">2920</span><span id="line-2920">      .build(new Increment(row).addColumn(FAMILY, Bytes.toBytes("B"), 2)));</span> | 
|  | <span class="source-line-no">2921</span><span id="line-2921">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2922</span><span id="line-2922">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2923</span><span id="line-2923"></span> | 
|  | <span class="source-line-no">2924</span><span id="line-2924">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2925</span><span id="line-2925">    assertEquals(3, Bytes.toLong(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2926</span><span id="line-2926">  }</span> | 
|  | <span class="source-line-no">2927</span><span id="line-2927"></span> | 
|  | <span class="source-line-no">2928</span><span id="line-2928">  @Test</span> | 
|  | <span class="source-line-no">2929</span><span id="line-2929">  public void testCheckAndAppend() throws Throwable {</span> | 
|  | <span class="source-line-no">2930</span><span id="line-2930">    final byte[] FAMILY = Bytes.toBytes("fam");</span> | 
|  | <span class="source-line-no">2931</span><span id="line-2931"></span> | 
|  | <span class="source-line-no">2932</span><span id="line-2932">    // Setting up region</span> | 
|  | <span class="source-line-no">2933</span><span id="line-2933">    this.region = initHRegion(tableName, method, CONF, FAMILY);</span> | 
|  | <span class="source-line-no">2934</span><span id="line-2934"></span> | 
|  | <span class="source-line-no">2935</span><span id="line-2935">    region.put(new Put(row).addColumn(FAMILY, Bytes.toBytes("A"), Bytes.toBytes("a")));</span> | 
|  | <span class="source-line-no">2936</span><span id="line-2936"></span> | 
|  | <span class="source-line-no">2937</span><span id="line-2937">    // CheckAndAppend with correct value</span> | 
|  | <span class="source-line-no">2938</span><span id="line-2938">    CheckAndMutateResult res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2939</span><span id="line-2939">      CheckAndMutate.newBuilder(row).ifEquals(FAMILY, Bytes.toBytes("A"), Bytes.toBytes("a"))</span> | 
|  | <span class="source-line-no">2940</span><span id="line-2940">        .build(new Append(row).addColumn(FAMILY, Bytes.toBytes("B"), Bytes.toBytes("b"))));</span> | 
|  | <span class="source-line-no">2941</span><span id="line-2941">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2942</span><span id="line-2942">    assertEquals("b", Bytes.toString(res.getResult().getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2943</span><span id="line-2943"></span> | 
|  | <span class="source-line-no">2944</span><span id="line-2944">    Result result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2945</span><span id="line-2945">    assertEquals("b", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2946</span><span id="line-2946"></span> | 
|  | <span class="source-line-no">2947</span><span id="line-2947">    // CheckAndAppend with wrong value</span> | 
|  | <span class="source-line-no">2948</span><span id="line-2948">    res = region.checkAndMutate(</span> | 
|  | <span class="source-line-no">2949</span><span id="line-2949">      CheckAndMutate.newBuilder(row).ifEquals(FAMILY, Bytes.toBytes("A"), Bytes.toBytes("b"))</span> | 
|  | <span class="source-line-no">2950</span><span id="line-2950">        .build(new Append(row).addColumn(FAMILY, Bytes.toBytes("B"), Bytes.toBytes("b"))));</span> | 
|  | <span class="source-line-no">2951</span><span id="line-2951">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2952</span><span id="line-2952">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2953</span><span id="line-2953"></span> | 
|  | <span class="source-line-no">2954</span><span id="line-2954">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2955</span><span id="line-2955">    assertEquals("b", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2956</span><span id="line-2956"></span> | 
|  | <span class="source-line-no">2957</span><span id="line-2957">    region.put(new Put(row).addColumn(FAMILY, Bytes.toBytes("C"), Bytes.toBytes("c")));</span> | 
|  | <span class="source-line-no">2958</span><span id="line-2958"></span> | 
|  | <span class="source-line-no">2959</span><span id="line-2959">    // CheckAndAppend with a filter and correct value</span> | 
|  | <span class="source-line-no">2960</span><span id="line-2960">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2961</span><span id="line-2961">      .ifMatches(new FilterList(</span> | 
|  | <span class="source-line-no">2962</span><span id="line-2962">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2963</span><span id="line-2963">          Bytes.toBytes("a")),</span> | 
|  | <span class="source-line-no">2964</span><span id="line-2964">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("C"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2965</span><span id="line-2965">          Bytes.toBytes("c"))))</span> | 
|  | <span class="source-line-no">2966</span><span id="line-2966">      .build(new Append(row).addColumn(FAMILY, Bytes.toBytes("B"), Bytes.toBytes("bb"))));</span> | 
|  | <span class="source-line-no">2967</span><span id="line-2967">    assertTrue(res.isSuccess());</span> | 
|  | <span class="source-line-no">2968</span><span id="line-2968">    assertEquals("bbb", Bytes.toString(res.getResult().getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2969</span><span id="line-2969"></span> | 
|  | <span class="source-line-no">2970</span><span id="line-2970">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2971</span><span id="line-2971">    assertEquals("bbb", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2972</span><span id="line-2972"></span> | 
|  | <span class="source-line-no">2973</span><span id="line-2973">    // CheckAndAppend with a filter and wrong value</span> | 
|  | <span class="source-line-no">2974</span><span id="line-2974">    res = region.checkAndMutate(CheckAndMutate.newBuilder(row)</span> | 
|  | <span class="source-line-no">2975</span><span id="line-2975">      .ifMatches(new FilterList(</span> | 
|  | <span class="source-line-no">2976</span><span id="line-2976">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("A"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2977</span><span id="line-2977">          Bytes.toBytes("b")),</span> | 
|  | <span class="source-line-no">2978</span><span id="line-2978">        new SingleColumnValueFilter(FAMILY, Bytes.toBytes("C"), CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">2979</span><span id="line-2979">          Bytes.toBytes("d"))))</span> | 
|  | <span class="source-line-no">2980</span><span id="line-2980">      .build(new Append(row).addColumn(FAMILY, Bytes.toBytes("B"), Bytes.toBytes("bb"))));</span> | 
|  | <span class="source-line-no">2981</span><span id="line-2981">    assertFalse(res.isSuccess());</span> | 
|  | <span class="source-line-no">2982</span><span id="line-2982">    assertNull(res.getResult());</span> | 
|  | <span class="source-line-no">2983</span><span id="line-2983"></span> | 
|  | <span class="source-line-no">2984</span><span id="line-2984">    result = region.get(new Get(row).addColumn(FAMILY, Bytes.toBytes("B")));</span> | 
|  | <span class="source-line-no">2985</span><span id="line-2985">    assertEquals("bbb", Bytes.toString(result.getValue(FAMILY, Bytes.toBytes("B"))));</span> | 
|  | <span class="source-line-no">2986</span><span id="line-2986">  }</span> | 
|  | <span class="source-line-no">2987</span><span id="line-2987"></span> | 
|  | <span class="source-line-no">2988</span><span id="line-2988">  @Test</span> | 
|  | <span class="source-line-no">2989</span><span id="line-2989">  public void testCheckAndIncrementAndAppend() throws Throwable {</span> | 
|  | <span class="source-line-no">2990</span><span id="line-2990">    // Setting up region</span> | 
|  | <span class="source-line-no">2991</span><span id="line-2991">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">2992</span><span id="line-2992"></span> | 
|  | <span class="source-line-no">2993</span><span id="line-2993">    // CheckAndMutate with Increment and Append</span> | 
|  | <span class="source-line-no">2994</span><span id="line-2994">    CheckAndMutate checkAndMutate = CheckAndMutate.newBuilder(row).ifNotExists(fam1, qual)</span> | 
|  | <span class="source-line-no">2995</span><span id="line-2995">      .build(new RowMutations(row).add((Mutation) new Increment(row).addColumn(fam1, qual1, 1L))</span> | 
|  | <span class="source-line-no">2996</span><span id="line-2996">        .add((Mutation) new Append(row).addColumn(fam1, qual2, Bytes.toBytes("a"))));</span> | 
|  | <span class="source-line-no">2997</span><span id="line-2997"></span> | 
|  | <span class="source-line-no">2998</span><span id="line-2998">    CheckAndMutateResult result = region.checkAndMutate(checkAndMutate);</span> | 
|  | <span class="source-line-no">2999</span><span id="line-2999">    assertTrue(result.isSuccess());</span> | 
|  | <span class="source-line-no">3000</span><span id="line-3000">    assertEquals(1L, Bytes.toLong(result.getResult().getValue(fam1, qual1)));</span> | 
|  | <span class="source-line-no">3001</span><span id="line-3001">    assertEquals("a", Bytes.toString(result.getResult().getValue(fam1, qual2)));</span> | 
|  | <span class="source-line-no">3002</span><span id="line-3002"></span> | 
|  | <span class="source-line-no">3003</span><span id="line-3003">    Result r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">3004</span><span id="line-3004">    assertEquals(1L, Bytes.toLong(r.getValue(fam1, qual1)));</span> | 
|  | <span class="source-line-no">3005</span><span id="line-3005">    assertEquals("a", Bytes.toString(r.getValue(fam1, qual2)));</span> | 
|  | <span class="source-line-no">3006</span><span id="line-3006"></span> | 
|  | <span class="source-line-no">3007</span><span id="line-3007">    // Set return results to false</span> | 
|  | <span class="source-line-no">3008</span><span id="line-3008">    checkAndMutate = CheckAndMutate.newBuilder(row).ifNotExists(fam1, qual)</span> | 
|  | <span class="source-line-no">3009</span><span id="line-3009">      .build(new RowMutations(row)</span> | 
|  | <span class="source-line-no">3010</span><span id="line-3010">        .add((Mutation) new Increment(row).addColumn(fam1, qual1, 1L).setReturnResults(false))</span> | 
|  | <span class="source-line-no">3011</span><span id="line-3011">        .add((Mutation) new Append(row).addColumn(fam1, qual2, Bytes.toBytes("a"))</span> | 
|  | <span class="source-line-no">3012</span><span id="line-3012">          .setReturnResults(false)));</span> | 
|  | <span class="source-line-no">3013</span><span id="line-3013"></span> | 
|  | <span class="source-line-no">3014</span><span id="line-3014">    result = region.checkAndMutate(checkAndMutate);</span> | 
|  | <span class="source-line-no">3015</span><span id="line-3015">    assertTrue(result.isSuccess());</span> | 
|  | <span class="source-line-no">3016</span><span id="line-3016">    assertNull(result.getResult().getValue(fam1, qual1));</span> | 
|  | <span class="source-line-no">3017</span><span id="line-3017">    assertNull(result.getResult().getValue(fam1, qual2));</span> | 
|  | <span class="source-line-no">3018</span><span id="line-3018"></span> | 
|  | <span class="source-line-no">3019</span><span id="line-3019">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">3020</span><span id="line-3020">    assertEquals(2L, Bytes.toLong(r.getValue(fam1, qual1)));</span> | 
|  | <span class="source-line-no">3021</span><span id="line-3021">    assertEquals("aa", Bytes.toString(r.getValue(fam1, qual2)));</span> | 
|  | <span class="source-line-no">3022</span><span id="line-3022"></span> | 
|  | <span class="source-line-no">3023</span><span id="line-3023">    checkAndMutate = CheckAndMutate.newBuilder(row).ifNotExists(fam1, qual)</span> | 
|  | <span class="source-line-no">3024</span><span id="line-3024">      .build(new RowMutations(row).add((Mutation) new Increment(row).addColumn(fam1, qual1, 1L))</span> | 
|  | <span class="source-line-no">3025</span><span id="line-3025">        .add((Mutation) new Append(row).addColumn(fam1, qual2, Bytes.toBytes("a"))</span> | 
|  | <span class="source-line-no">3026</span><span id="line-3026">          .setReturnResults(false)));</span> | 
|  | <span class="source-line-no">3027</span><span id="line-3027"></span> | 
|  | <span class="source-line-no">3028</span><span id="line-3028">    result = region.checkAndMutate(checkAndMutate);</span> | 
|  | <span class="source-line-no">3029</span><span id="line-3029">    assertTrue(result.isSuccess());</span> | 
|  | <span class="source-line-no">3030</span><span id="line-3030">    assertEquals(3L, Bytes.toLong(result.getResult().getValue(fam1, qual1)));</span> | 
|  | <span class="source-line-no">3031</span><span id="line-3031">    assertNull(result.getResult().getValue(fam1, qual2));</span> | 
|  | <span class="source-line-no">3032</span><span id="line-3032"></span> | 
|  | <span class="source-line-no">3033</span><span id="line-3033">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">3034</span><span id="line-3034">    assertEquals(3L, Bytes.toLong(r.getValue(fam1, qual1)));</span> | 
|  | <span class="source-line-no">3035</span><span id="line-3035">    assertEquals("aaa", Bytes.toString(r.getValue(fam1, qual2)));</span> | 
|  | <span class="source-line-no">3036</span><span id="line-3036">  }</span> | 
|  | <span class="source-line-no">3037</span><span id="line-3037"></span> | 
|  | <span class="source-line-no">3038</span><span id="line-3038">  @Test</span> | 
|  | <span class="source-line-no">3039</span><span id="line-3039">  public void testCheckAndRowMutations() throws Throwable {</span> | 
|  | <span class="source-line-no">3040</span><span id="line-3040">    final byte[] row = Bytes.toBytes("row");</span> | 
|  | <span class="source-line-no">3041</span><span id="line-3041">    final byte[] q1 = Bytes.toBytes("q1");</span> | 
|  | <span class="source-line-no">3042</span><span id="line-3042">    final byte[] q2 = Bytes.toBytes("q2");</span> | 
|  | <span class="source-line-no">3043</span><span id="line-3043">    final byte[] q3 = Bytes.toBytes("q3");</span> | 
|  | <span class="source-line-no">3044</span><span id="line-3044">    final byte[] q4 = Bytes.toBytes("q4");</span> | 
|  | <span class="source-line-no">3045</span><span id="line-3045">    final String v1 = "v1";</span> | 
|  | <span class="source-line-no">3046</span><span id="line-3046"></span> | 
|  | <span class="source-line-no">3047</span><span id="line-3047">    region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">3048</span><span id="line-3048"></span> | 
|  | <span class="source-line-no">3049</span><span id="line-3049">    // Initial values</span> | 
|  | <span class="source-line-no">3050</span><span id="line-3050">    region</span> | 
|  | <span class="source-line-no">3051</span><span id="line-3051">      .batchMutate(new Mutation[] { new Put(row).addColumn(fam1, q2, Bytes.toBytes("toBeDeleted")),</span> | 
|  | <span class="source-line-no">3052</span><span id="line-3052">        new Put(row).addColumn(fam1, q3, Bytes.toBytes(5L)),</span> | 
|  | <span class="source-line-no">3053</span><span id="line-3053">        new Put(row).addColumn(fam1, q4, Bytes.toBytes("a")), });</span> | 
|  | <span class="source-line-no">3054</span><span id="line-3054"></span> | 
|  | <span class="source-line-no">3055</span><span id="line-3055">    // Do CheckAndRowMutations</span> | 
|  | <span class="source-line-no">3056</span><span id="line-3056">    CheckAndMutate checkAndMutate = CheckAndMutate.newBuilder(row).ifNotExists(fam1, q1).build(</span> | 
|  | <span class="source-line-no">3057</span><span id="line-3057">      new RowMutations(row).add(Arrays.asList(new Put(row).addColumn(fam1, q1, Bytes.toBytes(v1)),</span> | 
|  | <span class="source-line-no">3058</span><span id="line-3058">        new Delete(row).addColumns(fam1, q2), new Increment(row).addColumn(fam1, q3, 1),</span> | 
|  | <span class="source-line-no">3059</span><span id="line-3059">        new Append(row).addColumn(fam1, q4, Bytes.toBytes("b")))));</span> | 
|  | <span class="source-line-no">3060</span><span id="line-3060"></span> | 
|  | <span class="source-line-no">3061</span><span id="line-3061">    CheckAndMutateResult result = region.checkAndMutate(checkAndMutate);</span> | 
|  | <span class="source-line-no">3062</span><span id="line-3062">    assertTrue(result.isSuccess());</span> | 
|  | <span class="source-line-no">3063</span><span id="line-3063">    assertEquals(6L, Bytes.toLong(result.getResult().getValue(fam1, q3)));</span> | 
|  | <span class="source-line-no">3064</span><span id="line-3064">    assertEquals("ab", Bytes.toString(result.getResult().getValue(fam1, q4)));</span> | 
|  | <span class="source-line-no">3065</span><span id="line-3065"></span> | 
|  | <span class="source-line-no">3066</span><span id="line-3066">    // Verify the value</span> | 
|  | <span class="source-line-no">3067</span><span id="line-3067">    Result r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">3068</span><span id="line-3068">    assertEquals(v1, Bytes.toString(r.getValue(fam1, q1)));</span> | 
|  | <span class="source-line-no">3069</span><span id="line-3069">    assertNull(r.getValue(fam1, q2));</span> | 
|  | <span class="source-line-no">3070</span><span id="line-3070">    assertEquals(6L, Bytes.toLong(r.getValue(fam1, q3)));</span> | 
|  | <span class="source-line-no">3071</span><span id="line-3071">    assertEquals("ab", Bytes.toString(r.getValue(fam1, q4)));</span> | 
|  | <span class="source-line-no">3072</span><span id="line-3072"></span> | 
|  | <span class="source-line-no">3073</span><span id="line-3073">    // Do CheckAndRowMutations again</span> | 
|  | <span class="source-line-no">3074</span><span id="line-3074">    checkAndMutate = CheckAndMutate.newBuilder(row).ifNotExists(fam1, q1)</span> | 
|  | <span class="source-line-no">3075</span><span id="line-3075">      .build(new RowMutations(row).add(Arrays.asList(new Delete(row).addColumns(fam1, q1),</span> | 
|  | <span class="source-line-no">3076</span><span id="line-3076">        new Put(row).addColumn(fam1, q2, Bytes.toBytes(v1)),</span> | 
|  | <span class="source-line-no">3077</span><span id="line-3077">        new Increment(row).addColumn(fam1, q3, 1),</span> | 
|  | <span class="source-line-no">3078</span><span id="line-3078">        new Append(row).addColumn(fam1, q4, Bytes.toBytes("b")))));</span> | 
|  | <span class="source-line-no">3079</span><span id="line-3079"></span> | 
|  | <span class="source-line-no">3080</span><span id="line-3080">    result = region.checkAndMutate(checkAndMutate);</span> | 
|  | <span class="source-line-no">3081</span><span id="line-3081">    assertFalse(result.isSuccess());</span> | 
|  | <span class="source-line-no">3082</span><span id="line-3082">    assertNull(result.getResult());</span> | 
|  | <span class="source-line-no">3083</span><span id="line-3083"></span> | 
|  | <span class="source-line-no">3084</span><span id="line-3084">    // Verify the value</span> | 
|  | <span class="source-line-no">3085</span><span id="line-3085">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">3086</span><span id="line-3086">    assertEquals(v1, Bytes.toString(r.getValue(fam1, q1)));</span> | 
|  | <span class="source-line-no">3087</span><span id="line-3087">    assertNull(r.getValue(fam1, q2));</span> | 
|  | <span class="source-line-no">3088</span><span id="line-3088">    assertEquals(6L, Bytes.toLong(r.getValue(fam1, q3)));</span> | 
|  | <span class="source-line-no">3089</span><span id="line-3089">    assertEquals("ab", Bytes.toString(r.getValue(fam1, q4)));</span> | 
|  | <span class="source-line-no">3090</span><span id="line-3090">  }</span> | 
|  | <span class="source-line-no">3091</span><span id="line-3091"></span> | 
|  | <span class="source-line-no">3092</span><span id="line-3092">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">3093</span><span id="line-3093">  // Delete tests</span> | 
|  | <span class="source-line-no">3094</span><span id="line-3094">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">3095</span><span id="line-3095">  @Test</span> | 
|  | <span class="source-line-no">3096</span><span id="line-3096">  public void testDelete_multiDeleteColumn() throws IOException {</span> | 
|  | <span class="source-line-no">3097</span><span id="line-3097">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3098</span><span id="line-3098">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3099</span><span id="line-3099">    byte[] qual = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">3100</span><span id="line-3100">    byte[] value = Bytes.toBytes("value");</span> | 
|  | <span class="source-line-no">3101</span><span id="line-3101"></span> | 
|  | <span class="source-line-no">3102</span><span id="line-3102">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">3103</span><span id="line-3103">    put.addColumn(fam1, qual, 1, value);</span> | 
|  | <span class="source-line-no">3104</span><span id="line-3104">    put.addColumn(fam1, qual, 2, value);</span> | 
|  | <span class="source-line-no">3105</span><span id="line-3105"></span> | 
|  | <span class="source-line-no">3106</span><span id="line-3106">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">3107</span><span id="line-3107">    region.put(put);</span> | 
|  | <span class="source-line-no">3108</span><span id="line-3108"></span> | 
|  | <span class="source-line-no">3109</span><span id="line-3109">    // We do support deleting more than 1 'latest' version</span> | 
|  | <span class="source-line-no">3110</span><span id="line-3110">    Delete delete = new Delete(row1);</span> | 
|  | <span class="source-line-no">3111</span><span id="line-3111">    delete.addColumn(fam1, qual);</span> | 
|  | <span class="source-line-no">3112</span><span id="line-3112">    delete.addColumn(fam1, qual);</span> | 
|  | <span class="source-line-no">3113</span><span id="line-3113">    region.delete(delete);</span> | 
|  | <span class="source-line-no">3114</span><span id="line-3114"></span> | 
|  | <span class="source-line-no">3115</span><span id="line-3115">    Get get = new Get(row1);</span> | 
|  | <span class="source-line-no">3116</span><span id="line-3116">    get.addFamily(fam1);</span> | 
|  | <span class="source-line-no">3117</span><span id="line-3117">    Result r = region.get(get);</span> | 
|  | <span class="source-line-no">3118</span><span id="line-3118">    assertEquals(0, r.size());</span> | 
|  | <span class="source-line-no">3119</span><span id="line-3119">  }</span> | 
|  | <span class="source-line-no">3120</span><span id="line-3120"></span> | 
|  | <span class="source-line-no">3121</span><span id="line-3121">  @Test</span> | 
|  | <span class="source-line-no">3122</span><span id="line-3122">  public void testDelete_CheckFamily() throws IOException {</span> | 
|  | <span class="source-line-no">3123</span><span id="line-3123">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3124</span><span id="line-3124">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3125</span><span id="line-3125">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">3126</span><span id="line-3126">    byte[] fam3 = Bytes.toBytes("fam3");</span> | 
|  | <span class="source-line-no">3127</span><span id="line-3127">    byte[] fam4 = Bytes.toBytes("fam4");</span> | 
|  | <span class="source-line-no">3128</span><span id="line-3128"></span> | 
|  | <span class="source-line-no">3129</span><span id="line-3129">    // Setting up region</span> | 
|  | <span class="source-line-no">3130</span><span id="line-3130">    this.region = initHRegion(tableName, method, CONF, fam1, fam2, fam3);</span> | 
|  | <span class="source-line-no">3131</span><span id="line-3131">    List<Cell> kvs = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3132</span><span id="line-3132">    kvs.add(new KeyValue(row1, fam4, null, null));</span> | 
|  | <span class="source-line-no">3133</span><span id="line-3133"></span> | 
|  | <span class="source-line-no">3134</span><span id="line-3134">    byte[] forUnitTestsOnly = Bytes.toBytes("ForUnitTestsOnly");</span> | 
|  | <span class="source-line-no">3135</span><span id="line-3135"></span> | 
|  | <span class="source-line-no">3136</span><span id="line-3136">    // testing existing family</span> | 
|  | <span class="source-line-no">3137</span><span id="line-3137">    NavigableMap<byte[], List<Cell>> deleteMap = new TreeMap<>(Bytes.BYTES_COMPARATOR);</span> | 
|  | <span class="source-line-no">3138</span><span id="line-3138">    deleteMap.put(fam2, kvs);</span> | 
|  | <span class="source-line-no">3139</span><span id="line-3139">    region.delete(new Delete(forUnitTestsOnly, HConstants.LATEST_TIMESTAMP, deleteMap));</span> | 
|  | <span class="source-line-no">3140</span><span id="line-3140"></span> | 
|  | <span class="source-line-no">3141</span><span id="line-3141">    // testing non existing family</span> | 
|  | <span class="source-line-no">3142</span><span id="line-3142">    NavigableMap<byte[], List<Cell>> deleteMap2 = new TreeMap<>(Bytes.BYTES_COMPARATOR);</span> | 
|  | <span class="source-line-no">3143</span><span id="line-3143">    deleteMap2.put(fam4, kvs);</span> | 
|  | <span class="source-line-no">3144</span><span id="line-3144">    assertThrows("Family " + Bytes.toString(fam4) + " does exist",</span> | 
|  | <span class="source-line-no">3145</span><span id="line-3145">      NoSuchColumnFamilyException.class,</span> | 
|  | <span class="source-line-no">3146</span><span id="line-3146">      () -> region.delete(new Delete(forUnitTestsOnly, HConstants.LATEST_TIMESTAMP, deleteMap2)));</span> | 
|  | <span class="source-line-no">3147</span><span id="line-3147">  }</span> | 
|  | <span class="source-line-no">3148</span><span id="line-3148"></span> | 
|  | <span class="source-line-no">3149</span><span id="line-3149">  @Test</span> | 
|  | <span class="source-line-no">3150</span><span id="line-3150">  public void testDelete_mixed() throws IOException, InterruptedException {</span> | 
|  | <span class="source-line-no">3151</span><span id="line-3151">    byte[] fam = Bytes.toBytes("info");</span> | 
|  | <span class="source-line-no">3152</span><span id="line-3152">    byte[][] families = { fam };</span> | 
|  | <span class="source-line-no">3153</span><span id="line-3153">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3154</span><span id="line-3154">    EnvironmentEdgeManagerTestHelper.injectEdge(new IncrementingEnvironmentEdge());</span> | 
|  | <span class="source-line-no">3155</span><span id="line-3155"></span> | 
|  | <span class="source-line-no">3156</span><span id="line-3156">    byte[] row = Bytes.toBytes("table_name");</span> | 
|  | <span class="source-line-no">3157</span><span id="line-3157">    // column names</span> | 
|  | <span class="source-line-no">3158</span><span id="line-3158">    byte[] serverinfo = Bytes.toBytes("serverinfo");</span> | 
|  | <span class="source-line-no">3159</span><span id="line-3159">    byte[] splitA = Bytes.toBytes("splitA");</span> | 
|  | <span class="source-line-no">3160</span><span id="line-3160">    byte[] splitB = Bytes.toBytes("splitB");</span> | 
|  | <span class="source-line-no">3161</span><span id="line-3161"></span> | 
|  | <span class="source-line-no">3162</span><span id="line-3162">    // add some data:</span> | 
|  | <span class="source-line-no">3163</span><span id="line-3163">    Put put = new Put(row);</span> | 
|  | <span class="source-line-no">3164</span><span id="line-3164">    put.addColumn(fam, splitA, Bytes.toBytes("reference_A"));</span> | 
|  | <span class="source-line-no">3165</span><span id="line-3165">    region.put(put);</span> | 
|  | <span class="source-line-no">3166</span><span id="line-3166"></span> | 
|  | <span class="source-line-no">3167</span><span id="line-3167">    put = new Put(row);</span> | 
|  | <span class="source-line-no">3168</span><span id="line-3168">    put.addColumn(fam, splitB, Bytes.toBytes("reference_B"));</span> | 
|  | <span class="source-line-no">3169</span><span id="line-3169">    region.put(put);</span> | 
|  | <span class="source-line-no">3170</span><span id="line-3170"></span> | 
|  | <span class="source-line-no">3171</span><span id="line-3171">    put = new Put(row);</span> | 
|  | <span class="source-line-no">3172</span><span id="line-3172">    put.addColumn(fam, serverinfo, Bytes.toBytes("ip_address"));</span> | 
|  | <span class="source-line-no">3173</span><span id="line-3173">    region.put(put);</span> | 
|  | <span class="source-line-no">3174</span><span id="line-3174"></span> | 
|  | <span class="source-line-no">3175</span><span id="line-3175">    // ok now delete a split:</span> | 
|  | <span class="source-line-no">3176</span><span id="line-3176">    Delete delete = new Delete(row);</span> | 
|  | <span class="source-line-no">3177</span><span id="line-3177">    delete.addColumns(fam, splitA);</span> | 
|  | <span class="source-line-no">3178</span><span id="line-3178">    region.delete(delete);</span> | 
|  | <span class="source-line-no">3179</span><span id="line-3179"></span> | 
|  | <span class="source-line-no">3180</span><span id="line-3180">    // assert some things:</span> | 
|  | <span class="source-line-no">3181</span><span id="line-3181">    Get get = new Get(row).addColumn(fam, serverinfo);</span> | 
|  | <span class="source-line-no">3182</span><span id="line-3182">    Result result = region.get(get);</span> | 
|  | <span class="source-line-no">3183</span><span id="line-3183">    assertEquals(1, result.size());</span> | 
|  | <span class="source-line-no">3184</span><span id="line-3184"></span> | 
|  | <span class="source-line-no">3185</span><span id="line-3185">    get = new Get(row).addColumn(fam, splitA);</span> | 
|  | <span class="source-line-no">3186</span><span id="line-3186">    result = region.get(get);</span> | 
|  | <span class="source-line-no">3187</span><span id="line-3187">    assertEquals(0, result.size());</span> | 
|  | <span class="source-line-no">3188</span><span id="line-3188"></span> | 
|  | <span class="source-line-no">3189</span><span id="line-3189">    get = new Get(row).addColumn(fam, splitB);</span> | 
|  | <span class="source-line-no">3190</span><span id="line-3190">    result = region.get(get);</span> | 
|  | <span class="source-line-no">3191</span><span id="line-3191">    assertEquals(1, result.size());</span> | 
|  | <span class="source-line-no">3192</span><span id="line-3192"></span> | 
|  | <span class="source-line-no">3193</span><span id="line-3193">    // Assert that after a delete, I can put.</span> | 
|  | <span class="source-line-no">3194</span><span id="line-3194">    put = new Put(row);</span> | 
|  | <span class="source-line-no">3195</span><span id="line-3195">    put.addColumn(fam, splitA, Bytes.toBytes("reference_A"));</span> | 
|  | <span class="source-line-no">3196</span><span id="line-3196">    region.put(put);</span> | 
|  | <span class="source-line-no">3197</span><span id="line-3197">    get = new Get(row);</span> | 
|  | <span class="source-line-no">3198</span><span id="line-3198">    result = region.get(get);</span> | 
|  | <span class="source-line-no">3199</span><span id="line-3199">    assertEquals(3, result.size());</span> | 
|  | <span class="source-line-no">3200</span><span id="line-3200"></span> | 
|  | <span class="source-line-no">3201</span><span id="line-3201">    // Now delete all... then test I can add stuff back</span> | 
|  | <span class="source-line-no">3202</span><span id="line-3202">    delete = new Delete(row);</span> | 
|  | <span class="source-line-no">3203</span><span id="line-3203">    region.delete(delete);</span> | 
|  | <span class="source-line-no">3204</span><span id="line-3204">    assertEquals(0, region.get(get).size());</span> | 
|  | <span class="source-line-no">3205</span><span id="line-3205"></span> | 
|  | <span class="source-line-no">3206</span><span id="line-3206">    region.put(new Put(row).addColumn(fam, splitA, Bytes.toBytes("reference_A")));</span> | 
|  | <span class="source-line-no">3207</span><span id="line-3207">    result = region.get(get);</span> | 
|  | <span class="source-line-no">3208</span><span id="line-3208">    assertEquals(1, result.size());</span> | 
|  | <span class="source-line-no">3209</span><span id="line-3209">  }</span> | 
|  | <span class="source-line-no">3210</span><span id="line-3210"></span> | 
|  | <span class="source-line-no">3211</span><span id="line-3211">  @Test</span> | 
|  | <span class="source-line-no">3212</span><span id="line-3212">  public void testDeleteRowWithFutureTs() throws IOException {</span> | 
|  | <span class="source-line-no">3213</span><span id="line-3213">    byte[] fam = Bytes.toBytes("info");</span> | 
|  | <span class="source-line-no">3214</span><span id="line-3214">    byte[][] families = { fam };</span> | 
|  | <span class="source-line-no">3215</span><span id="line-3215">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3216</span><span id="line-3216">    byte[] row = Bytes.toBytes("table_name");</span> | 
|  | <span class="source-line-no">3217</span><span id="line-3217">    // column names</span> | 
|  | <span class="source-line-no">3218</span><span id="line-3218">    byte[] serverinfo = Bytes.toBytes("serverinfo");</span> | 
|  | <span class="source-line-no">3219</span><span id="line-3219"></span> | 
|  | <span class="source-line-no">3220</span><span id="line-3220">    // add data in the far future</span> | 
|  | <span class="source-line-no">3221</span><span id="line-3221">    Put put = new Put(row);</span> | 
|  | <span class="source-line-no">3222</span><span id="line-3222">    put.addColumn(fam, serverinfo, HConstants.LATEST_TIMESTAMP - 5, Bytes.toBytes("value"));</span> | 
|  | <span class="source-line-no">3223</span><span id="line-3223">    region.put(put);</span> | 
|  | <span class="source-line-no">3224</span><span id="line-3224"></span> | 
|  | <span class="source-line-no">3225</span><span id="line-3225">    // now delete something in the present</span> | 
|  | <span class="source-line-no">3226</span><span id="line-3226">    Delete delete = new Delete(row);</span> | 
|  | <span class="source-line-no">3227</span><span id="line-3227">    region.delete(delete);</span> | 
|  | <span class="source-line-no">3228</span><span id="line-3228"></span> | 
|  | <span class="source-line-no">3229</span><span id="line-3229">    // make sure we still see our data</span> | 
|  | <span class="source-line-no">3230</span><span id="line-3230">    Get get = new Get(row).addColumn(fam, serverinfo);</span> | 
|  | <span class="source-line-no">3231</span><span id="line-3231">    Result result = region.get(get);</span> | 
|  | <span class="source-line-no">3232</span><span id="line-3232">    assertEquals(1, result.size());</span> | 
|  | <span class="source-line-no">3233</span><span id="line-3233"></span> | 
|  | <span class="source-line-no">3234</span><span id="line-3234">    // delete the future row</span> | 
|  | <span class="source-line-no">3235</span><span id="line-3235">    delete = new Delete(row, HConstants.LATEST_TIMESTAMP - 3);</span> | 
|  | <span class="source-line-no">3236</span><span id="line-3236">    region.delete(delete);</span> | 
|  | <span class="source-line-no">3237</span><span id="line-3237"></span> | 
|  | <span class="source-line-no">3238</span><span id="line-3238">    // make sure it is gone</span> | 
|  | <span class="source-line-no">3239</span><span id="line-3239">    get = new Get(row).addColumn(fam, serverinfo);</span> | 
|  | <span class="source-line-no">3240</span><span id="line-3240">    result = region.get(get);</span> | 
|  | <span class="source-line-no">3241</span><span id="line-3241">    assertEquals(0, result.size());</span> | 
|  | <span class="source-line-no">3242</span><span id="line-3242">  }</span> | 
|  | <span class="source-line-no">3243</span><span id="line-3243"></span> | 
|  | <span class="source-line-no">3244</span><span id="line-3244">  /**</span> | 
|  | <span class="source-line-no">3245</span><span id="line-3245">   * Tests that the special LATEST_TIMESTAMP option for puts gets replaced by the actual timestamp</span> | 
|  | <span class="source-line-no">3246</span><span id="line-3246">   */</span> | 
|  | <span class="source-line-no">3247</span><span id="line-3247">  @Test</span> | 
|  | <span class="source-line-no">3248</span><span id="line-3248">  public void testPutWithLatestTS() throws IOException {</span> | 
|  | <span class="source-line-no">3249</span><span id="line-3249">    byte[] fam = Bytes.toBytes("info");</span> | 
|  | <span class="source-line-no">3250</span><span id="line-3250">    byte[][] families = { fam };</span> | 
|  | <span class="source-line-no">3251</span><span id="line-3251">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3252</span><span id="line-3252">    byte[] row = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3253</span><span id="line-3253">    // column names</span> | 
|  | <span class="source-line-no">3254</span><span id="line-3254">    byte[] qual = Bytes.toBytes("qual");</span> | 
|  | <span class="source-line-no">3255</span><span id="line-3255"></span> | 
|  | <span class="source-line-no">3256</span><span id="line-3256">    // add data with LATEST_TIMESTAMP, put without WAL</span> | 
|  | <span class="source-line-no">3257</span><span id="line-3257">    Put put = new Put(row);</span> | 
|  | <span class="source-line-no">3258</span><span id="line-3258">    put.addColumn(fam, qual, HConstants.LATEST_TIMESTAMP, Bytes.toBytes("value"));</span> | 
|  | <span class="source-line-no">3259</span><span id="line-3259">    region.put(put);</span> | 
|  | <span class="source-line-no">3260</span><span id="line-3260"></span> | 
|  | <span class="source-line-no">3261</span><span id="line-3261">    // Make sure it shows up with an actual timestamp</span> | 
|  | <span class="source-line-no">3262</span><span id="line-3262">    Get get = new Get(row).addColumn(fam, qual);</span> | 
|  | <span class="source-line-no">3263</span><span id="line-3263">    Result result = region.get(get);</span> | 
|  | <span class="source-line-no">3264</span><span id="line-3264">    assertEquals(1, result.size());</span> | 
|  | <span class="source-line-no">3265</span><span id="line-3265">    Cell kv = result.rawCells()[0];</span> | 
|  | <span class="source-line-no">3266</span><span id="line-3266">    LOG.info("Got: " + kv);</span> | 
|  | <span class="source-line-no">3267</span><span id="line-3267">    assertTrue("LATEST_TIMESTAMP was not replaced with real timestamp",</span> | 
|  | <span class="source-line-no">3268</span><span id="line-3268">      kv.getTimestamp() != HConstants.LATEST_TIMESTAMP);</span> | 
|  | <span class="source-line-no">3269</span><span id="line-3269"></span> | 
|  | <span class="source-line-no">3270</span><span id="line-3270">    // Check same with WAL enabled (historically these took different</span> | 
|  | <span class="source-line-no">3271</span><span id="line-3271">    // code paths, so check both)</span> | 
|  | <span class="source-line-no">3272</span><span id="line-3272">    row = Bytes.toBytes("row2");</span> | 
|  | <span class="source-line-no">3273</span><span id="line-3273">    put = new Put(row);</span> | 
|  | <span class="source-line-no">3274</span><span id="line-3274">    put.addColumn(fam, qual, HConstants.LATEST_TIMESTAMP, Bytes.toBytes("value"));</span> | 
|  | <span class="source-line-no">3275</span><span id="line-3275">    region.put(put);</span> | 
|  | <span class="source-line-no">3276</span><span id="line-3276"></span> | 
|  | <span class="source-line-no">3277</span><span id="line-3277">    // Make sure it shows up with an actual timestamp</span> | 
|  | <span class="source-line-no">3278</span><span id="line-3278">    get = new Get(row).addColumn(fam, qual);</span> | 
|  | <span class="source-line-no">3279</span><span id="line-3279">    result = region.get(get);</span> | 
|  | <span class="source-line-no">3280</span><span id="line-3280">    assertEquals(1, result.size());</span> | 
|  | <span class="source-line-no">3281</span><span id="line-3281">    kv = result.rawCells()[0];</span> | 
|  | <span class="source-line-no">3282</span><span id="line-3282">    LOG.info("Got: " + kv);</span> | 
|  | <span class="source-line-no">3283</span><span id="line-3283">    assertTrue("LATEST_TIMESTAMP was not replaced with real timestamp",</span> | 
|  | <span class="source-line-no">3284</span><span id="line-3284">      kv.getTimestamp() != HConstants.LATEST_TIMESTAMP);</span> | 
|  | <span class="source-line-no">3285</span><span id="line-3285">  }</span> | 
|  | <span class="source-line-no">3286</span><span id="line-3286"></span> | 
|  | <span class="source-line-no">3287</span><span id="line-3287">  /**</span> | 
|  | <span class="source-line-no">3288</span><span id="line-3288">   * Tests that there is server-side filtering for invalid timestamp upper bound. Note that the</span> | 
|  | <span class="source-line-no">3289</span><span id="line-3289">   * timestamp lower bound is automatically handled for us by the TTL field.</span> | 
|  | <span class="source-line-no">3290</span><span id="line-3290">   */</span> | 
|  | <span class="source-line-no">3291</span><span id="line-3291">  @Test</span> | 
|  | <span class="source-line-no">3292</span><span id="line-3292">  public void testPutWithTsSlop() throws IOException {</span> | 
|  | <span class="source-line-no">3293</span><span id="line-3293">    byte[] fam = Bytes.toBytes("info");</span> | 
|  | <span class="source-line-no">3294</span><span id="line-3294">    byte[][] families = { fam };</span> | 
|  | <span class="source-line-no">3295</span><span id="line-3295"></span> | 
|  | <span class="source-line-no">3296</span><span id="line-3296">    // add data with a timestamp that is too recent for range. Ensure assert</span> | 
|  | <span class="source-line-no">3297</span><span id="line-3297">    CONF.setInt("hbase.hregion.keyvalue.timestamp.slop.millisecs", 1000);</span> | 
|  | <span class="source-line-no">3298</span><span id="line-3298">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3299</span><span id="line-3299">    boolean caughtExcep = false;</span> | 
|  | <span class="source-line-no">3300</span><span id="line-3300">    try {</span> | 
|  | <span class="source-line-no">3301</span><span id="line-3301">      // no TS specified == use latest. should not error</span> | 
|  | <span class="source-line-no">3302</span><span id="line-3302">      region.put(new Put(row).addColumn(fam, Bytes.toBytes("qual"), Bytes.toBytes("value")));</span> | 
|  | <span class="source-line-no">3303</span><span id="line-3303">      // TS out of range. should error</span> | 
|  | <span class="source-line-no">3304</span><span id="line-3304">      region.put(new Put(row).addColumn(fam, Bytes.toBytes("qual"),</span> | 
|  | <span class="source-line-no">3305</span><span id="line-3305">        EnvironmentEdgeManager.currentTime() + 2000, Bytes.toBytes("value")));</span> | 
|  | <span class="source-line-no">3306</span><span id="line-3306">      fail("Expected IOE for TS out of configured timerange");</span> | 
|  | <span class="source-line-no">3307</span><span id="line-3307">    } catch (FailedSanityCheckException ioe) {</span> | 
|  | <span class="source-line-no">3308</span><span id="line-3308">      LOG.debug("Received expected exception", ioe);</span> | 
|  | <span class="source-line-no">3309</span><span id="line-3309">      caughtExcep = true;</span> | 
|  | <span class="source-line-no">3310</span><span id="line-3310">    }</span> | 
|  | <span class="source-line-no">3311</span><span id="line-3311">    assertTrue("Should catch FailedSanityCheckException", caughtExcep);</span> | 
|  | <span class="source-line-no">3312</span><span id="line-3312">  }</span> | 
|  | <span class="source-line-no">3313</span><span id="line-3313"></span> | 
|  | <span class="source-line-no">3314</span><span id="line-3314">  @Test</span> | 
|  | <span class="source-line-no">3315</span><span id="line-3315">  public void testScanner_DeleteOneFamilyNotAnother() throws IOException {</span> | 
|  | <span class="source-line-no">3316</span><span id="line-3316">    byte[] fam1 = Bytes.toBytes("columnA");</span> | 
|  | <span class="source-line-no">3317</span><span id="line-3317">    byte[] fam2 = Bytes.toBytes("columnB");</span> | 
|  | <span class="source-line-no">3318</span><span id="line-3318">    this.region = initHRegion(tableName, method, CONF, fam1, fam2);</span> | 
|  | <span class="source-line-no">3319</span><span id="line-3319">    byte[] rowA = Bytes.toBytes("rowA");</span> | 
|  | <span class="source-line-no">3320</span><span id="line-3320">    byte[] rowB = Bytes.toBytes("rowB");</span> | 
|  | <span class="source-line-no">3321</span><span id="line-3321"></span> | 
|  | <span class="source-line-no">3322</span><span id="line-3322">    byte[] value = Bytes.toBytes("value");</span> | 
|  | <span class="source-line-no">3323</span><span id="line-3323"></span> | 
|  | <span class="source-line-no">3324</span><span id="line-3324">    Delete delete = new Delete(rowA);</span> | 
|  | <span class="source-line-no">3325</span><span id="line-3325">    delete.addFamily(fam1);</span> | 
|  | <span class="source-line-no">3326</span><span id="line-3326"></span> | 
|  | <span class="source-line-no">3327</span><span id="line-3327">    region.delete(delete);</span> | 
|  | <span class="source-line-no">3328</span><span id="line-3328"></span> | 
|  | <span class="source-line-no">3329</span><span id="line-3329">    // now create data.</span> | 
|  | <span class="source-line-no">3330</span><span id="line-3330">    Put put = new Put(rowA);</span> | 
|  | <span class="source-line-no">3331</span><span id="line-3331">    put.addColumn(fam2, null, value);</span> | 
|  | <span class="source-line-no">3332</span><span id="line-3332">    region.put(put);</span> | 
|  | <span class="source-line-no">3333</span><span id="line-3333"></span> | 
|  | <span class="source-line-no">3334</span><span id="line-3334">    put = new Put(rowB);</span> | 
|  | <span class="source-line-no">3335</span><span id="line-3335">    put.addColumn(fam1, null, value);</span> | 
|  | <span class="source-line-no">3336</span><span id="line-3336">    put.addColumn(fam2, null, value);</span> | 
|  | <span class="source-line-no">3337</span><span id="line-3337">    region.put(put);</span> | 
|  | <span class="source-line-no">3338</span><span id="line-3338"></span> | 
|  | <span class="source-line-no">3339</span><span id="line-3339">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">3340</span><span id="line-3340">    scan.addFamily(fam1).addFamily(fam2);</span> | 
|  | <span class="source-line-no">3341</span><span id="line-3341">    try (InternalScanner s = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">3342</span><span id="line-3342">      List<Cell> results = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3343</span><span id="line-3343">      s.next(results);</span> | 
|  | <span class="source-line-no">3344</span><span id="line-3344">      assertTrue(CellUtil.matchingRows(results.get(0), rowA));</span> | 
|  | <span class="source-line-no">3345</span><span id="line-3345"></span> | 
|  | <span class="source-line-no">3346</span><span id="line-3346">      results.clear();</span> | 
|  | <span class="source-line-no">3347</span><span id="line-3347">      s.next(results);</span> | 
|  | <span class="source-line-no">3348</span><span id="line-3348">      assertTrue(CellUtil.matchingRows(results.get(0), rowB));</span> | 
|  | <span class="source-line-no">3349</span><span id="line-3349">    }</span> | 
|  | <span class="source-line-no">3350</span><span id="line-3350">  }</span> | 
|  | <span class="source-line-no">3351</span><span id="line-3351"></span> | 
|  | <span class="source-line-no">3352</span><span id="line-3352">  @Test</span> | 
|  | <span class="source-line-no">3353</span><span id="line-3353">  public void testDataInMemoryWithoutWAL() throws IOException {</span> | 
|  | <span class="source-line-no">3354</span><span id="line-3354">    FileSystem fs = FileSystem.get(CONF);</span> | 
|  | <span class="source-line-no">3355</span><span id="line-3355">    Path rootDir = new Path(dir + "testDataInMemoryWithoutWAL");</span> | 
|  | <span class="source-line-no">3356</span><span id="line-3356">    FSHLog hLog = new FSHLog(fs, rootDir, "testDataInMemoryWithoutWAL", CONF);</span> | 
|  | <span class="source-line-no">3357</span><span id="line-3357">    hLog.init();</span> | 
|  | <span class="source-line-no">3358</span><span id="line-3358">    // This chunk creation is done throughout the code base. Do we want to move it into core?</span> | 
|  | <span class="source-line-no">3359</span><span id="line-3359">    // It is missing from this test. W/o it we NPE.</span> | 
|  | <span class="source-line-no">3360</span><span id="line-3360">    region = initHRegion(tableName, null, null, CONF, false, Durability.SYNC_WAL, hLog,</span> | 
|  | <span class="source-line-no">3361</span><span id="line-3361">      COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">3362</span><span id="line-3362"></span> | 
|  | <span class="source-line-no">3363</span><span id="line-3363">    Cell originalCell = ExtendedCellBuilderFactory.create(CellBuilderType.DEEP_COPY).setRow(row)</span> | 
|  | <span class="source-line-no">3364</span><span id="line-3364">      .setFamily(COLUMN_FAMILY_BYTES).setQualifier(qual1)</span> | 
|  | <span class="source-line-no">3365</span><span id="line-3365">      .setTimestamp(EnvironmentEdgeManager.currentTime()).setType(KeyValue.Type.Put.getCode())</span> | 
|  | <span class="source-line-no">3366</span><span id="line-3366">      .setValue(value1).build();</span> | 
|  | <span class="source-line-no">3367</span><span id="line-3367">    final long originalSize = originalCell.getSerializedSize();</span> | 
|  | <span class="source-line-no">3368</span><span id="line-3368"></span> | 
|  | <span class="source-line-no">3369</span><span id="line-3369">    Cell addCell = ExtendedCellBuilderFactory.create(CellBuilderType.DEEP_COPY).setRow(row)</span> | 
|  | <span class="source-line-no">3370</span><span id="line-3370">      .setFamily(COLUMN_FAMILY_BYTES).setQualifier(qual1)</span> | 
|  | <span class="source-line-no">3371</span><span id="line-3371">      .setTimestamp(EnvironmentEdgeManager.currentTime()).setType(KeyValue.Type.Put.getCode())</span> | 
|  | <span class="source-line-no">3372</span><span id="line-3372">      .setValue(Bytes.toBytes("xxxxxxxxxx")).build();</span> | 
|  | <span class="source-line-no">3373</span><span id="line-3373">    final long addSize = addCell.getSerializedSize();</span> | 
|  | <span class="source-line-no">3374</span><span id="line-3374"></span> | 
|  | <span class="source-line-no">3375</span><span id="line-3375">    LOG.info("originalSize:" + originalSize + ", addSize:" + addSize);</span> | 
|  | <span class="source-line-no">3376</span><span id="line-3376">    // start test. We expect that the addPut's durability will be replaced</span> | 
|  | <span class="source-line-no">3377</span><span id="line-3377">    // by originalPut's durability.</span> | 
|  | <span class="source-line-no">3378</span><span id="line-3378"></span> | 
|  | <span class="source-line-no">3379</span><span id="line-3379">    // case 1:</span> | 
|  | <span class="source-line-no">3380</span><span id="line-3380">    testDataInMemoryWithoutWAL(region,</span> | 
|  | <span class="source-line-no">3381</span><span id="line-3381">      new Put(row).add(originalCell).setDurability(Durability.SKIP_WAL),</span> | 
|  | <span class="source-line-no">3382</span><span id="line-3382">      new Put(row).add(addCell).setDurability(Durability.SKIP_WAL), originalSize + addSize);</span> | 
|  | <span class="source-line-no">3383</span><span id="line-3383"></span> | 
|  | <span class="source-line-no">3384</span><span id="line-3384">    // case 2:</span> | 
|  | <span class="source-line-no">3385</span><span id="line-3385">    testDataInMemoryWithoutWAL(region,</span> | 
|  | <span class="source-line-no">3386</span><span id="line-3386">      new Put(row).add(originalCell).setDurability(Durability.SKIP_WAL),</span> | 
|  | <span class="source-line-no">3387</span><span id="line-3387">      new Put(row).add(addCell).setDurability(Durability.SYNC_WAL), originalSize + addSize);</span> | 
|  | <span class="source-line-no">3388</span><span id="line-3388"></span> | 
|  | <span class="source-line-no">3389</span><span id="line-3389">    // case 3:</span> | 
|  | <span class="source-line-no">3390</span><span id="line-3390">    testDataInMemoryWithoutWAL(region,</span> | 
|  | <span class="source-line-no">3391</span><span id="line-3391">      new Put(row).add(originalCell).setDurability(Durability.SYNC_WAL),</span> | 
|  | <span class="source-line-no">3392</span><span id="line-3392">      new Put(row).add(addCell).setDurability(Durability.SKIP_WAL), 0);</span> | 
|  | <span class="source-line-no">3393</span><span id="line-3393"></span> | 
|  | <span class="source-line-no">3394</span><span id="line-3394">    // case 4:</span> | 
|  | <span class="source-line-no">3395</span><span id="line-3395">    testDataInMemoryWithoutWAL(region,</span> | 
|  | <span class="source-line-no">3396</span><span id="line-3396">      new Put(row).add(originalCell).setDurability(Durability.SYNC_WAL),</span> | 
|  | <span class="source-line-no">3397</span><span id="line-3397">      new Put(row).add(addCell).setDurability(Durability.SYNC_WAL), 0);</span> | 
|  | <span class="source-line-no">3398</span><span id="line-3398">  }</span> | 
|  | <span class="source-line-no">3399</span><span id="line-3399"></span> | 
|  | <span class="source-line-no">3400</span><span id="line-3400">  private static void testDataInMemoryWithoutWAL(HRegion region, Put originalPut, final Put addPut,</span> | 
|  | <span class="source-line-no">3401</span><span id="line-3401">    long delta) throws IOException {</span> | 
|  | <span class="source-line-no">3402</span><span id="line-3402">    final long initSize = region.getDataInMemoryWithoutWAL();</span> | 
|  | <span class="source-line-no">3403</span><span id="line-3403">    // save normalCPHost and replaced by mockedCPHost</span> | 
|  | <span class="source-line-no">3404</span><span id="line-3404">    RegionCoprocessorHost normalCPHost = region.getCoprocessorHost();</span> | 
|  | <span class="source-line-no">3405</span><span id="line-3405">    RegionCoprocessorHost mockedCPHost = mock(RegionCoprocessorHost.class);</span> | 
|  | <span class="source-line-no">3406</span><span id="line-3406">    // Because the preBatchMutate returns void, we can't do usual Mockito when...then form. Must</span> | 
|  | <span class="source-line-no">3407</span><span id="line-3407">    // do below format (from Mockito doc).</span> | 
|  | <span class="source-line-no">3408</span><span id="line-3408">    doAnswer(new Answer<Void>() {</span> | 
|  | <span class="source-line-no">3409</span><span id="line-3409">      @Override</span> | 
|  | <span class="source-line-no">3410</span><span id="line-3410">      public Void answer(InvocationOnMock invocation) throws Throwable {</span> | 
|  | <span class="source-line-no">3411</span><span id="line-3411">        MiniBatchOperationInProgress<Mutation> mb = invocation.getArgument(0);</span> | 
|  | <span class="source-line-no">3412</span><span id="line-3412">        mb.addOperationsFromCP(0, new Mutation[] { addPut });</span> | 
|  | <span class="source-line-no">3413</span><span id="line-3413">        return null;</span> | 
|  | <span class="source-line-no">3414</span><span id="line-3414">      }</span> | 
|  | <span class="source-line-no">3415</span><span id="line-3415">    }).when(mockedCPHost).preBatchMutate(isA(MiniBatchOperationInProgress.class));</span> | 
|  | <span class="source-line-no">3416</span><span id="line-3416">    ColumnFamilyDescriptorBuilder builder =</span> | 
|  | <span class="source-line-no">3417</span><span id="line-3417">      ColumnFamilyDescriptorBuilder.newBuilder(COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">3418</span><span id="line-3418">    ScanInfo info = new ScanInfo(CONF, builder.build(), Long.MAX_VALUE, Long.MAX_VALUE,</span> | 
|  | <span class="source-line-no">3419</span><span id="line-3419">      region.getCellComparator());</span> | 
|  | <span class="source-line-no">3420</span><span id="line-3420">    when(mockedCPHost.preFlushScannerOpen(any(HStore.class), any())).thenReturn(info);</span> | 
|  | <span class="source-line-no">3421</span><span id="line-3421"></span> | 
|  | <span class="source-line-no">3422</span><span id="line-3422">    when(mockedCPHost.preFlush(any(), any(StoreScanner.class), any()))</span> | 
|  | <span class="source-line-no">3423</span><span id="line-3423">      .thenAnswer(i -> i.getArgument(1));</span> | 
|  | <span class="source-line-no">3424</span><span id="line-3424">    region.setCoprocessorHost(mockedCPHost);</span> | 
|  | <span class="source-line-no">3425</span><span id="line-3425"></span> | 
|  | <span class="source-line-no">3426</span><span id="line-3426">    region.put(originalPut);</span> | 
|  | <span class="source-line-no">3427</span><span id="line-3427">    region.setCoprocessorHost(normalCPHost);</span> | 
|  | <span class="source-line-no">3428</span><span id="line-3428">    final long finalSize = region.getDataInMemoryWithoutWAL();</span> | 
|  | <span class="source-line-no">3429</span><span id="line-3429">    assertEquals("finalSize:" + finalSize + ", initSize:" + initSize + ", delta:" + delta,</span> | 
|  | <span class="source-line-no">3430</span><span id="line-3430">      finalSize, initSize + delta);</span> | 
|  | <span class="source-line-no">3431</span><span id="line-3431">  }</span> | 
|  | <span class="source-line-no">3432</span><span id="line-3432"></span> | 
|  | <span class="source-line-no">3433</span><span id="line-3433">  @Test</span> | 
|  | <span class="source-line-no">3434</span><span id="line-3434">  public void testDeleteColumns_PostInsert() throws IOException, InterruptedException {</span> | 
|  | <span class="source-line-no">3435</span><span id="line-3435">    Delete delete = new Delete(row);</span> | 
|  | <span class="source-line-no">3436</span><span id="line-3436">    delete.addColumns(fam1, qual1);</span> | 
|  | <span class="source-line-no">3437</span><span id="line-3437">    doTestDelete_AndPostInsert(delete);</span> | 
|  | <span class="source-line-no">3438</span><span id="line-3438">  }</span> | 
|  | <span class="source-line-no">3439</span><span id="line-3439"></span> | 
|  | <span class="source-line-no">3440</span><span id="line-3440">  @Test</span> | 
|  | <span class="source-line-no">3441</span><span id="line-3441">  public void testaddFamily_PostInsert() throws IOException, InterruptedException {</span> | 
|  | <span class="source-line-no">3442</span><span id="line-3442">    Delete delete = new Delete(row);</span> | 
|  | <span class="source-line-no">3443</span><span id="line-3443">    delete.addFamily(fam1);</span> | 
|  | <span class="source-line-no">3444</span><span id="line-3444">    doTestDelete_AndPostInsert(delete);</span> | 
|  | <span class="source-line-no">3445</span><span id="line-3445">  }</span> | 
|  | <span class="source-line-no">3446</span><span id="line-3446"></span> | 
|  | <span class="source-line-no">3447</span><span id="line-3447">  public void doTestDelete_AndPostInsert(Delete delete) throws IOException, InterruptedException {</span> | 
|  | <span class="source-line-no">3448</span><span id="line-3448">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">3449</span><span id="line-3449">    EnvironmentEdgeManagerTestHelper.injectEdge(new IncrementingEnvironmentEdge());</span> | 
|  | <span class="source-line-no">3450</span><span id="line-3450">    Put put = new Put(row);</span> | 
|  | <span class="source-line-no">3451</span><span id="line-3451">    put.addColumn(fam1, qual1, value1);</span> | 
|  | <span class="source-line-no">3452</span><span id="line-3452">    region.put(put);</span> | 
|  | <span class="source-line-no">3453</span><span id="line-3453"></span> | 
|  | <span class="source-line-no">3454</span><span id="line-3454">    // now delete the value:</span> | 
|  | <span class="source-line-no">3455</span><span id="line-3455">    region.delete(delete);</span> | 
|  | <span class="source-line-no">3456</span><span id="line-3456"></span> | 
|  | <span class="source-line-no">3457</span><span id="line-3457">    // ok put data:</span> | 
|  | <span class="source-line-no">3458</span><span id="line-3458">    put = new Put(row);</span> | 
|  | <span class="source-line-no">3459</span><span id="line-3459">    put.addColumn(fam1, qual1, value2);</span> | 
|  | <span class="source-line-no">3460</span><span id="line-3460">    region.put(put);</span> | 
|  | <span class="source-line-no">3461</span><span id="line-3461"></span> | 
|  | <span class="source-line-no">3462</span><span id="line-3462">    // ok get:</span> | 
|  | <span class="source-line-no">3463</span><span id="line-3463">    Get get = new Get(row);</span> | 
|  | <span class="source-line-no">3464</span><span id="line-3464">    get.addColumn(fam1, qual1);</span> | 
|  | <span class="source-line-no">3465</span><span id="line-3465"></span> | 
|  | <span class="source-line-no">3466</span><span id="line-3466">    Result r = region.get(get);</span> | 
|  | <span class="source-line-no">3467</span><span id="line-3467">    assertEquals(1, r.size());</span> | 
|  | <span class="source-line-no">3468</span><span id="line-3468">    assertArrayEquals(value2, r.getValue(fam1, qual1));</span> | 
|  | <span class="source-line-no">3469</span><span id="line-3469"></span> | 
|  | <span class="source-line-no">3470</span><span id="line-3470">    // next:</span> | 
|  | <span class="source-line-no">3471</span><span id="line-3471">    Scan scan = new Scan().withStartRow(row);</span> | 
|  | <span class="source-line-no">3472</span><span id="line-3472">    scan.addColumn(fam1, qual1);</span> | 
|  | <span class="source-line-no">3473</span><span id="line-3473">    try (InternalScanner s = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">3474</span><span id="line-3474">      List<Cell> results = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3475</span><span id="line-3475">      assertEquals(false, s.next(results));</span> | 
|  | <span class="source-line-no">3476</span><span id="line-3476">      assertEquals(1, results.size());</span> | 
|  | <span class="source-line-no">3477</span><span id="line-3477">      Cell kv = results.get(0);</span> | 
|  | <span class="source-line-no">3478</span><span id="line-3478"></span> | 
|  | <span class="source-line-no">3479</span><span id="line-3479">      assertArrayEquals(value2, CellUtil.cloneValue(kv));</span> | 
|  | <span class="source-line-no">3480</span><span id="line-3480">      assertArrayEquals(fam1, CellUtil.cloneFamily(kv));</span> | 
|  | <span class="source-line-no">3481</span><span id="line-3481">      assertArrayEquals(qual1, CellUtil.cloneQualifier(kv));</span> | 
|  | <span class="source-line-no">3482</span><span id="line-3482">      assertArrayEquals(row, CellUtil.cloneRow(kv));</span> | 
|  | <span class="source-line-no">3483</span><span id="line-3483">    }</span> | 
|  | <span class="source-line-no">3484</span><span id="line-3484">  }</span> | 
|  | <span class="source-line-no">3485</span><span id="line-3485"></span> | 
|  | <span class="source-line-no">3486</span><span id="line-3486">  @Test</span> | 
|  | <span class="source-line-no">3487</span><span id="line-3487">  public void testDelete_CheckTimestampUpdated() throws IOException {</span> | 
|  | <span class="source-line-no">3488</span><span id="line-3488">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3489</span><span id="line-3489">    byte[] col1 = Bytes.toBytes("col1");</span> | 
|  | <span class="source-line-no">3490</span><span id="line-3490">    byte[] col2 = Bytes.toBytes("col2");</span> | 
|  | <span class="source-line-no">3491</span><span id="line-3491">    byte[] col3 = Bytes.toBytes("col3");</span> | 
|  | <span class="source-line-no">3492</span><span id="line-3492"></span> | 
|  | <span class="source-line-no">3493</span><span id="line-3493">    byte[] forUnitTestsOnly = Bytes.toBytes("ForUnitTestsOnly");</span> | 
|  | <span class="source-line-no">3494</span><span id="line-3494"></span> | 
|  | <span class="source-line-no">3495</span><span id="line-3495">    // Setting up region</span> | 
|  | <span class="source-line-no">3496</span><span id="line-3496">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">3497</span><span id="line-3497">    // Building checkerList</span> | 
|  | <span class="source-line-no">3498</span><span id="line-3498">    List<Cell> kvs = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3499</span><span id="line-3499">    kvs.add(new KeyValue(row1, fam1, col1, null));</span> | 
|  | <span class="source-line-no">3500</span><span id="line-3500">    kvs.add(new KeyValue(row1, fam1, col2, null));</span> | 
|  | <span class="source-line-no">3501</span><span id="line-3501">    kvs.add(new KeyValue(row1, fam1, col3, null));</span> | 
|  | <span class="source-line-no">3502</span><span id="line-3502"></span> | 
|  | <span class="source-line-no">3503</span><span id="line-3503">    NavigableMap<byte[], List<Cell>> deleteMap = new TreeMap<>(Bytes.BYTES_COMPARATOR);</span> | 
|  | <span class="source-line-no">3504</span><span id="line-3504">    deleteMap.put(fam1, kvs);</span> | 
|  | <span class="source-line-no">3505</span><span id="line-3505">    region.delete(new Delete(forUnitTestsOnly, HConstants.LATEST_TIMESTAMP, deleteMap));</span> | 
|  | <span class="source-line-no">3506</span><span id="line-3506"></span> | 
|  | <span class="source-line-no">3507</span><span id="line-3507">    // extract the key values out the memstore:</span> | 
|  | <span class="source-line-no">3508</span><span id="line-3508">    // This is kinda hacky, but better than nothing...</span> | 
|  | <span class="source-line-no">3509</span><span id="line-3509">    long now = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">3510</span><span id="line-3510">    AbstractMemStore memstore = (AbstractMemStore) region.getStore(fam1).memstore;</span> | 
|  | <span class="source-line-no">3511</span><span id="line-3511">    Cell firstCell = memstore.getActive().first();</span> | 
|  | <span class="source-line-no">3512</span><span id="line-3512">    assertTrue(firstCell.getTimestamp() <= now);</span> | 
|  | <span class="source-line-no">3513</span><span id="line-3513">    now = firstCell.getTimestamp();</span> | 
|  | <span class="source-line-no">3514</span><span id="line-3514">    for (Cell cell : memstore.getActive().getCellSet()) {</span> | 
|  | <span class="source-line-no">3515</span><span id="line-3515">      assertTrue(cell.getTimestamp() <= now);</span> | 
|  | <span class="source-line-no">3516</span><span id="line-3516">      now = cell.getTimestamp();</span> | 
|  | <span class="source-line-no">3517</span><span id="line-3517">    }</span> | 
|  | <span class="source-line-no">3518</span><span id="line-3518">  }</span> | 
|  | <span class="source-line-no">3519</span><span id="line-3519"></span> | 
|  | <span class="source-line-no">3520</span><span id="line-3520">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">3521</span><span id="line-3521">  // Get tests</span> | 
|  | <span class="source-line-no">3522</span><span id="line-3522">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">3523</span><span id="line-3523">  @Test</span> | 
|  | <span class="source-line-no">3524</span><span id="line-3524">  public void testGet_FamilyChecker() throws IOException {</span> | 
|  | <span class="source-line-no">3525</span><span id="line-3525">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3526</span><span id="line-3526">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3527</span><span id="line-3527">    byte[] fam2 = Bytes.toBytes("False");</span> | 
|  | <span class="source-line-no">3528</span><span id="line-3528">    byte[] col1 = Bytes.toBytes("col1");</span> | 
|  | <span class="source-line-no">3529</span><span id="line-3529"></span> | 
|  | <span class="source-line-no">3530</span><span id="line-3530">    // Setting up region</span> | 
|  | <span class="source-line-no">3531</span><span id="line-3531">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">3532</span><span id="line-3532">    Get get = new Get(row1);</span> | 
|  | <span class="source-line-no">3533</span><span id="line-3533">    get.addColumn(fam2, col1);</span> | 
|  | <span class="source-line-no">3534</span><span id="line-3534"></span> | 
|  | <span class="source-line-no">3535</span><span id="line-3535">    // Test</span> | 
|  | <span class="source-line-no">3536</span><span id="line-3536">    try {</span> | 
|  | <span class="source-line-no">3537</span><span id="line-3537">      region.get(get);</span> | 
|  | <span class="source-line-no">3538</span><span id="line-3538">      fail("Expecting DoNotRetryIOException in get but did not get any");</span> | 
|  | <span class="source-line-no">3539</span><span id="line-3539">    } catch (org.apache.hadoop.hbase.DoNotRetryIOException e) {</span> | 
|  | <span class="source-line-no">3540</span><span id="line-3540">      LOG.info("Got expected DoNotRetryIOException successfully");</span> | 
|  | <span class="source-line-no">3541</span><span id="line-3541">    }</span> | 
|  | <span class="source-line-no">3542</span><span id="line-3542">  }</span> | 
|  | <span class="source-line-no">3543</span><span id="line-3543"></span> | 
|  | <span class="source-line-no">3544</span><span id="line-3544">  @Test</span> | 
|  | <span class="source-line-no">3545</span><span id="line-3545">  public void testGet_Basic() throws IOException {</span> | 
|  | <span class="source-line-no">3546</span><span id="line-3546">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3547</span><span id="line-3547">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3548</span><span id="line-3548">    byte[] col1 = Bytes.toBytes("col1");</span> | 
|  | <span class="source-line-no">3549</span><span id="line-3549">    byte[] col2 = Bytes.toBytes("col2");</span> | 
|  | <span class="source-line-no">3550</span><span id="line-3550">    byte[] col3 = Bytes.toBytes("col3");</span> | 
|  | <span class="source-line-no">3551</span><span id="line-3551">    byte[] col4 = Bytes.toBytes("col4");</span> | 
|  | <span class="source-line-no">3552</span><span id="line-3552">    byte[] col5 = Bytes.toBytes("col5");</span> | 
|  | <span class="source-line-no">3553</span><span id="line-3553"></span> | 
|  | <span class="source-line-no">3554</span><span id="line-3554">    // Setting up region</span> | 
|  | <span class="source-line-no">3555</span><span id="line-3555">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">3556</span><span id="line-3556">    // Add to memstore</span> | 
|  | <span class="source-line-no">3557</span><span id="line-3557">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">3558</span><span id="line-3558">    put.addColumn(fam1, col1, null);</span> | 
|  | <span class="source-line-no">3559</span><span id="line-3559">    put.addColumn(fam1, col2, null);</span> | 
|  | <span class="source-line-no">3560</span><span id="line-3560">    put.addColumn(fam1, col3, null);</span> | 
|  | <span class="source-line-no">3561</span><span id="line-3561">    put.addColumn(fam1, col4, null);</span> | 
|  | <span class="source-line-no">3562</span><span id="line-3562">    put.addColumn(fam1, col5, null);</span> | 
|  | <span class="source-line-no">3563</span><span id="line-3563">    region.put(put);</span> | 
|  | <span class="source-line-no">3564</span><span id="line-3564"></span> | 
|  | <span class="source-line-no">3565</span><span id="line-3565">    Get get = new Get(row1);</span> | 
|  | <span class="source-line-no">3566</span><span id="line-3566">    get.addColumn(fam1, col2);</span> | 
|  | <span class="source-line-no">3567</span><span id="line-3567">    get.addColumn(fam1, col4);</span> | 
|  | <span class="source-line-no">3568</span><span id="line-3568">    // Expected result</span> | 
|  | <span class="source-line-no">3569</span><span id="line-3569">    KeyValue kv1 = new KeyValue(row1, fam1, col2);</span> | 
|  | <span class="source-line-no">3570</span><span id="line-3570">    KeyValue kv2 = new KeyValue(row1, fam1, col4);</span> | 
|  | <span class="source-line-no">3571</span><span id="line-3571">    KeyValue[] expected = { kv1, kv2 };</span> | 
|  | <span class="source-line-no">3572</span><span id="line-3572"></span> | 
|  | <span class="source-line-no">3573</span><span id="line-3573">    // Test</span> | 
|  | <span class="source-line-no">3574</span><span id="line-3574">    Result res = region.get(get);</span> | 
|  | <span class="source-line-no">3575</span><span id="line-3575">    assertEquals(expected.length, res.size());</span> | 
|  | <span class="source-line-no">3576</span><span id="line-3576">    for (int i = 0; i < res.size(); i++) {</span> | 
|  | <span class="source-line-no">3577</span><span id="line-3577">      assertTrue(CellUtil.matchingRows(expected[i], res.rawCells()[i]));</span> | 
|  | <span class="source-line-no">3578</span><span id="line-3578">      assertTrue(CellUtil.matchingFamily(expected[i], res.rawCells()[i]));</span> | 
|  | <span class="source-line-no">3579</span><span id="line-3579">      assertTrue(CellUtil.matchingQualifier(expected[i], res.rawCells()[i]));</span> | 
|  | <span class="source-line-no">3580</span><span id="line-3580">    }</span> | 
|  | <span class="source-line-no">3581</span><span id="line-3581"></span> | 
|  | <span class="source-line-no">3582</span><span id="line-3582">    // Test using a filter on a Get</span> | 
|  | <span class="source-line-no">3583</span><span id="line-3583">    Get g = new Get(row1);</span> | 
|  | <span class="source-line-no">3584</span><span id="line-3584">    final int count = 2;</span> | 
|  | <span class="source-line-no">3585</span><span id="line-3585">    g.setFilter(new ColumnCountGetFilter(count));</span> | 
|  | <span class="source-line-no">3586</span><span id="line-3586">    res = region.get(g);</span> | 
|  | <span class="source-line-no">3587</span><span id="line-3587">    assertEquals(count, res.size());</span> | 
|  | <span class="source-line-no">3588</span><span id="line-3588">  }</span> | 
|  | <span class="source-line-no">3589</span><span id="line-3589"></span> | 
|  | <span class="source-line-no">3590</span><span id="line-3590">  @Test</span> | 
|  | <span class="source-line-no">3591</span><span id="line-3591">  public void testGet_Empty() throws IOException {</span> | 
|  | <span class="source-line-no">3592</span><span id="line-3592">    byte[] row = Bytes.toBytes("row");</span> | 
|  | <span class="source-line-no">3593</span><span id="line-3593">    byte[] fam = Bytes.toBytes("fam");</span> | 
|  | <span class="source-line-no">3594</span><span id="line-3594"></span> | 
|  | <span class="source-line-no">3595</span><span id="line-3595">    this.region = initHRegion(tableName, method, CONF, fam);</span> | 
|  | <span class="source-line-no">3596</span><span id="line-3596">    Get get = new Get(row);</span> | 
|  | <span class="source-line-no">3597</span><span id="line-3597">    get.addFamily(fam);</span> | 
|  | <span class="source-line-no">3598</span><span id="line-3598">    Result r = region.get(get);</span> | 
|  | <span class="source-line-no">3599</span><span id="line-3599"></span> | 
|  | <span class="source-line-no">3600</span><span id="line-3600">    assertTrue(r.isEmpty());</span> | 
|  | <span class="source-line-no">3601</span><span id="line-3601">  }</span> | 
|  | <span class="source-line-no">3602</span><span id="line-3602"></span> | 
|  | <span class="source-line-no">3603</span><span id="line-3603">  @Test</span> | 
|  | <span class="source-line-no">3604</span><span id="line-3604">  public void testGetWithFilter() throws IOException, InterruptedException {</span> | 
|  | <span class="source-line-no">3605</span><span id="line-3605">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3606</span><span id="line-3606">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3607</span><span id="line-3607">    byte[] col1 = Bytes.toBytes("col1");</span> | 
|  | <span class="source-line-no">3608</span><span id="line-3608">    byte[] value1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">3609</span><span id="line-3609">    byte[] value2 = Bytes.toBytes("value2");</span> | 
|  | <span class="source-line-no">3610</span><span id="line-3610"></span> | 
|  | <span class="source-line-no">3611</span><span id="line-3611">    final int maxVersions = 3;</span> | 
|  | <span class="source-line-no">3612</span><span id="line-3612">    TableDescriptor tableDescriptor =</span> | 
|  | <span class="source-line-no">3613</span><span id="line-3613">      TableDescriptorBuilder.newBuilder(TableName.valueOf("testFilterAndColumnTracker"))</span> | 
|  | <span class="source-line-no">3614</span><span id="line-3614">        .setColumnFamily(</span> | 
|  | <span class="source-line-no">3615</span><span id="line-3615">          ColumnFamilyDescriptorBuilder.newBuilder(fam1).setMaxVersions(maxVersions).build())</span> | 
|  | <span class="source-line-no">3616</span><span id="line-3616">        .build();</span> | 
|  | <span class="source-line-no">3617</span><span id="line-3617">    ChunkCreator.initialize(MemStoreLAB.CHUNK_SIZE_DEFAULT, false, 0, 0, 0, null,</span> | 
|  | <span class="source-line-no">3618</span><span id="line-3618">      MemStoreLAB.INDEX_CHUNK_SIZE_PERCENTAGE_DEFAULT);</span> | 
|  | <span class="source-line-no">3619</span><span id="line-3619">    RegionInfo info = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName()).build();</span> | 
|  | <span class="source-line-no">3620</span><span id="line-3620">    Path logDir = TEST_UTIL.getDataTestDirOnTestFS(method + ".log");</span> | 
|  | <span class="source-line-no">3621</span><span id="line-3621">    final WAL wal = HBaseTestingUtil.createWal(TEST_UTIL.getConfiguration(), logDir, info);</span> | 
|  | <span class="source-line-no">3622</span><span id="line-3622">    this.region = TEST_UTIL.createLocalHRegion(info, CONF, tableDescriptor, wal);</span> | 
|  | <span class="source-line-no">3623</span><span id="line-3623"></span> | 
|  | <span class="source-line-no">3624</span><span id="line-3624">    // Put 4 version to memstore</span> | 
|  | <span class="source-line-no">3625</span><span id="line-3625">    long ts = 0;</span> | 
|  | <span class="source-line-no">3626</span><span id="line-3626">    Put put = new Put(row1, ts);</span> | 
|  | <span class="source-line-no">3627</span><span id="line-3627">    put.addColumn(fam1, col1, value1);</span> | 
|  | <span class="source-line-no">3628</span><span id="line-3628">    region.put(put);</span> | 
|  | <span class="source-line-no">3629</span><span id="line-3629">    put = new Put(row1, ts + 1);</span> | 
|  | <span class="source-line-no">3630</span><span id="line-3630">    put.addColumn(fam1, col1, Bytes.toBytes("filter1"));</span> | 
|  | <span class="source-line-no">3631</span><span id="line-3631">    region.put(put);</span> | 
|  | <span class="source-line-no">3632</span><span id="line-3632">    put = new Put(row1, ts + 2);</span> | 
|  | <span class="source-line-no">3633</span><span id="line-3633">    put.addColumn(fam1, col1, Bytes.toBytes("filter2"));</span> | 
|  | <span class="source-line-no">3634</span><span id="line-3634">    region.put(put);</span> | 
|  | <span class="source-line-no">3635</span><span id="line-3635">    put = new Put(row1, ts + 3);</span> | 
|  | <span class="source-line-no">3636</span><span id="line-3636">    put.addColumn(fam1, col1, value2);</span> | 
|  | <span class="source-line-no">3637</span><span id="line-3637">    region.put(put);</span> | 
|  | <span class="source-line-no">3638</span><span id="line-3638"></span> | 
|  | <span class="source-line-no">3639</span><span id="line-3639">    Get get = new Get(row1);</span> | 
|  | <span class="source-line-no">3640</span><span id="line-3640">    get.readAllVersions();</span> | 
|  | <span class="source-line-no">3641</span><span id="line-3641">    Result res = region.get(get);</span> | 
|  | <span class="source-line-no">3642</span><span id="line-3642">    // Get 3 versions, the oldest version has gone from user view</span> | 
|  | <span class="source-line-no">3643</span><span id="line-3643">    assertEquals(maxVersions, res.size());</span> | 
|  | <span class="source-line-no">3644</span><span id="line-3644"></span> | 
|  | <span class="source-line-no">3645</span><span id="line-3645">    get.setFilter(new ValueFilter(CompareOperator.EQUAL, new SubstringComparator("value")));</span> | 
|  | <span class="source-line-no">3646</span><span id="line-3646">    res = region.get(get);</span> | 
|  | <span class="source-line-no">3647</span><span id="line-3647">    // When use value filter, the oldest version should still gone from user view and it</span> | 
|  | <span class="source-line-no">3648</span><span id="line-3648">    // should only return one key vaule</span> | 
|  | <span class="source-line-no">3649</span><span id="line-3649">    assertEquals(1, res.size());</span> | 
|  | <span class="source-line-no">3650</span><span id="line-3650">    assertTrue(CellUtil.matchingValue(new KeyValue(row1, fam1, col1, value2), res.rawCells()[0]));</span> | 
|  | <span class="source-line-no">3651</span><span id="line-3651">    assertEquals(ts + 3, res.rawCells()[0].getTimestamp());</span> | 
|  | <span class="source-line-no">3652</span><span id="line-3652"></span> | 
|  | <span class="source-line-no">3653</span><span id="line-3653">    region.flush(true);</span> | 
|  | <span class="source-line-no">3654</span><span id="line-3654">    region.compact(true);</span> | 
|  | <span class="source-line-no">3655</span><span id="line-3655">    Thread.sleep(1000);</span> | 
|  | <span class="source-line-no">3656</span><span id="line-3656">    res = region.get(get);</span> | 
|  | <span class="source-line-no">3657</span><span id="line-3657">    // After flush and compact, the result should be consistent with previous result</span> | 
|  | <span class="source-line-no">3658</span><span id="line-3658">    assertEquals(1, res.size());</span> | 
|  | <span class="source-line-no">3659</span><span id="line-3659">    assertTrue(CellUtil.matchingValue(new KeyValue(row1, fam1, col1, value2), res.rawCells()[0]));</span> | 
|  | <span class="source-line-no">3660</span><span id="line-3660">  }</span> | 
|  | <span class="source-line-no">3661</span><span id="line-3661"></span> | 
|  | <span class="source-line-no">3662</span><span id="line-3662">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">3663</span><span id="line-3663">  // Scanner tests</span> | 
|  | <span class="source-line-no">3664</span><span id="line-3664">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">3665</span><span id="line-3665">  @Test</span> | 
|  | <span class="source-line-no">3666</span><span id="line-3666">  public void testGetScanner_WithOkFamilies() throws IOException {</span> | 
|  | <span class="source-line-no">3667</span><span id="line-3667">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3668</span><span id="line-3668">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">3669</span><span id="line-3669"></span> | 
|  | <span class="source-line-no">3670</span><span id="line-3670">    byte[][] families = { fam1, fam2 };</span> | 
|  | <span class="source-line-no">3671</span><span id="line-3671"></span> | 
|  | <span class="source-line-no">3672</span><span id="line-3672">    // Setting up region</span> | 
|  | <span class="source-line-no">3673</span><span id="line-3673">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3674</span><span id="line-3674">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">3675</span><span id="line-3675">    scan.addFamily(fam1);</span> | 
|  | <span class="source-line-no">3676</span><span id="line-3676">    scan.addFamily(fam2);</span> | 
|  | <span class="source-line-no">3677</span><span id="line-3677">    region.getScanner(scan).close();</span> | 
|  | <span class="source-line-no">3678</span><span id="line-3678">  }</span> | 
|  | <span class="source-line-no">3679</span><span id="line-3679"></span> | 
|  | <span class="source-line-no">3680</span><span id="line-3680">  @Test</span> | 
|  | <span class="source-line-no">3681</span><span id="line-3681">  public void testGetScanner_WithNotOkFamilies() throws IOException {</span> | 
|  | <span class="source-line-no">3682</span><span id="line-3682">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3683</span><span id="line-3683">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">3684</span><span id="line-3684"></span> | 
|  | <span class="source-line-no">3685</span><span id="line-3685">    byte[][] families = { fam1 };</span> | 
|  | <span class="source-line-no">3686</span><span id="line-3686"></span> | 
|  | <span class="source-line-no">3687</span><span id="line-3687">    // Setting up region</span> | 
|  | <span class="source-line-no">3688</span><span id="line-3688">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3689</span><span id="line-3689">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">3690</span><span id="line-3690">    scan.addFamily(fam2);</span> | 
|  | <span class="source-line-no">3691</span><span id="line-3691">    assertThrows(NoSuchColumnFamilyException.class, () -> region.getScanner(scan));</span> | 
|  | <span class="source-line-no">3692</span><span id="line-3692">  }</span> | 
|  | <span class="source-line-no">3693</span><span id="line-3693"></span> | 
|  | <span class="source-line-no">3694</span><span id="line-3694">  @Test</span> | 
|  | <span class="source-line-no">3695</span><span id="line-3695">  public void testGetScanner_WithNoFamilies() throws IOException {</span> | 
|  | <span class="source-line-no">3696</span><span id="line-3696">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3697</span><span id="line-3697">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3698</span><span id="line-3698">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">3699</span><span id="line-3699">    byte[] fam3 = Bytes.toBytes("fam3");</span> | 
|  | <span class="source-line-no">3700</span><span id="line-3700">    byte[] fam4 = Bytes.toBytes("fam4");</span> | 
|  | <span class="source-line-no">3701</span><span id="line-3701"></span> | 
|  | <span class="source-line-no">3702</span><span id="line-3702">    byte[][] families = { fam1, fam2, fam3, fam4 };</span> | 
|  | <span class="source-line-no">3703</span><span id="line-3703"></span> | 
|  | <span class="source-line-no">3704</span><span id="line-3704">    // Setting up region</span> | 
|  | <span class="source-line-no">3705</span><span id="line-3705">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3706</span><span id="line-3706">    // Putting data in Region</span> | 
|  | <span class="source-line-no">3707</span><span id="line-3707">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">3708</span><span id="line-3708">    put.addColumn(fam1, null, null);</span> | 
|  | <span class="source-line-no">3709</span><span id="line-3709">    put.addColumn(fam2, null, null);</span> | 
|  | <span class="source-line-no">3710</span><span id="line-3710">    put.addColumn(fam3, null, null);</span> | 
|  | <span class="source-line-no">3711</span><span id="line-3711">    put.addColumn(fam4, null, null);</span> | 
|  | <span class="source-line-no">3712</span><span id="line-3712">    region.put(put);</span> | 
|  | <span class="source-line-no">3713</span><span id="line-3713"></span> | 
|  | <span class="source-line-no">3714</span><span id="line-3714">    Scan scan = null;</span> | 
|  | <span class="source-line-no">3715</span><span id="line-3715"></span> | 
|  | <span class="source-line-no">3716</span><span id="line-3716">    // Testing to see how many scanners that is produced by getScanner, starting with known number,</span> | 
|  | <span class="source-line-no">3717</span><span id="line-3717">    // 2 - current = 1</span> | 
|  | <span class="source-line-no">3718</span><span id="line-3718">    scan = new Scan();</span> | 
|  | <span class="source-line-no">3719</span><span id="line-3719">    scan.addFamily(fam2);</span> | 
|  | <span class="source-line-no">3720</span><span id="line-3720">    scan.addFamily(fam4);</span> | 
|  | <span class="source-line-no">3721</span><span id="line-3721">    try (RegionScannerImpl is = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">3722</span><span id="line-3722">      assertEquals(1, is.storeHeap.getHeap().size());</span> | 
|  | <span class="source-line-no">3723</span><span id="line-3723">    }</span> | 
|  | <span class="source-line-no">3724</span><span id="line-3724"></span> | 
|  | <span class="source-line-no">3725</span><span id="line-3725">    scan = new Scan();</span> | 
|  | <span class="source-line-no">3726</span><span id="line-3726">    try (RegionScannerImpl is = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">3727</span><span id="line-3727">      assertEquals(families.length - 1, is.storeHeap.getHeap().size());</span> | 
|  | <span class="source-line-no">3728</span><span id="line-3728">    }</span> | 
|  | <span class="source-line-no">3729</span><span id="line-3729">  }</span> | 
|  | <span class="source-line-no">3730</span><span id="line-3730"></span> | 
|  | <span class="source-line-no">3731</span><span id="line-3731">  /**</span> | 
|  | <span class="source-line-no">3732</span><span id="line-3732">   * This method tests https://issues.apache.org/jira/browse/HBASE-2516.</span> | 
|  | <span class="source-line-no">3733</span><span id="line-3733">   */</span> | 
|  | <span class="source-line-no">3734</span><span id="line-3734">  @Test</span> | 
|  | <span class="source-line-no">3735</span><span id="line-3735">  public void testGetScanner_WithRegionClosed() throws IOException {</span> | 
|  | <span class="source-line-no">3736</span><span id="line-3736">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3737</span><span id="line-3737">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">3738</span><span id="line-3738"></span> | 
|  | <span class="source-line-no">3739</span><span id="line-3739">    byte[][] families = { fam1, fam2 };</span> | 
|  | <span class="source-line-no">3740</span><span id="line-3740"></span> | 
|  | <span class="source-line-no">3741</span><span id="line-3741">    // Setting up region</span> | 
|  | <span class="source-line-no">3742</span><span id="line-3742">    region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3743</span><span id="line-3743">    region.closed.set(true);</span> | 
|  | <span class="source-line-no">3744</span><span id="line-3744">    try {</span> | 
|  | <span class="source-line-no">3745</span><span id="line-3745">      assertThrows(NotServingRegionException.class, () -> region.getScanner(null));</span> | 
|  | <span class="source-line-no">3746</span><span id="line-3746">    } finally {</span> | 
|  | <span class="source-line-no">3747</span><span id="line-3747">      // so we can close the region in tearDown</span> | 
|  | <span class="source-line-no">3748</span><span id="line-3748">      region.closed.set(false);</span> | 
|  | <span class="source-line-no">3749</span><span id="line-3749">    }</span> | 
|  | <span class="source-line-no">3750</span><span id="line-3750">  }</span> | 
|  | <span class="source-line-no">3751</span><span id="line-3751"></span> | 
|  | <span class="source-line-no">3752</span><span id="line-3752">  @Test</span> | 
|  | <span class="source-line-no">3753</span><span id="line-3753">  public void testRegionScanner_Next() throws IOException {</span> | 
|  | <span class="source-line-no">3754</span><span id="line-3754">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3755</span><span id="line-3755">    byte[] row2 = Bytes.toBytes("row2");</span> | 
|  | <span class="source-line-no">3756</span><span id="line-3756">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3757</span><span id="line-3757">    byte[] fam2 = Bytes.toBytes("fam2");</span> | 
|  | <span class="source-line-no">3758</span><span id="line-3758">    byte[] fam3 = Bytes.toBytes("fam3");</span> | 
|  | <span class="source-line-no">3759</span><span id="line-3759">    byte[] fam4 = Bytes.toBytes("fam4");</span> | 
|  | <span class="source-line-no">3760</span><span id="line-3760"></span> | 
|  | <span class="source-line-no">3761</span><span id="line-3761">    byte[][] families = { fam1, fam2, fam3, fam4 };</span> | 
|  | <span class="source-line-no">3762</span><span id="line-3762">    long ts = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">3763</span><span id="line-3763"></span> | 
|  | <span class="source-line-no">3764</span><span id="line-3764">    // Setting up region</span> | 
|  | <span class="source-line-no">3765</span><span id="line-3765">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3766</span><span id="line-3766">    // Putting data in Region</span> | 
|  | <span class="source-line-no">3767</span><span id="line-3767">    Put put = null;</span> | 
|  | <span class="source-line-no">3768</span><span id="line-3768">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">3769</span><span id="line-3769">    put.addColumn(fam1, (byte[]) null, ts, null);</span> | 
|  | <span class="source-line-no">3770</span><span id="line-3770">    put.addColumn(fam2, (byte[]) null, ts, null);</span> | 
|  | <span class="source-line-no">3771</span><span id="line-3771">    put.addColumn(fam3, (byte[]) null, ts, null);</span> | 
|  | <span class="source-line-no">3772</span><span id="line-3772">    put.addColumn(fam4, (byte[]) null, ts, null);</span> | 
|  | <span class="source-line-no">3773</span><span id="line-3773">    region.put(put);</span> | 
|  | <span class="source-line-no">3774</span><span id="line-3774"></span> | 
|  | <span class="source-line-no">3775</span><span id="line-3775">    put = new Put(row2);</span> | 
|  | <span class="source-line-no">3776</span><span id="line-3776">    put.addColumn(fam1, (byte[]) null, ts, null);</span> | 
|  | <span class="source-line-no">3777</span><span id="line-3777">    put.addColumn(fam2, (byte[]) null, ts, null);</span> | 
|  | <span class="source-line-no">3778</span><span id="line-3778">    put.addColumn(fam3, (byte[]) null, ts, null);</span> | 
|  | <span class="source-line-no">3779</span><span id="line-3779">    put.addColumn(fam4, (byte[]) null, ts, null);</span> | 
|  | <span class="source-line-no">3780</span><span id="line-3780">    region.put(put);</span> | 
|  | <span class="source-line-no">3781</span><span id="line-3781"></span> | 
|  | <span class="source-line-no">3782</span><span id="line-3782">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">3783</span><span id="line-3783">    scan.addFamily(fam2);</span> | 
|  | <span class="source-line-no">3784</span><span id="line-3784">    scan.addFamily(fam4);</span> | 
|  | <span class="source-line-no">3785</span><span id="line-3785">    try (InternalScanner is = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">3786</span><span id="line-3786">      List<ExtendedCell> res = null;</span> | 
|  | <span class="source-line-no">3787</span><span id="line-3787"></span> | 
|  | <span class="source-line-no">3788</span><span id="line-3788">      // Result 1</span> | 
|  | <span class="source-line-no">3789</span><span id="line-3789">      List<ExtendedCell> expected1 = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3790</span><span id="line-3790">      expected1.add(new KeyValue(row1, fam2, null, ts, KeyValue.Type.Put, null));</span> | 
|  | <span class="source-line-no">3791</span><span id="line-3791">      expected1.add(new KeyValue(row1, fam4, null, ts, KeyValue.Type.Put, null));</span> | 
|  | <span class="source-line-no">3792</span><span id="line-3792"></span> | 
|  | <span class="source-line-no">3793</span><span id="line-3793">      res = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3794</span><span id="line-3794">      is.next(res);</span> | 
|  | <span class="source-line-no">3795</span><span id="line-3795">      for (int i = 0; i < res.size(); i++) {</span> | 
|  | <span class="source-line-no">3796</span><span id="line-3796">        assertTrue(PrivateCellUtil.equalsIgnoreMvccVersion(expected1.get(i), res.get(i)));</span> | 
|  | <span class="source-line-no">3797</span><span id="line-3797">      }</span> | 
|  | <span class="source-line-no">3798</span><span id="line-3798"></span> | 
|  | <span class="source-line-no">3799</span><span id="line-3799">      // Result 2</span> | 
|  | <span class="source-line-no">3800</span><span id="line-3800">      List<ExtendedCell> expected2 = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3801</span><span id="line-3801">      expected2.add(new KeyValue(row2, fam2, null, ts, KeyValue.Type.Put, null));</span> | 
|  | <span class="source-line-no">3802</span><span id="line-3802">      expected2.add(new KeyValue(row2, fam4, null, ts, KeyValue.Type.Put, null));</span> | 
|  | <span class="source-line-no">3803</span><span id="line-3803"></span> | 
|  | <span class="source-line-no">3804</span><span id="line-3804">      res = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3805</span><span id="line-3805">      is.next(res);</span> | 
|  | <span class="source-line-no">3806</span><span id="line-3806">      for (int i = 0; i < res.size(); i++) {</span> | 
|  | <span class="source-line-no">3807</span><span id="line-3807">        assertTrue(PrivateCellUtil.equalsIgnoreMvccVersion(expected2.get(i), res.get(i)));</span> | 
|  | <span class="source-line-no">3808</span><span id="line-3808">      }</span> | 
|  | <span class="source-line-no">3809</span><span id="line-3809">    }</span> | 
|  | <span class="source-line-no">3810</span><span id="line-3810">  }</span> | 
|  | <span class="source-line-no">3811</span><span id="line-3811"></span> | 
|  | <span class="source-line-no">3812</span><span id="line-3812">  @Test</span> | 
|  | <span class="source-line-no">3813</span><span id="line-3813">  public void testScanner_ExplicitColumns_FromMemStore_EnforceVersions() throws IOException {</span> | 
|  | <span class="source-line-no">3814</span><span id="line-3814">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3815</span><span id="line-3815">    byte[] qf1 = Bytes.toBytes("qualifier1");</span> | 
|  | <span class="source-line-no">3816</span><span id="line-3816">    byte[] qf2 = Bytes.toBytes("qualifier2");</span> | 
|  | <span class="source-line-no">3817</span><span id="line-3817">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3818</span><span id="line-3818">    byte[][] families = { fam1 };</span> | 
|  | <span class="source-line-no">3819</span><span id="line-3819"></span> | 
|  | <span class="source-line-no">3820</span><span id="line-3820">    long ts1 = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">3821</span><span id="line-3821">    long ts2 = ts1 + 1;</span> | 
|  | <span class="source-line-no">3822</span><span id="line-3822">    long ts3 = ts1 + 2;</span> | 
|  | <span class="source-line-no">3823</span><span id="line-3823"></span> | 
|  | <span class="source-line-no">3824</span><span id="line-3824">    // Setting up region</span> | 
|  | <span class="source-line-no">3825</span><span id="line-3825">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3826</span><span id="line-3826">    // Putting data in Region</span> | 
|  | <span class="source-line-no">3827</span><span id="line-3827">    Put put = null;</span> | 
|  | <span class="source-line-no">3828</span><span id="line-3828">    KeyValue kv13 = new KeyValue(row1, fam1, qf1, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3829</span><span id="line-3829">    KeyValue kv12 = new KeyValue(row1, fam1, qf1, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3830</span><span id="line-3830">    KeyValue kv11 = new KeyValue(row1, fam1, qf1, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3831</span><span id="line-3831"></span> | 
|  | <span class="source-line-no">3832</span><span id="line-3832">    KeyValue kv23 = new KeyValue(row1, fam1, qf2, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3833</span><span id="line-3833">    KeyValue kv22 = new KeyValue(row1, fam1, qf2, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3834</span><span id="line-3834">    KeyValue kv21 = new KeyValue(row1, fam1, qf2, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3835</span><span id="line-3835"></span> | 
|  | <span class="source-line-no">3836</span><span id="line-3836">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">3837</span><span id="line-3837">    put.add(kv13);</span> | 
|  | <span class="source-line-no">3838</span><span id="line-3838">    put.add(kv12);</span> | 
|  | <span class="source-line-no">3839</span><span id="line-3839">    put.add(kv11);</span> | 
|  | <span class="source-line-no">3840</span><span id="line-3840">    put.add(kv23);</span> | 
|  | <span class="source-line-no">3841</span><span id="line-3841">    put.add(kv22);</span> | 
|  | <span class="source-line-no">3842</span><span id="line-3842">    put.add(kv21);</span> | 
|  | <span class="source-line-no">3843</span><span id="line-3843">    region.put(put);</span> | 
|  | <span class="source-line-no">3844</span><span id="line-3844"></span> | 
|  | <span class="source-line-no">3845</span><span id="line-3845">    // Expected</span> | 
|  | <span class="source-line-no">3846</span><span id="line-3846">    List<Cell> expected = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3847</span><span id="line-3847">    expected.add(kv13);</span> | 
|  | <span class="source-line-no">3848</span><span id="line-3848">    expected.add(kv12);</span> | 
|  | <span class="source-line-no">3849</span><span id="line-3849"></span> | 
|  | <span class="source-line-no">3850</span><span id="line-3850">    Scan scan = new Scan().withStartRow(row1);</span> | 
|  | <span class="source-line-no">3851</span><span id="line-3851">    scan.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">3852</span><span id="line-3852">    scan.readVersions(MAX_VERSIONS);</span> | 
|  | <span class="source-line-no">3853</span><span id="line-3853">    List<Cell> actual = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3854</span><span id="line-3854">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">3855</span><span id="line-3855">      boolean hasNext = scanner.next(actual);</span> | 
|  | <span class="source-line-no">3856</span><span id="line-3856">      assertEquals(false, hasNext);</span> | 
|  | <span class="source-line-no">3857</span><span id="line-3857"></span> | 
|  | <span class="source-line-no">3858</span><span id="line-3858">      // Verify result</span> | 
|  | <span class="source-line-no">3859</span><span id="line-3859">      for (int i = 0; i < expected.size(); i++) {</span> | 
|  | <span class="source-line-no">3860</span><span id="line-3860">        assertEquals(expected.get(i), actual.get(i));</span> | 
|  | <span class="source-line-no">3861</span><span id="line-3861">      }</span> | 
|  | <span class="source-line-no">3862</span><span id="line-3862">    }</span> | 
|  | <span class="source-line-no">3863</span><span id="line-3863">  }</span> | 
|  | <span class="source-line-no">3864</span><span id="line-3864"></span> | 
|  | <span class="source-line-no">3865</span><span id="line-3865">  @Test</span> | 
|  | <span class="source-line-no">3866</span><span id="line-3866">  public void testScanner_ExplicitColumns_FromFilesOnly_EnforceVersions() throws IOException {</span> | 
|  | <span class="source-line-no">3867</span><span id="line-3867">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3868</span><span id="line-3868">    byte[] qf1 = Bytes.toBytes("qualifier1");</span> | 
|  | <span class="source-line-no">3869</span><span id="line-3869">    byte[] qf2 = Bytes.toBytes("qualifier2");</span> | 
|  | <span class="source-line-no">3870</span><span id="line-3870">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3871</span><span id="line-3871">    byte[][] families = { fam1 };</span> | 
|  | <span class="source-line-no">3872</span><span id="line-3872"></span> | 
|  | <span class="source-line-no">3873</span><span id="line-3873">    long ts1 = 1;</span> | 
|  | <span class="source-line-no">3874</span><span id="line-3874">    long ts2 = ts1 + 1;</span> | 
|  | <span class="source-line-no">3875</span><span id="line-3875">    long ts3 = ts1 + 2;</span> | 
|  | <span class="source-line-no">3876</span><span id="line-3876"></span> | 
|  | <span class="source-line-no">3877</span><span id="line-3877">    // Setting up region</span> | 
|  | <span class="source-line-no">3878</span><span id="line-3878">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3879</span><span id="line-3879">    // Putting data in Region</span> | 
|  | <span class="source-line-no">3880</span><span id="line-3880">    Put put = null;</span> | 
|  | <span class="source-line-no">3881</span><span id="line-3881">    KeyValue kv13 = new KeyValue(row1, fam1, qf1, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3882</span><span id="line-3882">    KeyValue kv12 = new KeyValue(row1, fam1, qf1, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3883</span><span id="line-3883">    KeyValue kv11 = new KeyValue(row1, fam1, qf1, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3884</span><span id="line-3884"></span> | 
|  | <span class="source-line-no">3885</span><span id="line-3885">    KeyValue kv23 = new KeyValue(row1, fam1, qf2, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3886</span><span id="line-3886">    KeyValue kv22 = new KeyValue(row1, fam1, qf2, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3887</span><span id="line-3887">    KeyValue kv21 = new KeyValue(row1, fam1, qf2, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3888</span><span id="line-3888"></span> | 
|  | <span class="source-line-no">3889</span><span id="line-3889">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">3890</span><span id="line-3890">    put.add(kv13);</span> | 
|  | <span class="source-line-no">3891</span><span id="line-3891">    put.add(kv12);</span> | 
|  | <span class="source-line-no">3892</span><span id="line-3892">    put.add(kv11);</span> | 
|  | <span class="source-line-no">3893</span><span id="line-3893">    put.add(kv23);</span> | 
|  | <span class="source-line-no">3894</span><span id="line-3894">    put.add(kv22);</span> | 
|  | <span class="source-line-no">3895</span><span id="line-3895">    put.add(kv21);</span> | 
|  | <span class="source-line-no">3896</span><span id="line-3896">    region.put(put);</span> | 
|  | <span class="source-line-no">3897</span><span id="line-3897">    region.flush(true);</span> | 
|  | <span class="source-line-no">3898</span><span id="line-3898"></span> | 
|  | <span class="source-line-no">3899</span><span id="line-3899">    // Expected</span> | 
|  | <span class="source-line-no">3900</span><span id="line-3900">    List<ExtendedCell> expected = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3901</span><span id="line-3901">    expected.add(kv13);</span> | 
|  | <span class="source-line-no">3902</span><span id="line-3902">    expected.add(kv12);</span> | 
|  | <span class="source-line-no">3903</span><span id="line-3903">    expected.add(kv23);</span> | 
|  | <span class="source-line-no">3904</span><span id="line-3904">    expected.add(kv22);</span> | 
|  | <span class="source-line-no">3905</span><span id="line-3905"></span> | 
|  | <span class="source-line-no">3906</span><span id="line-3906">    Scan scan = new Scan().withStartRow(row1);</span> | 
|  | <span class="source-line-no">3907</span><span id="line-3907">    scan.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">3908</span><span id="line-3908">    scan.addColumn(fam1, qf2);</span> | 
|  | <span class="source-line-no">3909</span><span id="line-3909">    scan.readVersions(MAX_VERSIONS);</span> | 
|  | <span class="source-line-no">3910</span><span id="line-3910">    List<ExtendedCell> actual = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3911</span><span id="line-3911">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">3912</span><span id="line-3912">      boolean hasNext = scanner.next(actual);</span> | 
|  | <span class="source-line-no">3913</span><span id="line-3913">      assertEquals(false, hasNext);</span> | 
|  | <span class="source-line-no">3914</span><span id="line-3914"></span> | 
|  | <span class="source-line-no">3915</span><span id="line-3915">      // Verify result</span> | 
|  | <span class="source-line-no">3916</span><span id="line-3916">      for (int i = 0; i < expected.size(); i++) {</span> | 
|  | <span class="source-line-no">3917</span><span id="line-3917">        assertTrue(PrivateCellUtil.equalsIgnoreMvccVersion(expected.get(i), actual.get(i)));</span> | 
|  | <span class="source-line-no">3918</span><span id="line-3918">      }</span> | 
|  | <span class="source-line-no">3919</span><span id="line-3919">    }</span> | 
|  | <span class="source-line-no">3920</span><span id="line-3920">  }</span> | 
|  | <span class="source-line-no">3921</span><span id="line-3921"></span> | 
|  | <span class="source-line-no">3922</span><span id="line-3922">  @Test</span> | 
|  | <span class="source-line-no">3923</span><span id="line-3923">  public void testScanner_ExplicitColumns_FromMemStoreAndFiles_EnforceVersions()</span> | 
|  | <span class="source-line-no">3924</span><span id="line-3924">    throws IOException {</span> | 
|  | <span class="source-line-no">3925</span><span id="line-3925">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">3926</span><span id="line-3926">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">3927</span><span id="line-3927">    byte[][] families = { fam1 };</span> | 
|  | <span class="source-line-no">3928</span><span id="line-3928">    byte[] qf1 = Bytes.toBytes("qualifier1");</span> | 
|  | <span class="source-line-no">3929</span><span id="line-3929">    byte[] qf2 = Bytes.toBytes("qualifier2");</span> | 
|  | <span class="source-line-no">3930</span><span id="line-3930"></span> | 
|  | <span class="source-line-no">3931</span><span id="line-3931">    long ts1 = 1;</span> | 
|  | <span class="source-line-no">3932</span><span id="line-3932">    long ts2 = ts1 + 1;</span> | 
|  | <span class="source-line-no">3933</span><span id="line-3933">    long ts3 = ts1 + 2;</span> | 
|  | <span class="source-line-no">3934</span><span id="line-3934">    long ts4 = ts1 + 3;</span> | 
|  | <span class="source-line-no">3935</span><span id="line-3935"></span> | 
|  | <span class="source-line-no">3936</span><span id="line-3936">    // Setting up region</span> | 
|  | <span class="source-line-no">3937</span><span id="line-3937">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">3938</span><span id="line-3938">    // Putting data in Region</span> | 
|  | <span class="source-line-no">3939</span><span id="line-3939">    KeyValue kv14 = new KeyValue(row1, fam1, qf1, ts4, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3940</span><span id="line-3940">    KeyValue kv13 = new KeyValue(row1, fam1, qf1, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3941</span><span id="line-3941">    KeyValue kv12 = new KeyValue(row1, fam1, qf1, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3942</span><span id="line-3942">    KeyValue kv11 = new KeyValue(row1, fam1, qf1, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3943</span><span id="line-3943"></span> | 
|  | <span class="source-line-no">3944</span><span id="line-3944">    KeyValue kv24 = new KeyValue(row1, fam1, qf2, ts4, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3945</span><span id="line-3945">    KeyValue kv23 = new KeyValue(row1, fam1, qf2, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3946</span><span id="line-3946">    KeyValue kv22 = new KeyValue(row1, fam1, qf2, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3947</span><span id="line-3947">    KeyValue kv21 = new KeyValue(row1, fam1, qf2, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">3948</span><span id="line-3948"></span> | 
|  | <span class="source-line-no">3949</span><span id="line-3949">    Put put = null;</span> | 
|  | <span class="source-line-no">3950</span><span id="line-3950">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">3951</span><span id="line-3951">    put.add(kv14);</span> | 
|  | <span class="source-line-no">3952</span><span id="line-3952">    put.add(kv24);</span> | 
|  | <span class="source-line-no">3953</span><span id="line-3953">    region.put(put);</span> | 
|  | <span class="source-line-no">3954</span><span id="line-3954">    region.flush(true);</span> | 
|  | <span class="source-line-no">3955</span><span id="line-3955"></span> | 
|  | <span class="source-line-no">3956</span><span id="line-3956">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">3957</span><span id="line-3957">    put.add(kv23);</span> | 
|  | <span class="source-line-no">3958</span><span id="line-3958">    put.add(kv13);</span> | 
|  | <span class="source-line-no">3959</span><span id="line-3959">    region.put(put);</span> | 
|  | <span class="source-line-no">3960</span><span id="line-3960">    region.flush(true);</span> | 
|  | <span class="source-line-no">3961</span><span id="line-3961"></span> | 
|  | <span class="source-line-no">3962</span><span id="line-3962">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">3963</span><span id="line-3963">    put.add(kv22);</span> | 
|  | <span class="source-line-no">3964</span><span id="line-3964">    put.add(kv12);</span> | 
|  | <span class="source-line-no">3965</span><span id="line-3965">    region.put(put);</span> | 
|  | <span class="source-line-no">3966</span><span id="line-3966">    region.flush(true);</span> | 
|  | <span class="source-line-no">3967</span><span id="line-3967"></span> | 
|  | <span class="source-line-no">3968</span><span id="line-3968">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">3969</span><span id="line-3969">    put.add(kv21);</span> | 
|  | <span class="source-line-no">3970</span><span id="line-3970">    put.add(kv11);</span> | 
|  | <span class="source-line-no">3971</span><span id="line-3971">    region.put(put);</span> | 
|  | <span class="source-line-no">3972</span><span id="line-3972"></span> | 
|  | <span class="source-line-no">3973</span><span id="line-3973">    // Expected</span> | 
|  | <span class="source-line-no">3974</span><span id="line-3974">    List<ExtendedCell> expected = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3975</span><span id="line-3975">    expected.add(kv14);</span> | 
|  | <span class="source-line-no">3976</span><span id="line-3976">    expected.add(kv13);</span> | 
|  | <span class="source-line-no">3977</span><span id="line-3977">    expected.add(kv12);</span> | 
|  | <span class="source-line-no">3978</span><span id="line-3978">    expected.add(kv24);</span> | 
|  | <span class="source-line-no">3979</span><span id="line-3979">    expected.add(kv23);</span> | 
|  | <span class="source-line-no">3980</span><span id="line-3980">    expected.add(kv22);</span> | 
|  | <span class="source-line-no">3981</span><span id="line-3981"></span> | 
|  | <span class="source-line-no">3982</span><span id="line-3982">    Scan scan = new Scan().withStartRow(row1);</span> | 
|  | <span class="source-line-no">3983</span><span id="line-3983">    scan.addColumn(fam1, qf1);</span> | 
|  | <span class="source-line-no">3984</span><span id="line-3984">    scan.addColumn(fam1, qf2);</span> | 
|  | <span class="source-line-no">3985</span><span id="line-3985">    int versions = 3;</span> | 
|  | <span class="source-line-no">3986</span><span id="line-3986">    scan.readVersions(versions);</span> | 
|  | <span class="source-line-no">3987</span><span id="line-3987">    List<ExtendedCell> actual = new ArrayList<>();</span> | 
|  | <span class="source-line-no">3988</span><span id="line-3988">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">3989</span><span id="line-3989">      boolean hasNext = scanner.next(actual);</span> | 
|  | <span class="source-line-no">3990</span><span id="line-3990">      assertEquals(false, hasNext);</span> | 
|  | <span class="source-line-no">3991</span><span id="line-3991"></span> | 
|  | <span class="source-line-no">3992</span><span id="line-3992">      // Verify result</span> | 
|  | <span class="source-line-no">3993</span><span id="line-3993">      for (int i = 0; i < expected.size(); i++) {</span> | 
|  | <span class="source-line-no">3994</span><span id="line-3994">        assertTrue(PrivateCellUtil.equalsIgnoreMvccVersion(expected.get(i), actual.get(i)));</span> | 
|  | <span class="source-line-no">3995</span><span id="line-3995">      }</span> | 
|  | <span class="source-line-no">3996</span><span id="line-3996">    }</span> | 
|  | <span class="source-line-no">3997</span><span id="line-3997">  }</span> | 
|  | <span class="source-line-no">3998</span><span id="line-3998"></span> | 
|  | <span class="source-line-no">3999</span><span id="line-3999">  @Test</span> | 
|  | <span class="source-line-no">4000</span><span id="line-4000">  public void testScanner_Wildcard_FromMemStore_EnforceVersions() throws IOException {</span> | 
|  | <span class="source-line-no">4001</span><span id="line-4001">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">4002</span><span id="line-4002">    byte[] qf1 = Bytes.toBytes("qualifier1");</span> | 
|  | <span class="source-line-no">4003</span><span id="line-4003">    byte[] qf2 = Bytes.toBytes("qualifier2");</span> | 
|  | <span class="source-line-no">4004</span><span id="line-4004">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">4005</span><span id="line-4005">    byte[][] families = { fam1 };</span> | 
|  | <span class="source-line-no">4006</span><span id="line-4006"></span> | 
|  | <span class="source-line-no">4007</span><span id="line-4007">    long ts1 = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">4008</span><span id="line-4008">    long ts2 = ts1 + 1;</span> | 
|  | <span class="source-line-no">4009</span><span id="line-4009">    long ts3 = ts1 + 2;</span> | 
|  | <span class="source-line-no">4010</span><span id="line-4010"></span> | 
|  | <span class="source-line-no">4011</span><span id="line-4011">    // Setting up region</span> | 
|  | <span class="source-line-no">4012</span><span id="line-4012">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">4013</span><span id="line-4013">    // Putting data in Region</span> | 
|  | <span class="source-line-no">4014</span><span id="line-4014">    Put put = null;</span> | 
|  | <span class="source-line-no">4015</span><span id="line-4015">    KeyValue kv13 = new KeyValue(row1, fam1, qf1, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4016</span><span id="line-4016">    KeyValue kv12 = new KeyValue(row1, fam1, qf1, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4017</span><span id="line-4017">    KeyValue kv11 = new KeyValue(row1, fam1, qf1, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4018</span><span id="line-4018"></span> | 
|  | <span class="source-line-no">4019</span><span id="line-4019">    KeyValue kv23 = new KeyValue(row1, fam1, qf2, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4020</span><span id="line-4020">    KeyValue kv22 = new KeyValue(row1, fam1, qf2, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4021</span><span id="line-4021">    KeyValue kv21 = new KeyValue(row1, fam1, qf2, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4022</span><span id="line-4022"></span> | 
|  | <span class="source-line-no">4023</span><span id="line-4023">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">4024</span><span id="line-4024">    put.add(kv13);</span> | 
|  | <span class="source-line-no">4025</span><span id="line-4025">    put.add(kv12);</span> | 
|  | <span class="source-line-no">4026</span><span id="line-4026">    put.add(kv11);</span> | 
|  | <span class="source-line-no">4027</span><span id="line-4027">    put.add(kv23);</span> | 
|  | <span class="source-line-no">4028</span><span id="line-4028">    put.add(kv22);</span> | 
|  | <span class="source-line-no">4029</span><span id="line-4029">    put.add(kv21);</span> | 
|  | <span class="source-line-no">4030</span><span id="line-4030">    region.put(put);</span> | 
|  | <span class="source-line-no">4031</span><span id="line-4031"></span> | 
|  | <span class="source-line-no">4032</span><span id="line-4032">    // Expected</span> | 
|  | <span class="source-line-no">4033</span><span id="line-4033">    List<Cell> expected = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4034</span><span id="line-4034">    expected.add(kv13);</span> | 
|  | <span class="source-line-no">4035</span><span id="line-4035">    expected.add(kv12);</span> | 
|  | <span class="source-line-no">4036</span><span id="line-4036">    expected.add(kv23);</span> | 
|  | <span class="source-line-no">4037</span><span id="line-4037">    expected.add(kv22);</span> | 
|  | <span class="source-line-no">4038</span><span id="line-4038"></span> | 
|  | <span class="source-line-no">4039</span><span id="line-4039">    Scan scan = new Scan().withStartRow(row1);</span> | 
|  | <span class="source-line-no">4040</span><span id="line-4040">    scan.addFamily(fam1);</span> | 
|  | <span class="source-line-no">4041</span><span id="line-4041">    scan.readVersions(MAX_VERSIONS);</span> | 
|  | <span class="source-line-no">4042</span><span id="line-4042">    List<Cell> actual = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4043</span><span id="line-4043">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4044</span><span id="line-4044">      boolean hasNext = scanner.next(actual);</span> | 
|  | <span class="source-line-no">4045</span><span id="line-4045">      assertEquals(false, hasNext);</span> | 
|  | <span class="source-line-no">4046</span><span id="line-4046"></span> | 
|  | <span class="source-line-no">4047</span><span id="line-4047">      // Verify result</span> | 
|  | <span class="source-line-no">4048</span><span id="line-4048">      for (int i = 0; i < expected.size(); i++) {</span> | 
|  | <span class="source-line-no">4049</span><span id="line-4049">        assertEquals(expected.get(i), actual.get(i));</span> | 
|  | <span class="source-line-no">4050</span><span id="line-4050">      }</span> | 
|  | <span class="source-line-no">4051</span><span id="line-4051">    }</span> | 
|  | <span class="source-line-no">4052</span><span id="line-4052">  }</span> | 
|  | <span class="source-line-no">4053</span><span id="line-4053"></span> | 
|  | <span class="source-line-no">4054</span><span id="line-4054">  @Test</span> | 
|  | <span class="source-line-no">4055</span><span id="line-4055">  public void testScanner_Wildcard_FromFilesOnly_EnforceVersions() throws IOException {</span> | 
|  | <span class="source-line-no">4056</span><span id="line-4056">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">4057</span><span id="line-4057">    byte[] qf1 = Bytes.toBytes("qualifier1");</span> | 
|  | <span class="source-line-no">4058</span><span id="line-4058">    byte[] qf2 = Bytes.toBytes("qualifier2");</span> | 
|  | <span class="source-line-no">4059</span><span id="line-4059">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">4060</span><span id="line-4060"></span> | 
|  | <span class="source-line-no">4061</span><span id="line-4061">    long ts1 = 1;</span> | 
|  | <span class="source-line-no">4062</span><span id="line-4062">    long ts2 = ts1 + 1;</span> | 
|  | <span class="source-line-no">4063</span><span id="line-4063">    long ts3 = ts1 + 2;</span> | 
|  | <span class="source-line-no">4064</span><span id="line-4064"></span> | 
|  | <span class="source-line-no">4065</span><span id="line-4065">    // Setting up region</span> | 
|  | <span class="source-line-no">4066</span><span id="line-4066">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">4067</span><span id="line-4067">    // Putting data in Region</span> | 
|  | <span class="source-line-no">4068</span><span id="line-4068">    Put put = null;</span> | 
|  | <span class="source-line-no">4069</span><span id="line-4069">    KeyValue kv13 = new KeyValue(row1, fam1, qf1, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4070</span><span id="line-4070">    KeyValue kv12 = new KeyValue(row1, fam1, qf1, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4071</span><span id="line-4071">    KeyValue kv11 = new KeyValue(row1, fam1, qf1, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4072</span><span id="line-4072"></span> | 
|  | <span class="source-line-no">4073</span><span id="line-4073">    KeyValue kv23 = new KeyValue(row1, fam1, qf2, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4074</span><span id="line-4074">    KeyValue kv22 = new KeyValue(row1, fam1, qf2, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4075</span><span id="line-4075">    KeyValue kv21 = new KeyValue(row1, fam1, qf2, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4076</span><span id="line-4076"></span> | 
|  | <span class="source-line-no">4077</span><span id="line-4077">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">4078</span><span id="line-4078">    put.add(kv13);</span> | 
|  | <span class="source-line-no">4079</span><span id="line-4079">    put.add(kv12);</span> | 
|  | <span class="source-line-no">4080</span><span id="line-4080">    put.add(kv11);</span> | 
|  | <span class="source-line-no">4081</span><span id="line-4081">    put.add(kv23);</span> | 
|  | <span class="source-line-no">4082</span><span id="line-4082">    put.add(kv22);</span> | 
|  | <span class="source-line-no">4083</span><span id="line-4083">    put.add(kv21);</span> | 
|  | <span class="source-line-no">4084</span><span id="line-4084">    region.put(put);</span> | 
|  | <span class="source-line-no">4085</span><span id="line-4085">    region.flush(true);</span> | 
|  | <span class="source-line-no">4086</span><span id="line-4086"></span> | 
|  | <span class="source-line-no">4087</span><span id="line-4087">    // Expected</span> | 
|  | <span class="source-line-no">4088</span><span id="line-4088">    List<ExtendedCell> expected = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4089</span><span id="line-4089">    expected.add(kv13);</span> | 
|  | <span class="source-line-no">4090</span><span id="line-4090">    expected.add(kv12);</span> | 
|  | <span class="source-line-no">4091</span><span id="line-4091">    expected.add(kv23);</span> | 
|  | <span class="source-line-no">4092</span><span id="line-4092">    expected.add(kv22);</span> | 
|  | <span class="source-line-no">4093</span><span id="line-4093"></span> | 
|  | <span class="source-line-no">4094</span><span id="line-4094">    Scan scan = new Scan().withStartRow(row1);</span> | 
|  | <span class="source-line-no">4095</span><span id="line-4095">    scan.addFamily(fam1);</span> | 
|  | <span class="source-line-no">4096</span><span id="line-4096">    scan.readVersions(MAX_VERSIONS);</span> | 
|  | <span class="source-line-no">4097</span><span id="line-4097">    List<ExtendedCell> actual = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4098</span><span id="line-4098">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4099</span><span id="line-4099">      boolean hasNext = scanner.next(actual);</span> | 
|  | <span class="source-line-no">4100</span><span id="line-4100">      assertEquals(false, hasNext);</span> | 
|  | <span class="source-line-no">4101</span><span id="line-4101"></span> | 
|  | <span class="source-line-no">4102</span><span id="line-4102">      // Verify result</span> | 
|  | <span class="source-line-no">4103</span><span id="line-4103">      for (int i = 0; i < expected.size(); i++) {</span> | 
|  | <span class="source-line-no">4104</span><span id="line-4104">        assertTrue(PrivateCellUtil.equalsIgnoreMvccVersion(expected.get(i), actual.get(i)));</span> | 
|  | <span class="source-line-no">4105</span><span id="line-4105">      }</span> | 
|  | <span class="source-line-no">4106</span><span id="line-4106">    }</span> | 
|  | <span class="source-line-no">4107</span><span id="line-4107">  }</span> | 
|  | <span class="source-line-no">4108</span><span id="line-4108"></span> | 
|  | <span class="source-line-no">4109</span><span id="line-4109">  @Test</span> | 
|  | <span class="source-line-no">4110</span><span id="line-4110">  public void testScanner_StopRow1542() throws IOException {</span> | 
|  | <span class="source-line-no">4111</span><span id="line-4111">    byte[] family = Bytes.toBytes("testFamily");</span> | 
|  | <span class="source-line-no">4112</span><span id="line-4112">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">4113</span><span id="line-4113">    byte[] row1 = Bytes.toBytes("row111");</span> | 
|  | <span class="source-line-no">4114</span><span id="line-4114">    byte[] row2 = Bytes.toBytes("row222");</span> | 
|  | <span class="source-line-no">4115</span><span id="line-4115">    byte[] row3 = Bytes.toBytes("row333");</span> | 
|  | <span class="source-line-no">4116</span><span id="line-4116">    byte[] row4 = Bytes.toBytes("row444");</span> | 
|  | <span class="source-line-no">4117</span><span id="line-4117">    byte[] row5 = Bytes.toBytes("row555");</span> | 
|  | <span class="source-line-no">4118</span><span id="line-4118"></span> | 
|  | <span class="source-line-no">4119</span><span id="line-4119">    byte[] col1 = Bytes.toBytes("Pub111");</span> | 
|  | <span class="source-line-no">4120</span><span id="line-4120">    byte[] col2 = Bytes.toBytes("Pub222");</span> | 
|  | <span class="source-line-no">4121</span><span id="line-4121"></span> | 
|  | <span class="source-line-no">4122</span><span id="line-4122">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">4123</span><span id="line-4123">    put.addColumn(family, col1, Bytes.toBytes(10L));</span> | 
|  | <span class="source-line-no">4124</span><span id="line-4124">    region.put(put);</span> | 
|  | <span class="source-line-no">4125</span><span id="line-4125"></span> | 
|  | <span class="source-line-no">4126</span><span id="line-4126">    put = new Put(row2);</span> | 
|  | <span class="source-line-no">4127</span><span id="line-4127">    put.addColumn(family, col1, Bytes.toBytes(15L));</span> | 
|  | <span class="source-line-no">4128</span><span id="line-4128">    region.put(put);</span> | 
|  | <span class="source-line-no">4129</span><span id="line-4129"></span> | 
|  | <span class="source-line-no">4130</span><span id="line-4130">    put = new Put(row3);</span> | 
|  | <span class="source-line-no">4131</span><span id="line-4131">    put.addColumn(family, col2, Bytes.toBytes(20L));</span> | 
|  | <span class="source-line-no">4132</span><span id="line-4132">    region.put(put);</span> | 
|  | <span class="source-line-no">4133</span><span id="line-4133"></span> | 
|  | <span class="source-line-no">4134</span><span id="line-4134">    put = new Put(row4);</span> | 
|  | <span class="source-line-no">4135</span><span id="line-4135">    put.addColumn(family, col2, Bytes.toBytes(30L));</span> | 
|  | <span class="source-line-no">4136</span><span id="line-4136">    region.put(put);</span> | 
|  | <span class="source-line-no">4137</span><span id="line-4137"></span> | 
|  | <span class="source-line-no">4138</span><span id="line-4138">    put = new Put(row5);</span> | 
|  | <span class="source-line-no">4139</span><span id="line-4139">    put.addColumn(family, col1, Bytes.toBytes(40L));</span> | 
|  | <span class="source-line-no">4140</span><span id="line-4140">    region.put(put);</span> | 
|  | <span class="source-line-no">4141</span><span id="line-4141"></span> | 
|  | <span class="source-line-no">4142</span><span id="line-4142">    Scan scan = new Scan().withStartRow(row3).withStopRow(row4);</span> | 
|  | <span class="source-line-no">4143</span><span id="line-4143">    scan.readAllVersions();</span> | 
|  | <span class="source-line-no">4144</span><span id="line-4144">    scan.addColumn(family, col1);</span> | 
|  | <span class="source-line-no">4145</span><span id="line-4145">    try (InternalScanner s = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4146</span><span id="line-4146">      List<Cell> results = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4147</span><span id="line-4147">      assertEquals(false, s.next(results));</span> | 
|  | <span class="source-line-no">4148</span><span id="line-4148">      assertEquals(0, results.size());</span> | 
|  | <span class="source-line-no">4149</span><span id="line-4149">    }</span> | 
|  | <span class="source-line-no">4150</span><span id="line-4150">  }</span> | 
|  | <span class="source-line-no">4151</span><span id="line-4151"></span> | 
|  | <span class="source-line-no">4152</span><span id="line-4152">  @Test</span> | 
|  | <span class="source-line-no">4153</span><span id="line-4153">  public void testScanner_Wildcard_FromMemStoreAndFiles_EnforceVersions() throws IOException {</span> | 
|  | <span class="source-line-no">4154</span><span id="line-4154">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">4155</span><span id="line-4155">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">4156</span><span id="line-4156">    byte[] qf1 = Bytes.toBytes("qualifier1");</span> | 
|  | <span class="source-line-no">4157</span><span id="line-4157">    byte[] qf2 = Bytes.toBytes("quateslifier2");</span> | 
|  | <span class="source-line-no">4158</span><span id="line-4158"></span> | 
|  | <span class="source-line-no">4159</span><span id="line-4159">    long ts1 = 1;</span> | 
|  | <span class="source-line-no">4160</span><span id="line-4160">    long ts2 = ts1 + 1;</span> | 
|  | <span class="source-line-no">4161</span><span id="line-4161">    long ts3 = ts1 + 2;</span> | 
|  | <span class="source-line-no">4162</span><span id="line-4162">    long ts4 = ts1 + 3;</span> | 
|  | <span class="source-line-no">4163</span><span id="line-4163"></span> | 
|  | <span class="source-line-no">4164</span><span id="line-4164">    // Setting up region</span> | 
|  | <span class="source-line-no">4165</span><span id="line-4165">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">4166</span><span id="line-4166">    // Putting data in Region</span> | 
|  | <span class="source-line-no">4167</span><span id="line-4167">    KeyValue kv14 = new KeyValue(row1, fam1, qf1, ts4, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4168</span><span id="line-4168">    KeyValue kv13 = new KeyValue(row1, fam1, qf1, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4169</span><span id="line-4169">    KeyValue kv12 = new KeyValue(row1, fam1, qf1, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4170</span><span id="line-4170">    KeyValue kv11 = new KeyValue(row1, fam1, qf1, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4171</span><span id="line-4171"></span> | 
|  | <span class="source-line-no">4172</span><span id="line-4172">    KeyValue kv24 = new KeyValue(row1, fam1, qf2, ts4, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4173</span><span id="line-4173">    KeyValue kv23 = new KeyValue(row1, fam1, qf2, ts3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4174</span><span id="line-4174">    KeyValue kv22 = new KeyValue(row1, fam1, qf2, ts2, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4175</span><span id="line-4175">    KeyValue kv21 = new KeyValue(row1, fam1, qf2, ts1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">4176</span><span id="line-4176"></span> | 
|  | <span class="source-line-no">4177</span><span id="line-4177">    Put put = null;</span> | 
|  | <span class="source-line-no">4178</span><span id="line-4178">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">4179</span><span id="line-4179">    put.add(kv14);</span> | 
|  | <span class="source-line-no">4180</span><span id="line-4180">    put.add(kv24);</span> | 
|  | <span class="source-line-no">4181</span><span id="line-4181">    region.put(put);</span> | 
|  | <span class="source-line-no">4182</span><span id="line-4182">    region.flush(true);</span> | 
|  | <span class="source-line-no">4183</span><span id="line-4183"></span> | 
|  | <span class="source-line-no">4184</span><span id="line-4184">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">4185</span><span id="line-4185">    put.add(kv23);</span> | 
|  | <span class="source-line-no">4186</span><span id="line-4186">    put.add(kv13);</span> | 
|  | <span class="source-line-no">4187</span><span id="line-4187">    region.put(put);</span> | 
|  | <span class="source-line-no">4188</span><span id="line-4188">    region.flush(true);</span> | 
|  | <span class="source-line-no">4189</span><span id="line-4189"></span> | 
|  | <span class="source-line-no">4190</span><span id="line-4190">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">4191</span><span id="line-4191">    put.add(kv22);</span> | 
|  | <span class="source-line-no">4192</span><span id="line-4192">    put.add(kv12);</span> | 
|  | <span class="source-line-no">4193</span><span id="line-4193">    region.put(put);</span> | 
|  | <span class="source-line-no">4194</span><span id="line-4194">    region.flush(true);</span> | 
|  | <span class="source-line-no">4195</span><span id="line-4195"></span> | 
|  | <span class="source-line-no">4196</span><span id="line-4196">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">4197</span><span id="line-4197">    put.add(kv21);</span> | 
|  | <span class="source-line-no">4198</span><span id="line-4198">    put.add(kv11);</span> | 
|  | <span class="source-line-no">4199</span><span id="line-4199">    region.put(put);</span> | 
|  | <span class="source-line-no">4200</span><span id="line-4200"></span> | 
|  | <span class="source-line-no">4201</span><span id="line-4201">    // Expected</span> | 
|  | <span class="source-line-no">4202</span><span id="line-4202">    List<KeyValue> expected = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4203</span><span id="line-4203">    expected.add(kv14);</span> | 
|  | <span class="source-line-no">4204</span><span id="line-4204">    expected.add(kv13);</span> | 
|  | <span class="source-line-no">4205</span><span id="line-4205">    expected.add(kv12);</span> | 
|  | <span class="source-line-no">4206</span><span id="line-4206">    expected.add(kv24);</span> | 
|  | <span class="source-line-no">4207</span><span id="line-4207">    expected.add(kv23);</span> | 
|  | <span class="source-line-no">4208</span><span id="line-4208">    expected.add(kv22);</span> | 
|  | <span class="source-line-no">4209</span><span id="line-4209"></span> | 
|  | <span class="source-line-no">4210</span><span id="line-4210">    Scan scan = new Scan().withStartRow(row1);</span> | 
|  | <span class="source-line-no">4211</span><span id="line-4211">    int versions = 3;</span> | 
|  | <span class="source-line-no">4212</span><span id="line-4212">    scan.readVersions(versions);</span> | 
|  | <span class="source-line-no">4213</span><span id="line-4213">    List<ExtendedCell> actual = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4214</span><span id="line-4214">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4215</span><span id="line-4215">      boolean hasNext = scanner.next(actual);</span> | 
|  | <span class="source-line-no">4216</span><span id="line-4216">      assertEquals(false, hasNext);</span> | 
|  | <span class="source-line-no">4217</span><span id="line-4217"></span> | 
|  | <span class="source-line-no">4218</span><span id="line-4218">      // Verify result</span> | 
|  | <span class="source-line-no">4219</span><span id="line-4219">      for (int i = 0; i < expected.size(); i++) {</span> | 
|  | <span class="source-line-no">4220</span><span id="line-4220">        assertTrue(PrivateCellUtil.equalsIgnoreMvccVersion(expected.get(i), actual.get(i)));</span> | 
|  | <span class="source-line-no">4221</span><span id="line-4221">      }</span> | 
|  | <span class="source-line-no">4222</span><span id="line-4222">    }</span> | 
|  | <span class="source-line-no">4223</span><span id="line-4223">  }</span> | 
|  | <span class="source-line-no">4224</span><span id="line-4224"></span> | 
|  | <span class="source-line-no">4225</span><span id="line-4225">  /**</span> | 
|  | <span class="source-line-no">4226</span><span id="line-4226">   * Added for HBASE-5416 Here we test scan optimization when only subset of CFs are used in filter</span> | 
|  | <span class="source-line-no">4227</span><span id="line-4227">   * conditions.</span> | 
|  | <span class="source-line-no">4228</span><span id="line-4228">   */</span> | 
|  | <span class="source-line-no">4229</span><span id="line-4229">  @Test</span> | 
|  | <span class="source-line-no">4230</span><span id="line-4230">  public void testScanner_JoinedScanners() throws IOException {</span> | 
|  | <span class="source-line-no">4231</span><span id="line-4231">    byte[] cf_essential = Bytes.toBytes("essential");</span> | 
|  | <span class="source-line-no">4232</span><span id="line-4232">    byte[] cf_joined = Bytes.toBytes("joined");</span> | 
|  | <span class="source-line-no">4233</span><span id="line-4233">    byte[] cf_alpha = Bytes.toBytes("alpha");</span> | 
|  | <span class="source-line-no">4234</span><span id="line-4234">    this.region = initHRegion(tableName, method, CONF, cf_essential, cf_joined, cf_alpha);</span> | 
|  | <span class="source-line-no">4235</span><span id="line-4235">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">4236</span><span id="line-4236">    byte[] row2 = Bytes.toBytes("row2");</span> | 
|  | <span class="source-line-no">4237</span><span id="line-4237">    byte[] row3 = Bytes.toBytes("row3");</span> | 
|  | <span class="source-line-no">4238</span><span id="line-4238"></span> | 
|  | <span class="source-line-no">4239</span><span id="line-4239">    byte[] col_normal = Bytes.toBytes("d");</span> | 
|  | <span class="source-line-no">4240</span><span id="line-4240">    byte[] col_alpha = Bytes.toBytes("a");</span> | 
|  | <span class="source-line-no">4241</span><span id="line-4241"></span> | 
|  | <span class="source-line-no">4242</span><span id="line-4242">    byte[] filtered_val = Bytes.toBytes(3);</span> | 
|  | <span class="source-line-no">4243</span><span id="line-4243"></span> | 
|  | <span class="source-line-no">4244</span><span id="line-4244">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">4245</span><span id="line-4245">    put.addColumn(cf_essential, col_normal, Bytes.toBytes(1));</span> | 
|  | <span class="source-line-no">4246</span><span id="line-4246">    put.addColumn(cf_joined, col_alpha, Bytes.toBytes(1));</span> | 
|  | <span class="source-line-no">4247</span><span id="line-4247">    region.put(put);</span> | 
|  | <span class="source-line-no">4248</span><span id="line-4248"></span> | 
|  | <span class="source-line-no">4249</span><span id="line-4249">    put = new Put(row2);</span> | 
|  | <span class="source-line-no">4250</span><span id="line-4250">    put.addColumn(cf_essential, col_alpha, Bytes.toBytes(2));</span> | 
|  | <span class="source-line-no">4251</span><span id="line-4251">    put.addColumn(cf_joined, col_normal, Bytes.toBytes(2));</span> | 
|  | <span class="source-line-no">4252</span><span id="line-4252">    put.addColumn(cf_alpha, col_alpha, Bytes.toBytes(2));</span> | 
|  | <span class="source-line-no">4253</span><span id="line-4253">    region.put(put);</span> | 
|  | <span class="source-line-no">4254</span><span id="line-4254"></span> | 
|  | <span class="source-line-no">4255</span><span id="line-4255">    put = new Put(row3);</span> | 
|  | <span class="source-line-no">4256</span><span id="line-4256">    put.addColumn(cf_essential, col_normal, filtered_val);</span> | 
|  | <span class="source-line-no">4257</span><span id="line-4257">    put.addColumn(cf_joined, col_normal, filtered_val);</span> | 
|  | <span class="source-line-no">4258</span><span id="line-4258">    region.put(put);</span> | 
|  | <span class="source-line-no">4259</span><span id="line-4259"></span> | 
|  | <span class="source-line-no">4260</span><span id="line-4260">    // Check two things:</span> | 
|  | <span class="source-line-no">4261</span><span id="line-4261">    // 1. result list contains expected values</span> | 
|  | <span class="source-line-no">4262</span><span id="line-4262">    // 2. result list is sorted properly</span> | 
|  | <span class="source-line-no">4263</span><span id="line-4263"></span> | 
|  | <span class="source-line-no">4264</span><span id="line-4264">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">4265</span><span id="line-4265">    Filter filter = new SingleColumnValueExcludeFilter(cf_essential, col_normal,</span> | 
|  | <span class="source-line-no">4266</span><span id="line-4266">      CompareOperator.NOT_EQUAL, filtered_val);</span> | 
|  | <span class="source-line-no">4267</span><span id="line-4267">    scan.setFilter(filter);</span> | 
|  | <span class="source-line-no">4268</span><span id="line-4268">    scan.setLoadColumnFamiliesOnDemand(true);</span> | 
|  | <span class="source-line-no">4269</span><span id="line-4269">    try (InternalScanner s = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4270</span><span id="line-4270">      List<Cell> results = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4271</span><span id="line-4271">      assertTrue(s.next(results));</span> | 
|  | <span class="source-line-no">4272</span><span id="line-4272">      assertEquals(1, results.size());</span> | 
|  | <span class="source-line-no">4273</span><span id="line-4273">      results.clear();</span> | 
|  | <span class="source-line-no">4274</span><span id="line-4274"></span> | 
|  | <span class="source-line-no">4275</span><span id="line-4275">      assertTrue(s.next(results));</span> | 
|  | <span class="source-line-no">4276</span><span id="line-4276">      assertEquals(3, results.size());</span> | 
|  | <span class="source-line-no">4277</span><span id="line-4277">      assertTrue("orderCheck", CellUtil.matchingFamily(results.get(0), cf_alpha));</span> | 
|  | <span class="source-line-no">4278</span><span id="line-4278">      assertTrue("orderCheck", CellUtil.matchingFamily(results.get(1), cf_essential));</span> | 
|  | <span class="source-line-no">4279</span><span id="line-4279">      assertTrue("orderCheck", CellUtil.matchingFamily(results.get(2), cf_joined));</span> | 
|  | <span class="source-line-no">4280</span><span id="line-4280">      results.clear();</span> | 
|  | <span class="source-line-no">4281</span><span id="line-4281"></span> | 
|  | <span class="source-line-no">4282</span><span id="line-4282">      assertFalse(s.next(results));</span> | 
|  | <span class="source-line-no">4283</span><span id="line-4283">      assertEquals(0, results.size());</span> | 
|  | <span class="source-line-no">4284</span><span id="line-4284">    }</span> | 
|  | <span class="source-line-no">4285</span><span id="line-4285">  }</span> | 
|  | <span class="source-line-no">4286</span><span id="line-4286"></span> | 
|  | <span class="source-line-no">4287</span><span id="line-4287">  /**</span> | 
|  | <span class="source-line-no">4288</span><span id="line-4288">   * HBASE-5416 Test case when scan limits amount of KVs returned on each next() call.</span> | 
|  | <span class="source-line-no">4289</span><span id="line-4289">   */</span> | 
|  | <span class="source-line-no">4290</span><span id="line-4290">  @Test</span> | 
|  | <span class="source-line-no">4291</span><span id="line-4291">  public void testScanner_JoinedScannersWithLimits() throws IOException {</span> | 
|  | <span class="source-line-no">4292</span><span id="line-4292">    final byte[] cf_first = Bytes.toBytes("first");</span> | 
|  | <span class="source-line-no">4293</span><span id="line-4293">    final byte[] cf_second = Bytes.toBytes("second");</span> | 
|  | <span class="source-line-no">4294</span><span id="line-4294"></span> | 
|  | <span class="source-line-no">4295</span><span id="line-4295">    this.region = initHRegion(tableName, method, CONF, cf_first, cf_second);</span> | 
|  | <span class="source-line-no">4296</span><span id="line-4296">    final byte[] col_a = Bytes.toBytes("a");</span> | 
|  | <span class="source-line-no">4297</span><span id="line-4297">    final byte[] col_b = Bytes.toBytes("b");</span> | 
|  | <span class="source-line-no">4298</span><span id="line-4298"></span> | 
|  | <span class="source-line-no">4299</span><span id="line-4299">    Put put;</span> | 
|  | <span class="source-line-no">4300</span><span id="line-4300"></span> | 
|  | <span class="source-line-no">4301</span><span id="line-4301">    for (int i = 0; i < 10; i++) {</span> | 
|  | <span class="source-line-no">4302</span><span id="line-4302">      put = new Put(Bytes.toBytes("r" + Integer.toString(i)));</span> | 
|  | <span class="source-line-no">4303</span><span id="line-4303">      put.addColumn(cf_first, col_a, Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">4304</span><span id="line-4304">      if (i < 5) {</span> | 
|  | <span class="source-line-no">4305</span><span id="line-4305">        put.addColumn(cf_first, col_b, Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">4306</span><span id="line-4306">        put.addColumn(cf_second, col_a, Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">4307</span><span id="line-4307">        put.addColumn(cf_second, col_b, Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">4308</span><span id="line-4308">      }</span> | 
|  | <span class="source-line-no">4309</span><span id="line-4309">      region.put(put);</span> | 
|  | <span class="source-line-no">4310</span><span id="line-4310">    }</span> | 
|  | <span class="source-line-no">4311</span><span id="line-4311"></span> | 
|  | <span class="source-line-no">4312</span><span id="line-4312">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">4313</span><span id="line-4313">    scan.setLoadColumnFamiliesOnDemand(true);</span> | 
|  | <span class="source-line-no">4314</span><span id="line-4314">    Filter bogusFilter = new FilterBase() {</span> | 
|  | <span class="source-line-no">4315</span><span id="line-4315">      @Override</span> | 
|  | <span class="source-line-no">4316</span><span id="line-4316">      public ReturnCode filterCell(final Cell ignored) throws IOException {</span> | 
|  | <span class="source-line-no">4317</span><span id="line-4317">        return ReturnCode.INCLUDE;</span> | 
|  | <span class="source-line-no">4318</span><span id="line-4318">      }</span> | 
|  | <span class="source-line-no">4319</span><span id="line-4319"></span> | 
|  | <span class="source-line-no">4320</span><span id="line-4320">      @Override</span> | 
|  | <span class="source-line-no">4321</span><span id="line-4321">      public boolean isFamilyEssential(byte[] name) {</span> | 
|  | <span class="source-line-no">4322</span><span id="line-4322">        return Bytes.equals(name, cf_first);</span> | 
|  | <span class="source-line-no">4323</span><span id="line-4323">      }</span> | 
|  | <span class="source-line-no">4324</span><span id="line-4324">    };</span> | 
|  | <span class="source-line-no">4325</span><span id="line-4325"></span> | 
|  | <span class="source-line-no">4326</span><span id="line-4326">    scan.setFilter(bogusFilter);</span> | 
|  | <span class="source-line-no">4327</span><span id="line-4327">    try (InternalScanner s = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4328</span><span id="line-4328">      // Our data looks like this:</span> | 
|  | <span class="source-line-no">4329</span><span id="line-4329">      // r0: first:a, first:b, second:a, second:b</span> | 
|  | <span class="source-line-no">4330</span><span id="line-4330">      // r1: first:a, first:b, second:a, second:b</span> | 
|  | <span class="source-line-no">4331</span><span id="line-4331">      // r2: first:a, first:b, second:a, second:b</span> | 
|  | <span class="source-line-no">4332</span><span id="line-4332">      // r3: first:a, first:b, second:a, second:b</span> | 
|  | <span class="source-line-no">4333</span><span id="line-4333">      // r4: first:a, first:b, second:a, second:b</span> | 
|  | <span class="source-line-no">4334</span><span id="line-4334">      // r5: first:a</span> | 
|  | <span class="source-line-no">4335</span><span id="line-4335">      // r6: first:a</span> | 
|  | <span class="source-line-no">4336</span><span id="line-4336">      // r7: first:a</span> | 
|  | <span class="source-line-no">4337</span><span id="line-4337">      // r8: first:a</span> | 
|  | <span class="source-line-no">4338</span><span id="line-4338">      // r9: first:a</span> | 
|  | <span class="source-line-no">4339</span><span id="line-4339"></span> | 
|  | <span class="source-line-no">4340</span><span id="line-4340">      // But due to next's limit set to 3, we should get this:</span> | 
|  | <span class="source-line-no">4341</span><span id="line-4341">      // r0: first:a, first:b, second:a</span> | 
|  | <span class="source-line-no">4342</span><span id="line-4342">      // r0: second:b</span> | 
|  | <span class="source-line-no">4343</span><span id="line-4343">      // r1: first:a, first:b, second:a</span> | 
|  | <span class="source-line-no">4344</span><span id="line-4344">      // r1: second:b</span> | 
|  | <span class="source-line-no">4345</span><span id="line-4345">      // r2: first:a, first:b, second:a</span> | 
|  | <span class="source-line-no">4346</span><span id="line-4346">      // r2: second:b</span> | 
|  | <span class="source-line-no">4347</span><span id="line-4347">      // r3: first:a, first:b, second:a</span> | 
|  | <span class="source-line-no">4348</span><span id="line-4348">      // r3: second:b</span> | 
|  | <span class="source-line-no">4349</span><span id="line-4349">      // r4: first:a, first:b, second:a</span> | 
|  | <span class="source-line-no">4350</span><span id="line-4350">      // r4: second:b</span> | 
|  | <span class="source-line-no">4351</span><span id="line-4351">      // r5: first:a</span> | 
|  | <span class="source-line-no">4352</span><span id="line-4352">      // r6: first:a</span> | 
|  | <span class="source-line-no">4353</span><span id="line-4353">      // r7: first:a</span> | 
|  | <span class="source-line-no">4354</span><span id="line-4354">      // r8: first:a</span> | 
|  | <span class="source-line-no">4355</span><span id="line-4355">      // r9: first:a</span> | 
|  | <span class="source-line-no">4356</span><span id="line-4356"></span> | 
|  | <span class="source-line-no">4357</span><span id="line-4357">      List<Cell> results = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4358</span><span id="line-4358">      int index = 0;</span> | 
|  | <span class="source-line-no">4359</span><span id="line-4359">      ScannerContext scannerContext = ScannerContext.newBuilder().setBatchLimit(3).build();</span> | 
|  | <span class="source-line-no">4360</span><span id="line-4360">      while (true) {</span> | 
|  | <span class="source-line-no">4361</span><span id="line-4361">        boolean more = s.next(results, scannerContext);</span> | 
|  | <span class="source-line-no">4362</span><span id="line-4362">        if ((index >> 1) < 5) {</span> | 
|  | <span class="source-line-no">4363</span><span id="line-4363">          if (index % 2 == 0) {</span> | 
|  | <span class="source-line-no">4364</span><span id="line-4364">            assertEquals(3, results.size());</span> | 
|  | <span class="source-line-no">4365</span><span id="line-4365">          } else {</span> | 
|  | <span class="source-line-no">4366</span><span id="line-4366">            assertEquals(1, results.size());</span> | 
|  | <span class="source-line-no">4367</span><span id="line-4367">          }</span> | 
|  | <span class="source-line-no">4368</span><span id="line-4368">        } else {</span> | 
|  | <span class="source-line-no">4369</span><span id="line-4369">          assertEquals(1, results.size());</span> | 
|  | <span class="source-line-no">4370</span><span id="line-4370">        }</span> | 
|  | <span class="source-line-no">4371</span><span id="line-4371">        results.clear();</span> | 
|  | <span class="source-line-no">4372</span><span id="line-4372">        index++;</span> | 
|  | <span class="source-line-no">4373</span><span id="line-4373">        if (!more) {</span> | 
|  | <span class="source-line-no">4374</span><span id="line-4374">          break;</span> | 
|  | <span class="source-line-no">4375</span><span id="line-4375">        }</span> | 
|  | <span class="source-line-no">4376</span><span id="line-4376">      }</span> | 
|  | <span class="source-line-no">4377</span><span id="line-4377">    }</span> | 
|  | <span class="source-line-no">4378</span><span id="line-4378">  }</span> | 
|  | <span class="source-line-no">4379</span><span id="line-4379"></span> | 
|  | <span class="source-line-no">4380</span><span id="line-4380">  @Test</span> | 
|  | <span class="source-line-no">4381</span><span id="line-4381">  public void testScannerOperationId() throws IOException {</span> | 
|  | <span class="source-line-no">4382</span><span id="line-4382">    region = initHRegion(tableName, method, CONF, COLUMN_FAMILY_BYTES);</span> | 
|  | <span class="source-line-no">4383</span><span id="line-4383">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">4384</span><span id="line-4384">    try (RegionScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4385</span><span id="line-4385">      assertNull(scanner.getOperationId());</span> | 
|  | <span class="source-line-no">4386</span><span id="line-4386">    }</span> | 
|  | <span class="source-line-no">4387</span><span id="line-4387"></span> | 
|  | <span class="source-line-no">4388</span><span id="line-4388">    String operationId = "test_operation_id_0101";</span> | 
|  | <span class="source-line-no">4389</span><span id="line-4389">    scan = new Scan().setId(operationId);</span> | 
|  | <span class="source-line-no">4390</span><span id="line-4390">    try (RegionScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4391</span><span id="line-4391">      assertEquals(operationId, scanner.getOperationId());</span> | 
|  | <span class="source-line-no">4392</span><span id="line-4392">    }</span> | 
|  | <span class="source-line-no">4393</span><span id="line-4393"></span> | 
|  | <span class="source-line-no">4394</span><span id="line-4394">    HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">4395</span><span id="line-4395">  }</span> | 
|  | <span class="source-line-no">4396</span><span id="line-4396"></span> | 
|  | <span class="source-line-no">4397</span><span id="line-4397">  /**</span> | 
|  | <span class="source-line-no">4398</span><span id="line-4398">   * Write an HFile block full with Cells whose qualifier that are identical between 0 and</span> | 
|  | <span class="source-line-no">4399</span><span id="line-4399">   * Short.MAX_VALUE. See HBASE-13329.</span> | 
|  | <span class="source-line-no">4400</span><span id="line-4400">   */</span> | 
|  | <span class="source-line-no">4401</span><span id="line-4401">  @Test</span> | 
|  | <span class="source-line-no">4402</span><span id="line-4402">  public void testLongQualifier() throws Exception {</span> | 
|  | <span class="source-line-no">4403</span><span id="line-4403">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">4404</span><span id="line-4404">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">4405</span><span id="line-4405">    byte[] q = new byte[Short.MAX_VALUE + 2];</span> | 
|  | <span class="source-line-no">4406</span><span id="line-4406">    Arrays.fill(q, 0, q.length - 1, (byte) 42);</span> | 
|  | <span class="source-line-no">4407</span><span id="line-4407">    for (byte i = 0; i < 10; i++) {</span> | 
|  | <span class="source-line-no">4408</span><span id="line-4408">      Put p = new Put(Bytes.toBytes("row"));</span> | 
|  | <span class="source-line-no">4409</span><span id="line-4409">      // qualifiers that differ past Short.MAX_VALUE</span> | 
|  | <span class="source-line-no">4410</span><span id="line-4410">      q[q.length - 1] = i;</span> | 
|  | <span class="source-line-no">4411</span><span id="line-4411">      p.addColumn(family, q, q);</span> | 
|  | <span class="source-line-no">4412</span><span id="line-4412">      region.put(p);</span> | 
|  | <span class="source-line-no">4413</span><span id="line-4413">    }</span> | 
|  | <span class="source-line-no">4414</span><span id="line-4414">    region.flush(false);</span> | 
|  | <span class="source-line-no">4415</span><span id="line-4415">  }</span> | 
|  | <span class="source-line-no">4416</span><span id="line-4416"></span> | 
|  | <span class="source-line-no">4417</span><span id="line-4417">  /**</span> | 
|  | <span class="source-line-no">4418</span><span id="line-4418">   * Flushes the cache in a thread while scanning. The tests verify that the scan is coherent - e.g.</span> | 
|  | <span class="source-line-no">4419</span><span id="line-4419">   * the returned results are always of the same or later update as the previous results. scan /</span> | 
|  | <span class="source-line-no">4420</span><span id="line-4420">   * compact thread join</span> | 
|  | <span class="source-line-no">4421</span><span id="line-4421">   */</span> | 
|  | <span class="source-line-no">4422</span><span id="line-4422">  @Test</span> | 
|  | <span class="source-line-no">4423</span><span id="line-4423">  public void testFlushCacheWhileScanning() throws IOException, InterruptedException {</span> | 
|  | <span class="source-line-no">4424</span><span id="line-4424">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">4425</span><span id="line-4425">    int numRows = 1000;</span> | 
|  | <span class="source-line-no">4426</span><span id="line-4426">    int flushAndScanInterval = 10;</span> | 
|  | <span class="source-line-no">4427</span><span id="line-4427">    int compactInterval = 10 * flushAndScanInterval;</span> | 
|  | <span class="source-line-no">4428</span><span id="line-4428"></span> | 
|  | <span class="source-line-no">4429</span><span id="line-4429">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">4430</span><span id="line-4430">    FlushThread flushThread = new FlushThread();</span> | 
|  | <span class="source-line-no">4431</span><span id="line-4431">    try {</span> | 
|  | <span class="source-line-no">4432</span><span id="line-4432">      flushThread.start();</span> | 
|  | <span class="source-line-no">4433</span><span id="line-4433"></span> | 
|  | <span class="source-line-no">4434</span><span id="line-4434">      Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">4435</span><span id="line-4435">      scan.addFamily(family);</span> | 
|  | <span class="source-line-no">4436</span><span id="line-4436">      scan.setFilter(new SingleColumnValueFilter(family, qual1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">4437</span><span id="line-4437">        new BinaryComparator(Bytes.toBytes(5L))));</span> | 
|  | <span class="source-line-no">4438</span><span id="line-4438"></span> | 
|  | <span class="source-line-no">4439</span><span id="line-4439">      int expectedCount = 0;</span> | 
|  | <span class="source-line-no">4440</span><span id="line-4440">      List<Cell> res = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4441</span><span id="line-4441"></span> | 
|  | <span class="source-line-no">4442</span><span id="line-4442">      boolean toggle = true;</span> | 
|  | <span class="source-line-no">4443</span><span id="line-4443">      for (long i = 0; i < numRows; i++) {</span> | 
|  | <span class="source-line-no">4444</span><span id="line-4444">        Put put = new Put(Bytes.toBytes(i));</span> | 
|  | <span class="source-line-no">4445</span><span id="line-4445">        put.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">4446</span><span id="line-4446">        put.addColumn(family, qual1, Bytes.toBytes(i % 10));</span> | 
|  | <span class="source-line-no">4447</span><span id="line-4447">        region.put(put);</span> | 
|  | <span class="source-line-no">4448</span><span id="line-4448"></span> | 
|  | <span class="source-line-no">4449</span><span id="line-4449">        if (i != 0 && i % compactInterval == 0) {</span> | 
|  | <span class="source-line-no">4450</span><span id="line-4450">          LOG.debug("iteration = " + i + " ts=" + EnvironmentEdgeManager.currentTime());</span> | 
|  | <span class="source-line-no">4451</span><span id="line-4451">          region.compact(true);</span> | 
|  | <span class="source-line-no">4452</span><span id="line-4452">        }</span> | 
|  | <span class="source-line-no">4453</span><span id="line-4453"></span> | 
|  | <span class="source-line-no">4454</span><span id="line-4454">        if (i % 10 == 5L) {</span> | 
|  | <span class="source-line-no">4455</span><span id="line-4455">          expectedCount++;</span> | 
|  | <span class="source-line-no">4456</span><span id="line-4456">        }</span> | 
|  | <span class="source-line-no">4457</span><span id="line-4457"></span> | 
|  | <span class="source-line-no">4458</span><span id="line-4458">        if (i != 0 && i % flushAndScanInterval == 0) {</span> | 
|  | <span class="source-line-no">4459</span><span id="line-4459">          res.clear();</span> | 
|  | <span class="source-line-no">4460</span><span id="line-4460">          try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4461</span><span id="line-4461">            if (toggle) {</span> | 
|  | <span class="source-line-no">4462</span><span id="line-4462">              flushThread.flush();</span> | 
|  | <span class="source-line-no">4463</span><span id="line-4463">            }</span> | 
|  | <span class="source-line-no">4464</span><span id="line-4464">            while (scanner.next(res)) {</span> | 
|  | <span class="source-line-no">4465</span><span id="line-4465">              // ignore</span> | 
|  | <span class="source-line-no">4466</span><span id="line-4466">            }</span> | 
|  | <span class="source-line-no">4467</span><span id="line-4467">          }</span> | 
|  | <span class="source-line-no">4468</span><span id="line-4468">          if (!toggle) {</span> | 
|  | <span class="source-line-no">4469</span><span id="line-4469">            flushThread.flush();</span> | 
|  | <span class="source-line-no">4470</span><span id="line-4470">          }</span> | 
|  | <span class="source-line-no">4471</span><span id="line-4471">          assertEquals(</span> | 
|  | <span class="source-line-no">4472</span><span id="line-4472">            "toggle=" + toggle + "i=" + i + " ts=" + EnvironmentEdgeManager.currentTime(),</span> | 
|  | <span class="source-line-no">4473</span><span id="line-4473">            expectedCount, res.size());</span> | 
|  | <span class="source-line-no">4474</span><span id="line-4474">          toggle = !toggle;</span> | 
|  | <span class="source-line-no">4475</span><span id="line-4475">        }</span> | 
|  | <span class="source-line-no">4476</span><span id="line-4476">      }</span> | 
|  | <span class="source-line-no">4477</span><span id="line-4477"></span> | 
|  | <span class="source-line-no">4478</span><span id="line-4478">    } finally {</span> | 
|  | <span class="source-line-no">4479</span><span id="line-4479">      try {</span> | 
|  | <span class="source-line-no">4480</span><span id="line-4480">        flushThread.done();</span> | 
|  | <span class="source-line-no">4481</span><span id="line-4481">        flushThread.join();</span> | 
|  | <span class="source-line-no">4482</span><span id="line-4482">        flushThread.checkNoError();</span> | 
|  | <span class="source-line-no">4483</span><span id="line-4483">      } catch (InterruptedException ie) {</span> | 
|  | <span class="source-line-no">4484</span><span id="line-4484">        LOG.warn("Caught exception when joining with flushThread", ie);</span> | 
|  | <span class="source-line-no">4485</span><span id="line-4485">      }</span> | 
|  | <span class="source-line-no">4486</span><span id="line-4486">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">4487</span><span id="line-4487">      this.region = null;</span> | 
|  | <span class="source-line-no">4488</span><span id="line-4488">    }</span> | 
|  | <span class="source-line-no">4489</span><span id="line-4489">  }</span> | 
|  | <span class="source-line-no">4490</span><span id="line-4490"></span> | 
|  | <span class="source-line-no">4491</span><span id="line-4491">  protected class FlushThread extends Thread {</span> | 
|  | <span class="source-line-no">4492</span><span id="line-4492">    private volatile boolean done;</span> | 
|  | <span class="source-line-no">4493</span><span id="line-4493">    private Throwable error = null;</span> | 
|  | <span class="source-line-no">4494</span><span id="line-4494"></span> | 
|  | <span class="source-line-no">4495</span><span id="line-4495">    FlushThread() {</span> | 
|  | <span class="source-line-no">4496</span><span id="line-4496">      super("FlushThread");</span> | 
|  | <span class="source-line-no">4497</span><span id="line-4497">    }</span> | 
|  | <span class="source-line-no">4498</span><span id="line-4498"></span> | 
|  | <span class="source-line-no">4499</span><span id="line-4499">    public void done() {</span> | 
|  | <span class="source-line-no">4500</span><span id="line-4500">      done = true;</span> | 
|  | <span class="source-line-no">4501</span><span id="line-4501">      synchronized (this) {</span> | 
|  | <span class="source-line-no">4502</span><span id="line-4502">        interrupt();</span> | 
|  | <span class="source-line-no">4503</span><span id="line-4503">      }</span> | 
|  | <span class="source-line-no">4504</span><span id="line-4504">    }</span> | 
|  | <span class="source-line-no">4505</span><span id="line-4505"></span> | 
|  | <span class="source-line-no">4506</span><span id="line-4506">    public void checkNoError() {</span> | 
|  | <span class="source-line-no">4507</span><span id="line-4507">      if (error != null) {</span> | 
|  | <span class="source-line-no">4508</span><span id="line-4508">        assertNull(error);</span> | 
|  | <span class="source-line-no">4509</span><span id="line-4509">      }</span> | 
|  | <span class="source-line-no">4510</span><span id="line-4510">    }</span> | 
|  | <span class="source-line-no">4511</span><span id="line-4511"></span> | 
|  | <span class="source-line-no">4512</span><span id="line-4512">    @Override</span> | 
|  | <span class="source-line-no">4513</span><span id="line-4513">    public void run() {</span> | 
|  | <span class="source-line-no">4514</span><span id="line-4514">      done = false;</span> | 
|  | <span class="source-line-no">4515</span><span id="line-4515">      while (!done) {</span> | 
|  | <span class="source-line-no">4516</span><span id="line-4516">        synchronized (this) {</span> | 
|  | <span class="source-line-no">4517</span><span id="line-4517">          try {</span> | 
|  | <span class="source-line-no">4518</span><span id="line-4518">            wait();</span> | 
|  | <span class="source-line-no">4519</span><span id="line-4519">          } catch (InterruptedException ignored) {</span> | 
|  | <span class="source-line-no">4520</span><span id="line-4520">            if (done) {</span> | 
|  | <span class="source-line-no">4521</span><span id="line-4521">              break;</span> | 
|  | <span class="source-line-no">4522</span><span id="line-4522">            }</span> | 
|  | <span class="source-line-no">4523</span><span id="line-4523">          }</span> | 
|  | <span class="source-line-no">4524</span><span id="line-4524">        }</span> | 
|  | <span class="source-line-no">4525</span><span id="line-4525">        try {</span> | 
|  | <span class="source-line-no">4526</span><span id="line-4526">          region.flush(true);</span> | 
|  | <span class="source-line-no">4527</span><span id="line-4527">        } catch (IOException e) {</span> | 
|  | <span class="source-line-no">4528</span><span id="line-4528">          if (!done) {</span> | 
|  | <span class="source-line-no">4529</span><span id="line-4529">            LOG.error("Error while flushing cache", e);</span> | 
|  | <span class="source-line-no">4530</span><span id="line-4530">            error = e;</span> | 
|  | <span class="source-line-no">4531</span><span id="line-4531">          }</span> | 
|  | <span class="source-line-no">4532</span><span id="line-4532">          break;</span> | 
|  | <span class="source-line-no">4533</span><span id="line-4533">        } catch (Throwable t) {</span> | 
|  | <span class="source-line-no">4534</span><span id="line-4534">          LOG.error("Uncaught exception", t);</span> | 
|  | <span class="source-line-no">4535</span><span id="line-4535">          throw t;</span> | 
|  | <span class="source-line-no">4536</span><span id="line-4536">        }</span> | 
|  | <span class="source-line-no">4537</span><span id="line-4537">      }</span> | 
|  | <span class="source-line-no">4538</span><span id="line-4538">    }</span> | 
|  | <span class="source-line-no">4539</span><span id="line-4539"></span> | 
|  | <span class="source-line-no">4540</span><span id="line-4540">    public void flush() {</span> | 
|  | <span class="source-line-no">4541</span><span id="line-4541">      synchronized (this) {</span> | 
|  | <span class="source-line-no">4542</span><span id="line-4542">        notify();</span> | 
|  | <span class="source-line-no">4543</span><span id="line-4543">      }</span> | 
|  | <span class="source-line-no">4544</span><span id="line-4544">    }</span> | 
|  | <span class="source-line-no">4545</span><span id="line-4545">  }</span> | 
|  | <span class="source-line-no">4546</span><span id="line-4546"></span> | 
|  | <span class="source-line-no">4547</span><span id="line-4547">  /**</span> | 
|  | <span class="source-line-no">4548</span><span id="line-4548">   * So can be overridden in subclasses.</span> | 
|  | <span class="source-line-no">4549</span><span id="line-4549">   */</span> | 
|  | <span class="source-line-no">4550</span><span id="line-4550">  protected int getNumQualifiersForTestWritesWhileScanning() {</span> | 
|  | <span class="source-line-no">4551</span><span id="line-4551">    return 100;</span> | 
|  | <span class="source-line-no">4552</span><span id="line-4552">  }</span> | 
|  | <span class="source-line-no">4553</span><span id="line-4553"></span> | 
|  | <span class="source-line-no">4554</span><span id="line-4554">  /**</span> | 
|  | <span class="source-line-no">4555</span><span id="line-4555">   * So can be overridden in subclasses.</span> | 
|  | <span class="source-line-no">4556</span><span id="line-4556">   */</span> | 
|  | <span class="source-line-no">4557</span><span id="line-4557">  protected int getTestCountForTestWritesWhileScanning() {</span> | 
|  | <span class="source-line-no">4558</span><span id="line-4558">    return 100;</span> | 
|  | <span class="source-line-no">4559</span><span id="line-4559">  }</span> | 
|  | <span class="source-line-no">4560</span><span id="line-4560"></span> | 
|  | <span class="source-line-no">4561</span><span id="line-4561">  /**</span> | 
|  | <span class="source-line-no">4562</span><span id="line-4562">   * Writes very wide records and scans for the latest every time.. Flushes and compacts the region</span> | 
|  | <span class="source-line-no">4563</span><span id="line-4563">   * every now and then to keep things realistic. by flush / scan / compaction when joining threads</span> | 
|  | <span class="source-line-no">4564</span><span id="line-4564">   */</span> | 
|  | <span class="source-line-no">4565</span><span id="line-4565">  @Test</span> | 
|  | <span class="source-line-no">4566</span><span id="line-4566">  public void testWritesWhileScanning() throws IOException, InterruptedException {</span> | 
|  | <span class="source-line-no">4567</span><span id="line-4567">    int testCount = getTestCountForTestWritesWhileScanning();</span> | 
|  | <span class="source-line-no">4568</span><span id="line-4568">    int numRows = 1;</span> | 
|  | <span class="source-line-no">4569</span><span id="line-4569">    int numFamilies = 10;</span> | 
|  | <span class="source-line-no">4570</span><span id="line-4570">    int numQualifiers = getNumQualifiersForTestWritesWhileScanning();</span> | 
|  | <span class="source-line-no">4571</span><span id="line-4571">    int flushInterval = 7;</span> | 
|  | <span class="source-line-no">4572</span><span id="line-4572">    int compactInterval = 5 * flushInterval;</span> | 
|  | <span class="source-line-no">4573</span><span id="line-4573">    byte[][] families = new byte[numFamilies][];</span> | 
|  | <span class="source-line-no">4574</span><span id="line-4574">    for (int i = 0; i < numFamilies; i++) {</span> | 
|  | <span class="source-line-no">4575</span><span id="line-4575">      families[i] = Bytes.toBytes("family" + i);</span> | 
|  | <span class="source-line-no">4576</span><span id="line-4576">    }</span> | 
|  | <span class="source-line-no">4577</span><span id="line-4577">    byte[][] qualifiers = new byte[numQualifiers][];</span> | 
|  | <span class="source-line-no">4578</span><span id="line-4578">    for (int i = 0; i < numQualifiers; i++) {</span> | 
|  | <span class="source-line-no">4579</span><span id="line-4579">      qualifiers[i] = Bytes.toBytes("qual" + i);</span> | 
|  | <span class="source-line-no">4580</span><span id="line-4580">    }</span> | 
|  | <span class="source-line-no">4581</span><span id="line-4581"></span> | 
|  | <span class="source-line-no">4582</span><span id="line-4582">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">4583</span><span id="line-4583">    FlushThread flushThread = new FlushThread();</span> | 
|  | <span class="source-line-no">4584</span><span id="line-4584">    PutThread putThread = new PutThread(numRows, families, qualifiers);</span> | 
|  | <span class="source-line-no">4585</span><span id="line-4585">    try {</span> | 
|  | <span class="source-line-no">4586</span><span id="line-4586">      putThread.start();</span> | 
|  | <span class="source-line-no">4587</span><span id="line-4587">      putThread.waitForFirstPut();</span> | 
|  | <span class="source-line-no">4588</span><span id="line-4588"></span> | 
|  | <span class="source-line-no">4589</span><span id="line-4589">      flushThread.start();</span> | 
|  | <span class="source-line-no">4590</span><span id="line-4590"></span> | 
|  | <span class="source-line-no">4591</span><span id="line-4591">      Scan scan = new Scan().withStartRow(Bytes.toBytes("row0")).withStopRow(Bytes.toBytes("row1"));</span> | 
|  | <span class="source-line-no">4592</span><span id="line-4592"></span> | 
|  | <span class="source-line-no">4593</span><span id="line-4593">      int expectedCount = numFamilies * numQualifiers;</span> | 
|  | <span class="source-line-no">4594</span><span id="line-4594">      List<Cell> res = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4595</span><span id="line-4595"></span> | 
|  | <span class="source-line-no">4596</span><span id="line-4596">      long prevTimestamp = 0L;</span> | 
|  | <span class="source-line-no">4597</span><span id="line-4597">      for (int i = 0; i < testCount; i++) {</span> | 
|  | <span class="source-line-no">4598</span><span id="line-4598"></span> | 
|  | <span class="source-line-no">4599</span><span id="line-4599">        if (i != 0 && i % compactInterval == 0) {</span> | 
|  | <span class="source-line-no">4600</span><span id="line-4600">          region.compact(true);</span> | 
|  | <span class="source-line-no">4601</span><span id="line-4601">          for (HStore store : region.getStores()) {</span> | 
|  | <span class="source-line-no">4602</span><span id="line-4602">            store.closeAndArchiveCompactedFiles();</span> | 
|  | <span class="source-line-no">4603</span><span id="line-4603">          }</span> | 
|  | <span class="source-line-no">4604</span><span id="line-4604">        }</span> | 
|  | <span class="source-line-no">4605</span><span id="line-4605"></span> | 
|  | <span class="source-line-no">4606</span><span id="line-4606">        if (i != 0 && i % flushInterval == 0) {</span> | 
|  | <span class="source-line-no">4607</span><span id="line-4607">          flushThread.flush();</span> | 
|  | <span class="source-line-no">4608</span><span id="line-4608">        }</span> | 
|  | <span class="source-line-no">4609</span><span id="line-4609"></span> | 
|  | <span class="source-line-no">4610</span><span id="line-4610">        boolean previousEmpty = res.isEmpty();</span> | 
|  | <span class="source-line-no">4611</span><span id="line-4611">        res.clear();</span> | 
|  | <span class="source-line-no">4612</span><span id="line-4612">        try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">4613</span><span id="line-4613">          boolean moreRows;</span> | 
|  | <span class="source-line-no">4614</span><span id="line-4614">          do {</span> | 
|  | <span class="source-line-no">4615</span><span id="line-4615">            moreRows = scanner.next(res);</span> | 
|  | <span class="source-line-no">4616</span><span id="line-4616">          } while (moreRows);</span> | 
|  | <span class="source-line-no">4617</span><span id="line-4617">        }</span> | 
|  | <span class="source-line-no">4618</span><span id="line-4618">        if (!res.isEmpty() || !previousEmpty || i > compactInterval) {</span> | 
|  | <span class="source-line-no">4619</span><span id="line-4619">          assertEquals("i=" + i, expectedCount, res.size());</span> | 
|  | <span class="source-line-no">4620</span><span id="line-4620">          long timestamp = res.get(0).getTimestamp();</span> | 
|  | <span class="source-line-no">4621</span><span id="line-4621">          assertTrue("Timestamps were broke: " + timestamp + " prev: " + prevTimestamp,</span> | 
|  | <span class="source-line-no">4622</span><span id="line-4622">            timestamp >= prevTimestamp);</span> | 
|  | <span class="source-line-no">4623</span><span id="line-4623">          prevTimestamp = timestamp;</span> | 
|  | <span class="source-line-no">4624</span><span id="line-4624">        }</span> | 
|  | <span class="source-line-no">4625</span><span id="line-4625">      }</span> | 
|  | <span class="source-line-no">4626</span><span id="line-4626"></span> | 
|  | <span class="source-line-no">4627</span><span id="line-4627">      putThread.done();</span> | 
|  | <span class="source-line-no">4628</span><span id="line-4628"></span> | 
|  | <span class="source-line-no">4629</span><span id="line-4629">      region.flush(true);</span> | 
|  | <span class="source-line-no">4630</span><span id="line-4630"></span> | 
|  | <span class="source-line-no">4631</span><span id="line-4631">    } finally {</span> | 
|  | <span class="source-line-no">4632</span><span id="line-4632">      try {</span> | 
|  | <span class="source-line-no">4633</span><span id="line-4633">        flushThread.done();</span> | 
|  | <span class="source-line-no">4634</span><span id="line-4634">        flushThread.join();</span> | 
|  | <span class="source-line-no">4635</span><span id="line-4635">        flushThread.checkNoError();</span> | 
|  | <span class="source-line-no">4636</span><span id="line-4636"></span> | 
|  | <span class="source-line-no">4637</span><span id="line-4637">        putThread.join();</span> | 
|  | <span class="source-line-no">4638</span><span id="line-4638">        putThread.checkNoError();</span> | 
|  | <span class="source-line-no">4639</span><span id="line-4639">      } catch (InterruptedException ie) {</span> | 
|  | <span class="source-line-no">4640</span><span id="line-4640">        LOG.warn("Caught exception when joining with flushThread", ie);</span> | 
|  | <span class="source-line-no">4641</span><span id="line-4641">      }</span> | 
|  | <span class="source-line-no">4642</span><span id="line-4642"></span> | 
|  | <span class="source-line-no">4643</span><span id="line-4643">      try {</span> | 
|  | <span class="source-line-no">4644</span><span id="line-4644">        HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">4645</span><span id="line-4645">      } catch (DroppedSnapshotException dse) {</span> | 
|  | <span class="source-line-no">4646</span><span id="line-4646">        // We could get this on way out because we interrupt the background flusher and it could</span> | 
|  | <span class="source-line-no">4647</span><span id="line-4647">        // fail anywhere causing a DSE over in the background flusher... only it is not properly</span> | 
|  | <span class="source-line-no">4648</span><span id="line-4648">        // dealt with so could still be memory hanging out when we get to here -- memory we can't</span> | 
|  | <span class="source-line-no">4649</span><span id="line-4649">        // flush because the accounting is 'off' since original DSE.</span> | 
|  | <span class="source-line-no">4650</span><span id="line-4650">      }</span> | 
|  | <span class="source-line-no">4651</span><span id="line-4651">      this.region = null;</span> | 
|  | <span class="source-line-no">4652</span><span id="line-4652">    }</span> | 
|  | <span class="source-line-no">4653</span><span id="line-4653">  }</span> | 
|  | <span class="source-line-no">4654</span><span id="line-4654"></span> | 
|  | <span class="source-line-no">4655</span><span id="line-4655">  @Test</span> | 
|  | <span class="source-line-no">4656</span><span id="line-4656">  public void testCloseAndArchiveCompactedFiles() throws IOException {</span> | 
|  | <span class="source-line-no">4657</span><span id="line-4657">    byte[] CF1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">4658</span><span id="line-4658">    byte[] CF2 = Bytes.toBytes("CF2");</span> | 
|  | <span class="source-line-no">4659</span><span id="line-4659">    this.region = initHRegion(tableName, method, CONF, CF1, CF2);</span> | 
|  | <span class="source-line-no">4660</span><span id="line-4660">    for (int i = 0; i < 2; i++) {</span> | 
|  | <span class="source-line-no">4661</span><span id="line-4661">      int index = i;</span> | 
|  | <span class="source-line-no">4662</span><span id="line-4662">      Put put =</span> | 
|  | <span class="source-line-no">4663</span><span id="line-4663">        new Put(Bytes.toBytes(index)).addColumn(CF1, Bytes.toBytes("q"), Bytes.toBytes(index));</span> | 
|  | <span class="source-line-no">4664</span><span id="line-4664">      region.put(put);</span> | 
|  | <span class="source-line-no">4665</span><span id="line-4665">      region.flush(true);</span> | 
|  | <span class="source-line-no">4666</span><span id="line-4666">    }</span> | 
|  | <span class="source-line-no">4667</span><span id="line-4667"></span> | 
|  | <span class="source-line-no">4668</span><span id="line-4668">    region.compact(true);</span> | 
|  | <span class="source-line-no">4669</span><span id="line-4669"></span> | 
|  | <span class="source-line-no">4670</span><span id="line-4670">    HStore store1 = region.getStore(CF1);</span> | 
|  | <span class="source-line-no">4671</span><span id="line-4671">    HStore store2 = region.getStore(CF2);</span> | 
|  | <span class="source-line-no">4672</span><span id="line-4672">    store1.closeAndArchiveCompactedFiles();</span> | 
|  | <span class="source-line-no">4673</span><span id="line-4673">    store2.closeAndArchiveCompactedFiles();</span> | 
|  | <span class="source-line-no">4674</span><span id="line-4674"></span> | 
|  | <span class="source-line-no">4675</span><span id="line-4675">    int storefilesCount = region.getStores().stream().mapToInt(Store::getStorefilesCount).sum();</span> | 
|  | <span class="source-line-no">4676</span><span id="line-4676">    assertTrue(storefilesCount == 1);</span> | 
|  | <span class="source-line-no">4677</span><span id="line-4677"></span> | 
|  | <span class="source-line-no">4678</span><span id="line-4678">    FileSystem fs = region.getRegionFileSystem().getFileSystem();</span> | 
|  | <span class="source-line-no">4679</span><span id="line-4679">    Configuration conf = region.getReadOnlyConfiguration();</span> | 
|  | <span class="source-line-no">4680</span><span id="line-4680">    RegionInfo regionInfo = region.getRegionInfo();</span> | 
|  | <span class="source-line-no">4681</span><span id="line-4681">    Path store1ArchiveDir = HFileArchiveUtil.getStoreArchivePath(conf, regionInfo, CF1);</span> | 
|  | <span class="source-line-no">4682</span><span id="line-4682">    assertTrue(fs.exists(store1ArchiveDir));</span> | 
|  | <span class="source-line-no">4683</span><span id="line-4683">    // The archived dir of CF2 does not exist because this column family has no data at all</span> | 
|  | <span class="source-line-no">4684</span><span id="line-4684">    Path store2ArchiveDir = HFileArchiveUtil.getStoreArchivePath(conf, regionInfo, CF2);</span> | 
|  | <span class="source-line-no">4685</span><span id="line-4685">    assertFalse(fs.exists(store2ArchiveDir));</span> | 
|  | <span class="source-line-no">4686</span><span id="line-4686">  }</span> | 
|  | <span class="source-line-no">4687</span><span id="line-4687"></span> | 
|  | <span class="source-line-no">4688</span><span id="line-4688">  protected class PutThread extends Thread {</span> | 
|  | <span class="source-line-no">4689</span><span id="line-4689">    private volatile boolean done;</span> | 
|  | <span class="source-line-no">4690</span><span id="line-4690">    private volatile int numPutsFinished = 0;</span> | 
|  | <span class="source-line-no">4691</span><span id="line-4691"></span> | 
|  | <span class="source-line-no">4692</span><span id="line-4692">    private Throwable error = null;</span> | 
|  | <span class="source-line-no">4693</span><span id="line-4693">    private int numRows;</span> | 
|  | <span class="source-line-no">4694</span><span id="line-4694">    private byte[][] families;</span> | 
|  | <span class="source-line-no">4695</span><span id="line-4695">    private byte[][] qualifiers;</span> | 
|  | <span class="source-line-no">4696</span><span id="line-4696"></span> | 
|  | <span class="source-line-no">4697</span><span id="line-4697">    private PutThread(int numRows, byte[][] families, byte[][] qualifiers) {</span> | 
|  | <span class="source-line-no">4698</span><span id="line-4698">      super("PutThread");</span> | 
|  | <span class="source-line-no">4699</span><span id="line-4699">      this.numRows = numRows;</span> | 
|  | <span class="source-line-no">4700</span><span id="line-4700">      this.families = families;</span> | 
|  | <span class="source-line-no">4701</span><span id="line-4701">      this.qualifiers = qualifiers;</span> | 
|  | <span class="source-line-no">4702</span><span id="line-4702">    }</span> | 
|  | <span class="source-line-no">4703</span><span id="line-4703"></span> | 
|  | <span class="source-line-no">4704</span><span id="line-4704">    /**</span> | 
|  | <span class="source-line-no">4705</span><span id="line-4705">     * Block calling thread until this instance of PutThread has put at least one row.</span> | 
|  | <span class="source-line-no">4706</span><span id="line-4706">     */</span> | 
|  | <span class="source-line-no">4707</span><span id="line-4707">    public void waitForFirstPut() throws InterruptedException {</span> | 
|  | <span class="source-line-no">4708</span><span id="line-4708">      // wait until put thread actually puts some data</span> | 
|  | <span class="source-line-no">4709</span><span id="line-4709">      while (isAlive() && numPutsFinished == 0) {</span> | 
|  | <span class="source-line-no">4710</span><span id="line-4710">        checkNoError();</span> | 
|  | <span class="source-line-no">4711</span><span id="line-4711">        Thread.sleep(50);</span> | 
|  | <span class="source-line-no">4712</span><span id="line-4712">      }</span> | 
|  | <span class="source-line-no">4713</span><span id="line-4713">    }</span> | 
|  | <span class="source-line-no">4714</span><span id="line-4714"></span> | 
|  | <span class="source-line-no">4715</span><span id="line-4715">    public void done() {</span> | 
|  | <span class="source-line-no">4716</span><span id="line-4716">      done = true;</span> | 
|  | <span class="source-line-no">4717</span><span id="line-4717">      synchronized (this) {</span> | 
|  | <span class="source-line-no">4718</span><span id="line-4718">        interrupt();</span> | 
|  | <span class="source-line-no">4719</span><span id="line-4719">      }</span> | 
|  | <span class="source-line-no">4720</span><span id="line-4720">    }</span> | 
|  | <span class="source-line-no">4721</span><span id="line-4721"></span> | 
|  | <span class="source-line-no">4722</span><span id="line-4722">    public void checkNoError() {</span> | 
|  | <span class="source-line-no">4723</span><span id="line-4723">      if (error != null) {</span> | 
|  | <span class="source-line-no">4724</span><span id="line-4724">        assertNull(error);</span> | 
|  | <span class="source-line-no">4725</span><span id="line-4725">      }</span> | 
|  | <span class="source-line-no">4726</span><span id="line-4726">    }</span> | 
|  | <span class="source-line-no">4727</span><span id="line-4727"></span> | 
|  | <span class="source-line-no">4728</span><span id="line-4728">    @Override</span> | 
|  | <span class="source-line-no">4729</span><span id="line-4729">    public void run() {</span> | 
|  | <span class="source-line-no">4730</span><span id="line-4730">      done = false;</span> | 
|  | <span class="source-line-no">4731</span><span id="line-4731">      while (!done) {</span> | 
|  | <span class="source-line-no">4732</span><span id="line-4732">        try {</span> | 
|  | <span class="source-line-no">4733</span><span id="line-4733">          for (int r = 0; r < numRows; r++) {</span> | 
|  | <span class="source-line-no">4734</span><span id="line-4734">            byte[] row = Bytes.toBytes("row" + r);</span> | 
|  | <span class="source-line-no">4735</span><span id="line-4735">            Put put = new Put(row);</span> | 
|  | <span class="source-line-no">4736</span><span id="line-4736">            put.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">4737</span><span id="line-4737">            byte[] value = Bytes.toBytes(String.valueOf(numPutsFinished));</span> | 
|  | <span class="source-line-no">4738</span><span id="line-4738">            for (byte[] family : families) {</span> | 
|  | <span class="source-line-no">4739</span><span id="line-4739">              for (byte[] qualifier : qualifiers) {</span> | 
|  | <span class="source-line-no">4740</span><span id="line-4740">                put.addColumn(family, qualifier, numPutsFinished, value);</span> | 
|  | <span class="source-line-no">4741</span><span id="line-4741">              }</span> | 
|  | <span class="source-line-no">4742</span><span id="line-4742">            }</span> | 
|  | <span class="source-line-no">4743</span><span id="line-4743">            region.put(put);</span> | 
|  | <span class="source-line-no">4744</span><span id="line-4744">            numPutsFinished++;</span> | 
|  | <span class="source-line-no">4745</span><span id="line-4745">            if (numPutsFinished > 0 && numPutsFinished % 47 == 0) {</span> | 
|  | <span class="source-line-no">4746</span><span id="line-4746">              LOG.debug("put iteration = {}", numPutsFinished);</span> | 
|  | <span class="source-line-no">4747</span><span id="line-4747">              Delete delete = new Delete(row, (long) numPutsFinished - 30);</span> | 
|  | <span class="source-line-no">4748</span><span id="line-4748">              region.delete(delete);</span> | 
|  | <span class="source-line-no">4749</span><span id="line-4749">            }</span> | 
|  | <span class="source-line-no">4750</span><span id="line-4750">            numPutsFinished++;</span> | 
|  | <span class="source-line-no">4751</span><span id="line-4751">          }</span> | 
|  | <span class="source-line-no">4752</span><span id="line-4752">        } catch (InterruptedIOException e) {</span> | 
|  | <span class="source-line-no">4753</span><span id="line-4753">          // This is fine. It means we are done, or didn't get the lock on time</span> | 
|  | <span class="source-line-no">4754</span><span id="line-4754">          LOG.info("Interrupted", e);</span> | 
|  | <span class="source-line-no">4755</span><span id="line-4755">        } catch (IOException e) {</span> | 
|  | <span class="source-line-no">4756</span><span id="line-4756">          LOG.error("Error while putting records", e);</span> | 
|  | <span class="source-line-no">4757</span><span id="line-4757">          error = e;</span> | 
|  | <span class="source-line-no">4758</span><span id="line-4758">          break;</span> | 
|  | <span class="source-line-no">4759</span><span id="line-4759">        }</span> | 
|  | <span class="source-line-no">4760</span><span id="line-4760">      }</span> | 
|  | <span class="source-line-no">4761</span><span id="line-4761"></span> | 
|  | <span class="source-line-no">4762</span><span id="line-4762">    }</span> | 
|  | <span class="source-line-no">4763</span><span id="line-4763"></span> | 
|  | <span class="source-line-no">4764</span><span id="line-4764">  }</span> | 
|  | <span class="source-line-no">4765</span><span id="line-4765"></span> | 
|  | <span class="source-line-no">4766</span><span id="line-4766">  /**</span> | 
|  | <span class="source-line-no">4767</span><span id="line-4767">   * Writes very wide records and gets the latest row every time.. Flushes and compacts the region</span> | 
|  | <span class="source-line-no">4768</span><span id="line-4768">   * aggressivly to catch issues. by flush / scan / compaction when joining threads</span> | 
|  | <span class="source-line-no">4769</span><span id="line-4769">   */</span> | 
|  | <span class="source-line-no">4770</span><span id="line-4770">  @Test</span> | 
|  | <span class="source-line-no">4771</span><span id="line-4771">  public void testWritesWhileGetting() throws Exception {</span> | 
|  | <span class="source-line-no">4772</span><span id="line-4772">    int testCount = 50;</span> | 
|  | <span class="source-line-no">4773</span><span id="line-4773">    int numRows = 1;</span> | 
|  | <span class="source-line-no">4774</span><span id="line-4774">    int numFamilies = 10;</span> | 
|  | <span class="source-line-no">4775</span><span id="line-4775">    int numQualifiers = 100;</span> | 
|  | <span class="source-line-no">4776</span><span id="line-4776">    int compactInterval = 100;</span> | 
|  | <span class="source-line-no">4777</span><span id="line-4777">    byte[][] families = new byte[numFamilies][];</span> | 
|  | <span class="source-line-no">4778</span><span id="line-4778">    for (int i = 0; i < numFamilies; i++) {</span> | 
|  | <span class="source-line-no">4779</span><span id="line-4779">      families[i] = Bytes.toBytes("family" + i);</span> | 
|  | <span class="source-line-no">4780</span><span id="line-4780">    }</span> | 
|  | <span class="source-line-no">4781</span><span id="line-4781">    byte[][] qualifiers = new byte[numQualifiers][];</span> | 
|  | <span class="source-line-no">4782</span><span id="line-4782">    for (int i = 0; i < numQualifiers; i++) {</span> | 
|  | <span class="source-line-no">4783</span><span id="line-4783">      qualifiers[i] = Bytes.toBytes("qual" + i);</span> | 
|  | <span class="source-line-no">4784</span><span id="line-4784">    }</span> | 
|  | <span class="source-line-no">4785</span><span id="line-4785"></span> | 
|  | <span class="source-line-no">4786</span><span id="line-4786">    // This test flushes constantly and can cause many files to be created,</span> | 
|  | <span class="source-line-no">4787</span><span id="line-4787">    // possibly</span> | 
|  | <span class="source-line-no">4788</span><span id="line-4788">    // extending over the ulimit. Make sure compactions are aggressive in</span> | 
|  | <span class="source-line-no">4789</span><span id="line-4789">    // reducing</span> | 
|  | <span class="source-line-no">4790</span><span id="line-4790">    // the number of HFiles created.</span> | 
|  | <span class="source-line-no">4791</span><span id="line-4791">    Configuration conf = HBaseConfiguration.create(CONF);</span> | 
|  | <span class="source-line-no">4792</span><span id="line-4792">    conf.setInt("hbase.hstore.compaction.min", 1);</span> | 
|  | <span class="source-line-no">4793</span><span id="line-4793">    conf.setInt("hbase.hstore.compaction.max", 1000);</span> | 
|  | <span class="source-line-no">4794</span><span id="line-4794">    this.region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">4795</span><span id="line-4795">    PutThread putThread = null;</span> | 
|  | <span class="source-line-no">4796</span><span id="line-4796">    MultithreadedTestUtil.TestContext ctx = new MultithreadedTestUtil.TestContext(conf);</span> | 
|  | <span class="source-line-no">4797</span><span id="line-4797">    try {</span> | 
|  | <span class="source-line-no">4798</span><span id="line-4798">      putThread = new PutThread(numRows, families, qualifiers);</span> | 
|  | <span class="source-line-no">4799</span><span id="line-4799">      putThread.start();</span> | 
|  | <span class="source-line-no">4800</span><span id="line-4800">      putThread.waitForFirstPut();</span> | 
|  | <span class="source-line-no">4801</span><span id="line-4801"></span> | 
|  | <span class="source-line-no">4802</span><span id="line-4802">      // Add a thread that flushes as fast as possible</span> | 
|  | <span class="source-line-no">4803</span><span id="line-4803">      ctx.addThread(new RepeatingTestThread(ctx) {</span> | 
|  | <span class="source-line-no">4804</span><span id="line-4804"></span> | 
|  | <span class="source-line-no">4805</span><span id="line-4805">        @Override</span> | 
|  | <span class="source-line-no">4806</span><span id="line-4806">        public void doAnAction() throws Exception {</span> | 
|  | <span class="source-line-no">4807</span><span id="line-4807">          region.flush(true);</span> | 
|  | <span class="source-line-no">4808</span><span id="line-4808">          // Compact regularly to avoid creating too many files and exceeding</span> | 
|  | <span class="source-line-no">4809</span><span id="line-4809">          // the ulimit.</span> | 
|  | <span class="source-line-no">4810</span><span id="line-4810">          region.compact(false);</span> | 
|  | <span class="source-line-no">4811</span><span id="line-4811">          for (HStore store : region.getStores()) {</span> | 
|  | <span class="source-line-no">4812</span><span id="line-4812">            store.closeAndArchiveCompactedFiles();</span> | 
|  | <span class="source-line-no">4813</span><span id="line-4813">          }</span> | 
|  | <span class="source-line-no">4814</span><span id="line-4814">        }</span> | 
|  | <span class="source-line-no">4815</span><span id="line-4815">      });</span> | 
|  | <span class="source-line-no">4816</span><span id="line-4816">      ctx.startThreads();</span> | 
|  | <span class="source-line-no">4817</span><span id="line-4817"></span> | 
|  | <span class="source-line-no">4818</span><span id="line-4818">      Get get = new Get(Bytes.toBytes("row0"));</span> | 
|  | <span class="source-line-no">4819</span><span id="line-4819">      Result result = null;</span> | 
|  | <span class="source-line-no">4820</span><span id="line-4820"></span> | 
|  | <span class="source-line-no">4821</span><span id="line-4821">      int expectedCount = numFamilies * numQualifiers;</span> | 
|  | <span class="source-line-no">4822</span><span id="line-4822"></span> | 
|  | <span class="source-line-no">4823</span><span id="line-4823">      long prevTimestamp = 0L;</span> | 
|  | <span class="source-line-no">4824</span><span id="line-4824">      for (int i = 0; i < testCount; i++) {</span> | 
|  | <span class="source-line-no">4825</span><span id="line-4825">        LOG.info("testWritesWhileGetting verify turn " + i);</span> | 
|  | <span class="source-line-no">4826</span><span id="line-4826">        boolean previousEmpty = result == null || result.isEmpty();</span> | 
|  | <span class="source-line-no">4827</span><span id="line-4827">        result = region.get(get);</span> | 
|  | <span class="source-line-no">4828</span><span id="line-4828">        if (!result.isEmpty() || !previousEmpty || i > compactInterval) {</span> | 
|  | <span class="source-line-no">4829</span><span id="line-4829">          assertEquals("i=" + i, expectedCount, result.size());</span> | 
|  | <span class="source-line-no">4830</span><span id="line-4830">          // TODO this was removed, now what dangit?!</span> | 
|  | <span class="source-line-no">4831</span><span id="line-4831">          // search looking for the qualifier in question?</span> | 
|  | <span class="source-line-no">4832</span><span id="line-4832">          long timestamp = 0;</span> | 
|  | <span class="source-line-no">4833</span><span id="line-4833">          for (Cell kv : result.rawCells()) {</span> | 
|  | <span class="source-line-no">4834</span><span id="line-4834">            if (</span> | 
|  | <span class="source-line-no">4835</span><span id="line-4835">              CellUtil.matchingFamily(kv, families[0])</span> | 
|  | <span class="source-line-no">4836</span><span id="line-4836">                && CellUtil.matchingQualifier(kv, qualifiers[0])</span> | 
|  | <span class="source-line-no">4837</span><span id="line-4837">            ) {</span> | 
|  | <span class="source-line-no">4838</span><span id="line-4838">              timestamp = kv.getTimestamp();</span> | 
|  | <span class="source-line-no">4839</span><span id="line-4839">            }</span> | 
|  | <span class="source-line-no">4840</span><span id="line-4840">          }</span> | 
|  | <span class="source-line-no">4841</span><span id="line-4841">          assertTrue(timestamp >= prevTimestamp);</span> | 
|  | <span class="source-line-no">4842</span><span id="line-4842">          prevTimestamp = timestamp;</span> | 
|  | <span class="source-line-no">4843</span><span id="line-4843">          ExtendedCell previousKV = null;</span> | 
|  | <span class="source-line-no">4844</span><span id="line-4844"></span> | 
|  | <span class="source-line-no">4845</span><span id="line-4845">          for (ExtendedCell kv : ClientInternalHelper.getExtendedRawCells(result)) {</span> | 
|  | <span class="source-line-no">4846</span><span id="line-4846">            byte[] thisValue = CellUtil.cloneValue(kv);</span> | 
|  | <span class="source-line-no">4847</span><span id="line-4847">            if (previousKV != null) {</span> | 
|  | <span class="source-line-no">4848</span><span id="line-4848">              if (Bytes.compareTo(CellUtil.cloneValue(previousKV), thisValue) != 0) {</span> | 
|  | <span class="source-line-no">4849</span><span id="line-4849">                LOG.warn("These two KV should have the same value." + " Previous KV:" + previousKV</span> | 
|  | <span class="source-line-no">4850</span><span id="line-4850">                  + "(memStoreTS:" + previousKV.getSequenceId() + ")" + ", New KV: " + kv</span> | 
|  | <span class="source-line-no">4851</span><span id="line-4851">                  + "(memStoreTS:" + kv.getSequenceId() + ")");</span> | 
|  | <span class="source-line-no">4852</span><span id="line-4852">                assertEquals(0, Bytes.compareTo(CellUtil.cloneValue(previousKV), thisValue));</span> | 
|  | <span class="source-line-no">4853</span><span id="line-4853">              }</span> | 
|  | <span class="source-line-no">4854</span><span id="line-4854">            }</span> | 
|  | <span class="source-line-no">4855</span><span id="line-4855">            previousKV = kv;</span> | 
|  | <span class="source-line-no">4856</span><span id="line-4856">          }</span> | 
|  | <span class="source-line-no">4857</span><span id="line-4857">        }</span> | 
|  | <span class="source-line-no">4858</span><span id="line-4858">      }</span> | 
|  | <span class="source-line-no">4859</span><span id="line-4859">    } finally {</span> | 
|  | <span class="source-line-no">4860</span><span id="line-4860">      if (putThread != null) putThread.done();</span> | 
|  | <span class="source-line-no">4861</span><span id="line-4861"></span> | 
|  | <span class="source-line-no">4862</span><span id="line-4862">      region.flush(true);</span> | 
|  | <span class="source-line-no">4863</span><span id="line-4863"></span> | 
|  | <span class="source-line-no">4864</span><span id="line-4864">      if (putThread != null) {</span> | 
|  | <span class="source-line-no">4865</span><span id="line-4865">        putThread.join();</span> | 
|  | <span class="source-line-no">4866</span><span id="line-4866">        putThread.checkNoError();</span> | 
|  | <span class="source-line-no">4867</span><span id="line-4867">      }</span> | 
|  | <span class="source-line-no">4868</span><span id="line-4868"></span> | 
|  | <span class="source-line-no">4869</span><span id="line-4869">      ctx.stop();</span> | 
|  | <span class="source-line-no">4870</span><span id="line-4870">      HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">4871</span><span id="line-4871">      this.region = null;</span> | 
|  | <span class="source-line-no">4872</span><span id="line-4872">    }</span> | 
|  | <span class="source-line-no">4873</span><span id="line-4873">  }</span> | 
|  | <span class="source-line-no">4874</span><span id="line-4874"></span> | 
|  | <span class="source-line-no">4875</span><span id="line-4875">  @Test</span> | 
|  | <span class="source-line-no">4876</span><span id="line-4876">  public void testHolesInMeta() throws Exception {</span> | 
|  | <span class="source-line-no">4877</span><span id="line-4877">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">4878</span><span id="line-4878">    this.region =</span> | 
|  | <span class="source-line-no">4879</span><span id="line-4879">      initHRegion(tableName, Bytes.toBytes("x"), Bytes.toBytes("z"), method, CONF, false, family);</span> | 
|  | <span class="source-line-no">4880</span><span id="line-4880">    byte[] rowNotServed = Bytes.toBytes("a");</span> | 
|  | <span class="source-line-no">4881</span><span id="line-4881">    Get g = new Get(rowNotServed);</span> | 
|  | <span class="source-line-no">4882</span><span id="line-4882">    try {</span> | 
|  | <span class="source-line-no">4883</span><span id="line-4883">      region.get(g);</span> | 
|  | <span class="source-line-no">4884</span><span id="line-4884">      fail();</span> | 
|  | <span class="source-line-no">4885</span><span id="line-4885">    } catch (WrongRegionException x) {</span> | 
|  | <span class="source-line-no">4886</span><span id="line-4886">      // OK</span> | 
|  | <span class="source-line-no">4887</span><span id="line-4887">    }</span> | 
|  | <span class="source-line-no">4888</span><span id="line-4888">    byte[] row = Bytes.toBytes("y");</span> | 
|  | <span class="source-line-no">4889</span><span id="line-4889">    g = new Get(row);</span> | 
|  | <span class="source-line-no">4890</span><span id="line-4890">    region.get(g);</span> | 
|  | <span class="source-line-no">4891</span><span id="line-4891">  }</span> | 
|  | <span class="source-line-no">4892</span><span id="line-4892"></span> | 
|  | <span class="source-line-no">4893</span><span id="line-4893">  @Test</span> | 
|  | <span class="source-line-no">4894</span><span id="line-4894">  public void testIndexesScanWithOneDeletedRow() throws IOException {</span> | 
|  | <span class="source-line-no">4895</span><span id="line-4895">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">4896</span><span id="line-4896"></span> | 
|  | <span class="source-line-no">4897</span><span id="line-4897">    // Setting up region</span> | 
|  | <span class="source-line-no">4898</span><span id="line-4898">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">4899</span><span id="line-4899">    Put put = new Put(Bytes.toBytes(1L));</span> | 
|  | <span class="source-line-no">4900</span><span id="line-4900">    put.addColumn(family, qual1, 1L, Bytes.toBytes(1L));</span> | 
|  | <span class="source-line-no">4901</span><span id="line-4901">    region.put(put);</span> | 
|  | <span class="source-line-no">4902</span><span id="line-4902"></span> | 
|  | <span class="source-line-no">4903</span><span id="line-4903">    region.flush(true);</span> | 
|  | <span class="source-line-no">4904</span><span id="line-4904"></span> | 
|  | <span class="source-line-no">4905</span><span id="line-4905">    Delete delete = new Delete(Bytes.toBytes(1L), 1L);</span> | 
|  | <span class="source-line-no">4906</span><span id="line-4906">    region.delete(delete);</span> | 
|  | <span class="source-line-no">4907</span><span id="line-4907"></span> | 
|  | <span class="source-line-no">4908</span><span id="line-4908">    put = new Put(Bytes.toBytes(2L));</span> | 
|  | <span class="source-line-no">4909</span><span id="line-4909">    put.addColumn(family, qual1, 2L, Bytes.toBytes(2L));</span> | 
|  | <span class="source-line-no">4910</span><span id="line-4910">    region.put(put);</span> | 
|  | <span class="source-line-no">4911</span><span id="line-4911"></span> | 
|  | <span class="source-line-no">4912</span><span id="line-4912">    Scan idxScan = new Scan();</span> | 
|  | <span class="source-line-no">4913</span><span id="line-4913">    idxScan.addFamily(family);</span> | 
|  | <span class="source-line-no">4914</span><span id="line-4914">    idxScan.setFilter(new FilterList(FilterList.Operator.MUST_PASS_ALL,</span> | 
|  | <span class="source-line-no">4915</span><span id="line-4915">      Arrays.<Filter> asList(</span> | 
|  | <span class="source-line-no">4916</span><span id="line-4916">        new SingleColumnValueFilter(family, qual1, CompareOperator.GREATER_OR_EQUAL,</span> | 
|  | <span class="source-line-no">4917</span><span id="line-4917">          new BinaryComparator(Bytes.toBytes(0L))),</span> | 
|  | <span class="source-line-no">4918</span><span id="line-4918">        new SingleColumnValueFilter(family, qual1, CompareOperator.LESS_OR_EQUAL,</span> | 
|  | <span class="source-line-no">4919</span><span id="line-4919">          new BinaryComparator(Bytes.toBytes(3L))))));</span> | 
|  | <span class="source-line-no">4920</span><span id="line-4920">    try (InternalScanner scanner = region.getScanner(idxScan)) {</span> | 
|  | <span class="source-line-no">4921</span><span id="line-4921">      List<Cell> res = new ArrayList<>();</span> | 
|  | <span class="source-line-no">4922</span><span id="line-4922"></span> | 
|  | <span class="source-line-no">4923</span><span id="line-4923">      while (scanner.next(res)) {</span> | 
|  | <span class="source-line-no">4924</span><span id="line-4924">        // Ignore res value.</span> | 
|  | <span class="source-line-no">4925</span><span id="line-4925">      }</span> | 
|  | <span class="source-line-no">4926</span><span id="line-4926">      assertEquals(1L, res.size());</span> | 
|  | <span class="source-line-no">4927</span><span id="line-4927">    }</span> | 
|  | <span class="source-line-no">4928</span><span id="line-4928">  }</span> | 
|  | <span class="source-line-no">4929</span><span id="line-4929"></span> | 
|  | <span class="source-line-no">4930</span><span id="line-4930">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">4931</span><span id="line-4931">  // Bloom filter test</span> | 
|  | <span class="source-line-no">4932</span><span id="line-4932">  // ////////////////////////////////////////////////////////////////////////////</span> | 
|  | <span class="source-line-no">4933</span><span id="line-4933">  @Test</span> | 
|  | <span class="source-line-no">4934</span><span id="line-4934">  public void testBloomFilterSize() throws IOException {</span> | 
|  | <span class="source-line-no">4935</span><span id="line-4935">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">4936</span><span id="line-4936">    byte[] qf1 = Bytes.toBytes("col");</span> | 
|  | <span class="source-line-no">4937</span><span id="line-4937">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">4938</span><span id="line-4938">    // Create Table</span> | 
|  | <span class="source-line-no">4939</span><span id="line-4939">    TableDescriptor tableDescriptor = TableDescriptorBuilder.newBuilder(tableName)</span> | 
|  | <span class="source-line-no">4940</span><span id="line-4940">      .setColumnFamily(ColumnFamilyDescriptorBuilder.newBuilder(fam1)</span> | 
|  | <span class="source-line-no">4941</span><span id="line-4941">        .setMaxVersions(Integer.MAX_VALUE).setBloomFilterType(BloomType.ROWCOL).build())</span> | 
|  | <span class="source-line-no">4942</span><span id="line-4942">      .build();</span> | 
|  | <span class="source-line-no">4943</span><span id="line-4943">    RegionInfo info = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName()).build();</span> | 
|  | <span class="source-line-no">4944</span><span id="line-4944">    this.region = TEST_UTIL.createLocalHRegion(info, tableDescriptor);</span> | 
|  | <span class="source-line-no">4945</span><span id="line-4945">    int num_unique_rows = 10;</span> | 
|  | <span class="source-line-no">4946</span><span id="line-4946">    int duplicate_multiplier = 2;</span> | 
|  | <span class="source-line-no">4947</span><span id="line-4947">    int num_storefiles = 4;</span> | 
|  | <span class="source-line-no">4948</span><span id="line-4948"></span> | 
|  | <span class="source-line-no">4949</span><span id="line-4949">    int version = 0;</span> | 
|  | <span class="source-line-no">4950</span><span id="line-4950">    for (int f = 0; f < num_storefiles; f++) {</span> | 
|  | <span class="source-line-no">4951</span><span id="line-4951">      for (int i = 0; i < duplicate_multiplier; i++) {</span> | 
|  | <span class="source-line-no">4952</span><span id="line-4952">        for (int j = 0; j < num_unique_rows; j++) {</span> | 
|  | <span class="source-line-no">4953</span><span id="line-4953">          Put put = new Put(Bytes.toBytes("row" + j));</span> | 
|  | <span class="source-line-no">4954</span><span id="line-4954">          put.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">4955</span><span id="line-4955">          long ts = version++;</span> | 
|  | <span class="source-line-no">4956</span><span id="line-4956">          put.addColumn(fam1, qf1, ts, val1);</span> | 
|  | <span class="source-line-no">4957</span><span id="line-4957">          region.put(put);</span> | 
|  | <span class="source-line-no">4958</span><span id="line-4958">        }</span> | 
|  | <span class="source-line-no">4959</span><span id="line-4959">      }</span> | 
|  | <span class="source-line-no">4960</span><span id="line-4960">      region.flush(true);</span> | 
|  | <span class="source-line-no">4961</span><span id="line-4961">    }</span> | 
|  | <span class="source-line-no">4962</span><span id="line-4962">    // before compaction</span> | 
|  | <span class="source-line-no">4963</span><span id="line-4963">    HStore store = region.getStore(fam1);</span> | 
|  | <span class="source-line-no">4964</span><span id="line-4964">    Collection<HStoreFile> storeFiles = store.getStorefiles();</span> | 
|  | <span class="source-line-no">4965</span><span id="line-4965">    for (HStoreFile storefile : storeFiles) {</span> | 
|  | <span class="source-line-no">4966</span><span id="line-4966">      StoreFileReader reader = storefile.getReader();</span> | 
|  | <span class="source-line-no">4967</span><span id="line-4967">      reader.loadFileInfo();</span> | 
|  | <span class="source-line-no">4968</span><span id="line-4968">      reader.loadBloomfilter();</span> | 
|  | <span class="source-line-no">4969</span><span id="line-4969">      assertEquals(num_unique_rows * duplicate_multiplier, reader.getEntries());</span> | 
|  | <span class="source-line-no">4970</span><span id="line-4970">      assertEquals(num_unique_rows, reader.getFilterEntries());</span> | 
|  | <span class="source-line-no">4971</span><span id="line-4971">    }</span> | 
|  | <span class="source-line-no">4972</span><span id="line-4972"></span> | 
|  | <span class="source-line-no">4973</span><span id="line-4973">    region.compact(true);</span> | 
|  | <span class="source-line-no">4974</span><span id="line-4974"></span> | 
|  | <span class="source-line-no">4975</span><span id="line-4975">    // after compaction</span> | 
|  | <span class="source-line-no">4976</span><span id="line-4976">    storeFiles = store.getStorefiles();</span> | 
|  | <span class="source-line-no">4977</span><span id="line-4977">    for (HStoreFile storefile : storeFiles) {</span> | 
|  | <span class="source-line-no">4978</span><span id="line-4978">      StoreFileReader reader = storefile.getReader();</span> | 
|  | <span class="source-line-no">4979</span><span id="line-4979">      reader.loadFileInfo();</span> | 
|  | <span class="source-line-no">4980</span><span id="line-4980">      reader.loadBloomfilter();</span> | 
|  | <span class="source-line-no">4981</span><span id="line-4981">      assertEquals(num_unique_rows * duplicate_multiplier * num_storefiles, reader.getEntries());</span> | 
|  | <span class="source-line-no">4982</span><span id="line-4982">      assertEquals(num_unique_rows, reader.getFilterEntries());</span> | 
|  | <span class="source-line-no">4983</span><span id="line-4983">    }</span> | 
|  | <span class="source-line-no">4984</span><span id="line-4984">  }</span> | 
|  | <span class="source-line-no">4985</span><span id="line-4985"></span> | 
|  | <span class="source-line-no">4986</span><span id="line-4986">  @Test</span> | 
|  | <span class="source-line-no">4987</span><span id="line-4987">  public void testAllColumnsWithBloomFilter() throws IOException {</span> | 
|  | <span class="source-line-no">4988</span><span id="line-4988">    byte[] TABLE = Bytes.toBytes(name.getMethodName());</span> | 
|  | <span class="source-line-no">4989</span><span id="line-4989">    byte[] FAMILY = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">4990</span><span id="line-4990"></span> | 
|  | <span class="source-line-no">4991</span><span id="line-4991">    // Create table</span> | 
|  | <span class="source-line-no">4992</span><span id="line-4992">    TableDescriptor tableDescriptor = TableDescriptorBuilder.newBuilder(TableName.valueOf(TABLE))</span> | 
|  | <span class="source-line-no">4993</span><span id="line-4993">      .setColumnFamily(ColumnFamilyDescriptorBuilder.newBuilder(FAMILY)</span> | 
|  | <span class="source-line-no">4994</span><span id="line-4994">        .setMaxVersions(Integer.MAX_VALUE).setBloomFilterType(BloomType.ROWCOL).build())</span> | 
|  | <span class="source-line-no">4995</span><span id="line-4995">      .build();</span> | 
|  | <span class="source-line-no">4996</span><span id="line-4996">    RegionInfo info = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName()).build();</span> | 
|  | <span class="source-line-no">4997</span><span id="line-4997">    this.region = TEST_UTIL.createLocalHRegion(info, tableDescriptor);</span> | 
|  | <span class="source-line-no">4998</span><span id="line-4998">    // For row:0, col:0: insert versions 1 through 5.</span> | 
|  | <span class="source-line-no">4999</span><span id="line-4999">    byte[] row = Bytes.toBytes("row:" + 0);</span> | 
|  | <span class="source-line-no">5000</span><span id="line-5000">    byte[] column = Bytes.toBytes("column:" + 0);</span> | 
|  | <span class="source-line-no">5001</span><span id="line-5001">    Put put = new Put(row);</span> | 
|  | <span class="source-line-no">5002</span><span id="line-5002">    put.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">5003</span><span id="line-5003">    for (long idx = 1; idx <= 4; idx++) {</span> | 
|  | <span class="source-line-no">5004</span><span id="line-5004">      put.addColumn(FAMILY, column, idx, Bytes.toBytes("value-version-" + idx));</span> | 
|  | <span class="source-line-no">5005</span><span id="line-5005">    }</span> | 
|  | <span class="source-line-no">5006</span><span id="line-5006">    region.put(put);</span> | 
|  | <span class="source-line-no">5007</span><span id="line-5007"></span> | 
|  | <span class="source-line-no">5008</span><span id="line-5008">    // Flush</span> | 
|  | <span class="source-line-no">5009</span><span id="line-5009">    region.flush(true);</span> | 
|  | <span class="source-line-no">5010</span><span id="line-5010"></span> | 
|  | <span class="source-line-no">5011</span><span id="line-5011">    // Get rows</span> | 
|  | <span class="source-line-no">5012</span><span id="line-5012">    Get get = new Get(row);</span> | 
|  | <span class="source-line-no">5013</span><span id="line-5013">    get.readAllVersions();</span> | 
|  | <span class="source-line-no">5014</span><span id="line-5014">    Cell[] kvs = region.get(get).rawCells();</span> | 
|  | <span class="source-line-no">5015</span><span id="line-5015"></span> | 
|  | <span class="source-line-no">5016</span><span id="line-5016">    // Check if rows are correct</span> | 
|  | <span class="source-line-no">5017</span><span id="line-5017">    assertEquals(4, kvs.length);</span> | 
|  | <span class="source-line-no">5018</span><span id="line-5018">    checkOneCell(kvs[0], FAMILY, 0, 0, 4);</span> | 
|  | <span class="source-line-no">5019</span><span id="line-5019">    checkOneCell(kvs[1], FAMILY, 0, 0, 3);</span> | 
|  | <span class="source-line-no">5020</span><span id="line-5020">    checkOneCell(kvs[2], FAMILY, 0, 0, 2);</span> | 
|  | <span class="source-line-no">5021</span><span id="line-5021">    checkOneCell(kvs[3], FAMILY, 0, 0, 1);</span> | 
|  | <span class="source-line-no">5022</span><span id="line-5022">  }</span> | 
|  | <span class="source-line-no">5023</span><span id="line-5023"></span> | 
|  | <span class="source-line-no">5024</span><span id="line-5024">  /**</span> | 
|  | <span class="source-line-no">5025</span><span id="line-5025">   * Testcase to cover bug-fix for HBASE-2823 Ensures correct delete when issuing delete row on</span> | 
|  | <span class="source-line-no">5026</span><span id="line-5026">   * columns with bloom filter set to row+col (BloomType.ROWCOL)</span> | 
|  | <span class="source-line-no">5027</span><span id="line-5027">   */</span> | 
|  | <span class="source-line-no">5028</span><span id="line-5028">  @Test</span> | 
|  | <span class="source-line-no">5029</span><span id="line-5029">  public void testDeleteRowWithBloomFilter() throws IOException {</span> | 
|  | <span class="source-line-no">5030</span><span id="line-5030">    byte[] familyName = Bytes.toBytes("familyName");</span> | 
|  | <span class="source-line-no">5031</span><span id="line-5031"></span> | 
|  | <span class="source-line-no">5032</span><span id="line-5032">    // Create Table</span> | 
|  | <span class="source-line-no">5033</span><span id="line-5033">    TableDescriptor tableDescriptor = TableDescriptorBuilder.newBuilder(tableName)</span> | 
|  | <span class="source-line-no">5034</span><span id="line-5034">      .setColumnFamily(ColumnFamilyDescriptorBuilder.newBuilder(familyName)</span> | 
|  | <span class="source-line-no">5035</span><span id="line-5035">        .setMaxVersions(Integer.MAX_VALUE).setBloomFilterType(BloomType.ROWCOL).build())</span> | 
|  | <span class="source-line-no">5036</span><span id="line-5036">      .build();</span> | 
|  | <span class="source-line-no">5037</span><span id="line-5037">    RegionInfo info = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName()).build();</span> | 
|  | <span class="source-line-no">5038</span><span id="line-5038">    this.region = TEST_UTIL.createLocalHRegion(info, tableDescriptor);</span> | 
|  | <span class="source-line-no">5039</span><span id="line-5039">    // Insert some data</span> | 
|  | <span class="source-line-no">5040</span><span id="line-5040">    byte[] row = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">5041</span><span id="line-5041">    byte[] col = Bytes.toBytes("col1");</span> | 
|  | <span class="source-line-no">5042</span><span id="line-5042"></span> | 
|  | <span class="source-line-no">5043</span><span id="line-5043">    Put put = new Put(row);</span> | 
|  | <span class="source-line-no">5044</span><span id="line-5044">    put.addColumn(familyName, col, 1, Bytes.toBytes("SomeRandomValue"));</span> | 
|  | <span class="source-line-no">5045</span><span id="line-5045">    region.put(put);</span> | 
|  | <span class="source-line-no">5046</span><span id="line-5046">    region.flush(true);</span> | 
|  | <span class="source-line-no">5047</span><span id="line-5047"></span> | 
|  | <span class="source-line-no">5048</span><span id="line-5048">    Delete del = new Delete(row);</span> | 
|  | <span class="source-line-no">5049</span><span id="line-5049">    region.delete(del);</span> | 
|  | <span class="source-line-no">5050</span><span id="line-5050">    region.flush(true);</span> | 
|  | <span class="source-line-no">5051</span><span id="line-5051"></span> | 
|  | <span class="source-line-no">5052</span><span id="line-5052">    // Get remaining rows (should have none)</span> | 
|  | <span class="source-line-no">5053</span><span id="line-5053">    Get get = new Get(row);</span> | 
|  | <span class="source-line-no">5054</span><span id="line-5054">    get.addColumn(familyName, col);</span> | 
|  | <span class="source-line-no">5055</span><span id="line-5055"></span> | 
|  | <span class="source-line-no">5056</span><span id="line-5056">    Cell[] keyValues = region.get(get).rawCells();</span> | 
|  | <span class="source-line-no">5057</span><span id="line-5057">    assertEquals(0, keyValues.length);</span> | 
|  | <span class="source-line-no">5058</span><span id="line-5058">  }</span> | 
|  | <span class="source-line-no">5059</span><span id="line-5059"></span> | 
|  | <span class="source-line-no">5060</span><span id="line-5060">  @Test</span> | 
|  | <span class="source-line-no">5061</span><span id="line-5061">  public void testgetHDFSBlocksDistribution() throws Exception {</span> | 
|  | <span class="source-line-no">5062</span><span id="line-5062">    HBaseTestingUtil htu = new HBaseTestingUtil();</span> | 
|  | <span class="source-line-no">5063</span><span id="line-5063">    // Why do we set the block size in this test? If we set it smaller than the kvs, then we'll</span> | 
|  | <span class="source-line-no">5064</span><span id="line-5064">    // break up the file in to more pieces that can be distributed across the three nodes and we</span> | 
|  | <span class="source-line-no">5065</span><span id="line-5065">    // won't be able to have the condition this test asserts; that at least one node has</span> | 
|  | <span class="source-line-no">5066</span><span id="line-5066">    // a copy of all replicas -- if small block size, then blocks are spread evenly across the</span> | 
|  | <span class="source-line-no">5067</span><span id="line-5067">    // the three nodes. hfilev3 with tags seems to put us over the block size. St.Ack.</span> | 
|  | <span class="source-line-no">5068</span><span id="line-5068">    // final int DEFAULT_BLOCK_SIZE = 1024;</span> | 
|  | <span class="source-line-no">5069</span><span id="line-5069">    // htu.getConfiguration().setLong("dfs.blocksize", DEFAULT_BLOCK_SIZE);</span> | 
|  | <span class="source-line-no">5070</span><span id="line-5070">    htu.getConfiguration().setInt("dfs.replication", 2);</span> | 
|  | <span class="source-line-no">5071</span><span id="line-5071"></span> | 
|  | <span class="source-line-no">5072</span><span id="line-5072">    // set up a cluster with 3 nodes</span> | 
|  | <span class="source-line-no">5073</span><span id="line-5073">    SingleProcessHBaseCluster cluster = null;</span> | 
|  | <span class="source-line-no">5074</span><span id="line-5074">    String dataNodeHosts[] = new String[] { "host1", "host2", "host3" };</span> | 
|  | <span class="source-line-no">5075</span><span id="line-5075">    int regionServersCount = 3;</span> | 
|  | <span class="source-line-no">5076</span><span id="line-5076"></span> | 
|  | <span class="source-line-no">5077</span><span id="line-5077">    try {</span> | 
|  | <span class="source-line-no">5078</span><span id="line-5078">      StartTestingClusterOption option = StartTestingClusterOption.builder()</span> | 
|  | <span class="source-line-no">5079</span><span id="line-5079">        .numRegionServers(regionServersCount).dataNodeHosts(dataNodeHosts).build();</span> | 
|  | <span class="source-line-no">5080</span><span id="line-5080">      cluster = htu.startMiniCluster(option);</span> | 
|  | <span class="source-line-no">5081</span><span id="line-5081">      byte[][] families = { fam1, fam2 };</span> | 
|  | <span class="source-line-no">5082</span><span id="line-5082">      Table ht = htu.createTable(tableName, families);</span> | 
|  | <span class="source-line-no">5083</span><span id="line-5083"></span> | 
|  | <span class="source-line-no">5084</span><span id="line-5084">      // Setting up region</span> | 
|  | <span class="source-line-no">5085</span><span id="line-5085">      byte row[] = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">5086</span><span id="line-5086">      byte col[] = Bytes.toBytes("col1");</span> | 
|  | <span class="source-line-no">5087</span><span id="line-5087"></span> | 
|  | <span class="source-line-no">5088</span><span id="line-5088">      Put put = new Put(row);</span> | 
|  | <span class="source-line-no">5089</span><span id="line-5089">      put.addColumn(fam1, col, 1, Bytes.toBytes("test1"));</span> | 
|  | <span class="source-line-no">5090</span><span id="line-5090">      put.addColumn(fam2, col, 1, Bytes.toBytes("test2"));</span> | 
|  | <span class="source-line-no">5091</span><span id="line-5091">      ht.put(put);</span> | 
|  | <span class="source-line-no">5092</span><span id="line-5092"></span> | 
|  | <span class="source-line-no">5093</span><span id="line-5093">      HRegion firstRegion = htu.getHBaseCluster().getRegions(tableName).get(0);</span> | 
|  | <span class="source-line-no">5094</span><span id="line-5094">      firstRegion.flush(true);</span> | 
|  | <span class="source-line-no">5095</span><span id="line-5095">      HDFSBlocksDistribution blocksDistribution1 = firstRegion.getHDFSBlocksDistribution();</span> | 
|  | <span class="source-line-no">5096</span><span id="line-5096"></span> | 
|  | <span class="source-line-no">5097</span><span id="line-5097">      // Given the default replication factor is 2 and we have 2 HFiles,</span> | 
|  | <span class="source-line-no">5098</span><span id="line-5098">      // we will have total of 4 replica of blocks on 3 datanodes; thus there</span> | 
|  | <span class="source-line-no">5099</span><span id="line-5099">      // must be at least one host that have replica for 2 HFiles. That host's</span> | 
|  | <span class="source-line-no">5100</span><span id="line-5100">      // weight will be equal to the unique block weight.</span> | 
|  | <span class="source-line-no">5101</span><span id="line-5101">      long uniqueBlocksWeight1 = blocksDistribution1.getUniqueBlocksTotalWeight();</span> | 
|  | <span class="source-line-no">5102</span><span id="line-5102">      StringBuilder sb = new StringBuilder();</span> | 
|  | <span class="source-line-no">5103</span><span id="line-5103">      for (String host : blocksDistribution1.getTopHosts()) {</span> | 
|  | <span class="source-line-no">5104</span><span id="line-5104">        if (sb.length() > 0) sb.append(", ");</span> | 
|  | <span class="source-line-no">5105</span><span id="line-5105">        sb.append(host);</span> | 
|  | <span class="source-line-no">5106</span><span id="line-5106">        sb.append("=");</span> | 
|  | <span class="source-line-no">5107</span><span id="line-5107">        sb.append(blocksDistribution1.getWeight(host));</span> | 
|  | <span class="source-line-no">5108</span><span id="line-5108">      }</span> | 
|  | <span class="source-line-no">5109</span><span id="line-5109"></span> | 
|  | <span class="source-line-no">5110</span><span id="line-5110">      String topHost = blocksDistribution1.getTopHosts().get(0);</span> | 
|  | <span class="source-line-no">5111</span><span id="line-5111">      long topHostWeight = blocksDistribution1.getWeight(topHost);</span> | 
|  | <span class="source-line-no">5112</span><span id="line-5112">      String msg = "uniqueBlocksWeight=" + uniqueBlocksWeight1 + ", topHostWeight=" + topHostWeight</span> | 
|  | <span class="source-line-no">5113</span><span id="line-5113">        + ", topHost=" + topHost + "; " + sb.toString();</span> | 
|  | <span class="source-line-no">5114</span><span id="line-5114">      LOG.info(msg);</span> | 
|  | <span class="source-line-no">5115</span><span id="line-5115">      assertTrue(msg, uniqueBlocksWeight1 == topHostWeight);</span> | 
|  | <span class="source-line-no">5116</span><span id="line-5116"></span> | 
|  | <span class="source-line-no">5117</span><span id="line-5117">      // use the static method to compute the value, it should be the same.</span> | 
|  | <span class="source-line-no">5118</span><span id="line-5118">      // static method is used by load balancer or other components</span> | 
|  | <span class="source-line-no">5119</span><span id="line-5119">      HDFSBlocksDistribution blocksDistribution2 = HRegion.computeHDFSBlocksDistribution(</span> | 
|  | <span class="source-line-no">5120</span><span id="line-5120">        htu.getConfiguration(), firstRegion.getTableDescriptor(), firstRegion.getRegionInfo());</span> | 
|  | <span class="source-line-no">5121</span><span id="line-5121">      long uniqueBlocksWeight2 = blocksDistribution2.getUniqueBlocksTotalWeight();</span> | 
|  | <span class="source-line-no">5122</span><span id="line-5122"></span> | 
|  | <span class="source-line-no">5123</span><span id="line-5123">      assertTrue(uniqueBlocksWeight1 == uniqueBlocksWeight2);</span> | 
|  | <span class="source-line-no">5124</span><span id="line-5124"></span> | 
|  | <span class="source-line-no">5125</span><span id="line-5125">      ht.close();</span> | 
|  | <span class="source-line-no">5126</span><span id="line-5126">    } finally {</span> | 
|  | <span class="source-line-no">5127</span><span id="line-5127">      if (cluster != null) {</span> | 
|  | <span class="source-line-no">5128</span><span id="line-5128">        htu.shutdownMiniCluster();</span> | 
|  | <span class="source-line-no">5129</span><span id="line-5129">      }</span> | 
|  | <span class="source-line-no">5130</span><span id="line-5130">    }</span> | 
|  | <span class="source-line-no">5131</span><span id="line-5131">  }</span> | 
|  | <span class="source-line-no">5132</span><span id="line-5132"></span> | 
|  | <span class="source-line-no">5133</span><span id="line-5133">  /**</span> | 
|  | <span class="source-line-no">5134</span><span id="line-5134">   * Testcase to check state of region initialization task set to ABORTED or not if any exceptions</span> | 
|  | <span class="source-line-no">5135</span><span id="line-5135">   * during initialization</span> | 
|  | <span class="source-line-no">5136</span><span id="line-5136">   */</span> | 
|  | <span class="source-line-no">5137</span><span id="line-5137">  @Test</span> | 
|  | <span class="source-line-no">5138</span><span id="line-5138">  public void testStatusSettingToAbortIfAnyExceptionDuringRegionInitilization() throws Exception {</span> | 
|  | <span class="source-line-no">5139</span><span id="line-5139">    RegionInfo info;</span> | 
|  | <span class="source-line-no">5140</span><span id="line-5140">    try {</span> | 
|  | <span class="source-line-no">5141</span><span id="line-5141">      FileSystem fs = mock(FileSystem.class);</span> | 
|  | <span class="source-line-no">5142</span><span id="line-5142">      when(fs.exists(any())).thenThrow(new IOException());</span> | 
|  | <span class="source-line-no">5143</span><span id="line-5143">      TableDescriptorBuilder tableDescriptorBuilder = TableDescriptorBuilder.newBuilder(tableName);</span> | 
|  | <span class="source-line-no">5144</span><span id="line-5144">      ColumnFamilyDescriptor columnFamilyDescriptor =</span> | 
|  | <span class="source-line-no">5145</span><span id="line-5145">        ColumnFamilyDescriptorBuilder.newBuilder(Bytes.toBytes("cf")).build();</span> | 
|  | <span class="source-line-no">5146</span><span id="line-5146">      tableDescriptorBuilder.setColumnFamily(columnFamilyDescriptor);</span> | 
|  | <span class="source-line-no">5147</span><span id="line-5147">      info = RegionInfoBuilder.newBuilder(tableName).build();</span> | 
|  | <span class="source-line-no">5148</span><span id="line-5148">      Path path = new Path(dir + "testStatusSettingToAbortIfAnyExceptionDuringRegionInitilization");</span> | 
|  | <span class="source-line-no">5149</span><span id="line-5149">      region = HRegion.newHRegion(path, null, fs, CONF, info, tableDescriptorBuilder.build(), null);</span> | 
|  | <span class="source-line-no">5150</span><span id="line-5150">      // region initialization throws IOException and set task state to ABORTED.</span> | 
|  | <span class="source-line-no">5151</span><span id="line-5151">      region.initialize();</span> | 
|  | <span class="source-line-no">5152</span><span id="line-5152">      fail("Region initialization should fail due to IOException");</span> | 
|  | <span class="source-line-no">5153</span><span id="line-5153">    } catch (IOException io) {</span> | 
|  | <span class="source-line-no">5154</span><span id="line-5154">      List<MonitoredTask> tasks = TaskMonitor.get().getTasks();</span> | 
|  | <span class="source-line-no">5155</span><span id="line-5155">      for (MonitoredTask monitoredTask : tasks) {</span> | 
|  | <span class="source-line-no">5156</span><span id="line-5156">        if (</span> | 
|  | <span class="source-line-no">5157</span><span id="line-5157">          !(monitoredTask instanceof MonitoredRPCHandler)</span> | 
|  | <span class="source-line-no">5158</span><span id="line-5158">            && monitoredTask.getDescription().contains(region.toString())</span> | 
|  | <span class="source-line-no">5159</span><span id="line-5159">        ) {</span> | 
|  | <span class="source-line-no">5160</span><span id="line-5160">          assertTrue("Region state should be ABORTED.",</span> | 
|  | <span class="source-line-no">5161</span><span id="line-5161">            monitoredTask.getState().equals(MonitoredTask.State.ABORTED));</span> | 
|  | <span class="source-line-no">5162</span><span id="line-5162">          break;</span> | 
|  | <span class="source-line-no">5163</span><span id="line-5163">        }</span> | 
|  | <span class="source-line-no">5164</span><span id="line-5164">      }</span> | 
|  | <span class="source-line-no">5165</span><span id="line-5165">    }</span> | 
|  | <span class="source-line-no">5166</span><span id="line-5166">  }</span> | 
|  | <span class="source-line-no">5167</span><span id="line-5167"></span> | 
|  | <span class="source-line-no">5168</span><span id="line-5168">  /**</span> | 
|  | <span class="source-line-no">5169</span><span id="line-5169">   * Verifies that the .regioninfo file is written on region creation and that is recreated if</span> | 
|  | <span class="source-line-no">5170</span><span id="line-5170">   * missing during region opening.</span> | 
|  | <span class="source-line-no">5171</span><span id="line-5171">   */</span> | 
|  | <span class="source-line-no">5172</span><span id="line-5172">  @Test</span> | 
|  | <span class="source-line-no">5173</span><span id="line-5173">  public void testRegionInfoFileCreation() throws IOException {</span> | 
|  | <span class="source-line-no">5174</span><span id="line-5174">    Path rootDir = new Path(dir + "testRegionInfoFileCreation");</span> | 
|  | <span class="source-line-no">5175</span><span id="line-5175"></span> | 
|  | <span class="source-line-no">5176</span><span id="line-5176">    TableDescriptorBuilder tableDescriptorBuilder =</span> | 
|  | <span class="source-line-no">5177</span><span id="line-5177">      TableDescriptorBuilder.newBuilder(TableName.valueOf(name.getMethodName()));</span> | 
|  | <span class="source-line-no">5178</span><span id="line-5178">    ColumnFamilyDescriptor columnFamilyDescriptor =</span> | 
|  | <span class="source-line-no">5179</span><span id="line-5179">      ColumnFamilyDescriptorBuilder.newBuilder(Bytes.toBytes("cf")).build();</span> | 
|  | <span class="source-line-no">5180</span><span id="line-5180">    tableDescriptorBuilder.setColumnFamily(columnFamilyDescriptor);</span> | 
|  | <span class="source-line-no">5181</span><span id="line-5181">    TableDescriptor tableDescriptor = tableDescriptorBuilder.build();</span> | 
|  | <span class="source-line-no">5182</span><span id="line-5182"></span> | 
|  | <span class="source-line-no">5183</span><span id="line-5183">    RegionInfo hri = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName()).build();</span> | 
|  | <span class="source-line-no">5184</span><span id="line-5184"></span> | 
|  | <span class="source-line-no">5185</span><span id="line-5185">    // Create a region and skip the initialization (like CreateTableHandler)</span> | 
|  | <span class="source-line-no">5186</span><span id="line-5186">    region = HBaseTestingUtil.createRegionAndWAL(hri, rootDir, CONF, tableDescriptor, false);</span> | 
|  | <span class="source-line-no">5187</span><span id="line-5187">    Path regionDir = region.getRegionFileSystem().getRegionDir();</span> | 
|  | <span class="source-line-no">5188</span><span id="line-5188">    FileSystem fs = region.getRegionFileSystem().getFileSystem();</span> | 
|  | <span class="source-line-no">5189</span><span id="line-5189">    HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">5190</span><span id="line-5190"></span> | 
|  | <span class="source-line-no">5191</span><span id="line-5191">    Path regionInfoFile = new Path(regionDir, HRegionFileSystem.REGION_INFO_FILE);</span> | 
|  | <span class="source-line-no">5192</span><span id="line-5192"></span> | 
|  | <span class="source-line-no">5193</span><span id="line-5193">    // Verify that the .regioninfo file is present</span> | 
|  | <span class="source-line-no">5194</span><span id="line-5194">    assertTrue(HRegionFileSystem.REGION_INFO_FILE + " should be present in the region dir",</span> | 
|  | <span class="source-line-no">5195</span><span id="line-5195">      fs.exists(regionInfoFile));</span> | 
|  | <span class="source-line-no">5196</span><span id="line-5196"></span> | 
|  | <span class="source-line-no">5197</span><span id="line-5197">    // Try to open the region</span> | 
|  | <span class="source-line-no">5198</span><span id="line-5198">    region = HRegion.openHRegion(rootDir, hri, tableDescriptor, null, CONF);</span> | 
|  | <span class="source-line-no">5199</span><span id="line-5199">    assertEquals(regionDir, region.getRegionFileSystem().getRegionDir());</span> | 
|  | <span class="source-line-no">5200</span><span id="line-5200">    HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">5201</span><span id="line-5201"></span> | 
|  | <span class="source-line-no">5202</span><span id="line-5202">    // Verify that the .regioninfo file is still there</span> | 
|  | <span class="source-line-no">5203</span><span id="line-5203">    assertTrue(HRegionFileSystem.REGION_INFO_FILE + " should be present in the region dir",</span> | 
|  | <span class="source-line-no">5204</span><span id="line-5204">      fs.exists(regionInfoFile));</span> | 
|  | <span class="source-line-no">5205</span><span id="line-5205"></span> | 
|  | <span class="source-line-no">5206</span><span id="line-5206">    // Remove the .regioninfo file and verify is recreated on region open</span> | 
|  | <span class="source-line-no">5207</span><span id="line-5207">    fs.delete(regionInfoFile, true);</span> | 
|  | <span class="source-line-no">5208</span><span id="line-5208">    assertFalse(HRegionFileSystem.REGION_INFO_FILE + " should be removed from the region dir",</span> | 
|  | <span class="source-line-no">5209</span><span id="line-5209">      fs.exists(regionInfoFile));</span> | 
|  | <span class="source-line-no">5210</span><span id="line-5210"></span> | 
|  | <span class="source-line-no">5211</span><span id="line-5211">    region = HRegion.openHRegion(rootDir, hri, tableDescriptor, null, CONF);</span> | 
|  | <span class="source-line-no">5212</span><span id="line-5212">    // region = TEST_UTIL.openHRegion(hri, htd);</span> | 
|  | <span class="source-line-no">5213</span><span id="line-5213">    assertEquals(regionDir, region.getRegionFileSystem().getRegionDir());</span> | 
|  | <span class="source-line-no">5214</span><span id="line-5214">    HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">5215</span><span id="line-5215"></span> | 
|  | <span class="source-line-no">5216</span><span id="line-5216">    // Verify that the .regioninfo file is still there</span> | 
|  | <span class="source-line-no">5217</span><span id="line-5217">    assertTrue(HRegionFileSystem.REGION_INFO_FILE + " should be present in the region dir",</span> | 
|  | <span class="source-line-no">5218</span><span id="line-5218">      fs.exists(new Path(regionDir, HRegionFileSystem.REGION_INFO_FILE)));</span> | 
|  | <span class="source-line-no">5219</span><span id="line-5219"></span> | 
|  | <span class="source-line-no">5220</span><span id="line-5220">    region = null;</span> | 
|  | <span class="source-line-no">5221</span><span id="line-5221">  }</span> | 
|  | <span class="source-line-no">5222</span><span id="line-5222"></span> | 
|  | <span class="source-line-no">5223</span><span id="line-5223">  /**</span> | 
|  | <span class="source-line-no">5224</span><span id="line-5224">   * TestCase for increment</span> | 
|  | <span class="source-line-no">5225</span><span id="line-5225">   */</span> | 
|  | <span class="source-line-no">5226</span><span id="line-5226">  private static class Incrementer implements Runnable {</span> | 
|  | <span class="source-line-no">5227</span><span id="line-5227">    private HRegion region;</span> | 
|  | <span class="source-line-no">5228</span><span id="line-5228">    private final static byte[] incRow = Bytes.toBytes("incRow");</span> | 
|  | <span class="source-line-no">5229</span><span id="line-5229">    private final static byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">5230</span><span id="line-5230">    private final static byte[] qualifier = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">5231</span><span id="line-5231">    private final static long ONE = 1L;</span> | 
|  | <span class="source-line-no">5232</span><span id="line-5232">    private int incCounter;</span> | 
|  | <span class="source-line-no">5233</span><span id="line-5233"></span> | 
|  | <span class="source-line-no">5234</span><span id="line-5234">    public Incrementer(HRegion region, int incCounter) {</span> | 
|  | <span class="source-line-no">5235</span><span id="line-5235">      this.region = region;</span> | 
|  | <span class="source-line-no">5236</span><span id="line-5236">      this.incCounter = incCounter;</span> | 
|  | <span class="source-line-no">5237</span><span id="line-5237">    }</span> | 
|  | <span class="source-line-no">5238</span><span id="line-5238"></span> | 
|  | <span class="source-line-no">5239</span><span id="line-5239">    @Override</span> | 
|  | <span class="source-line-no">5240</span><span id="line-5240">    public void run() {</span> | 
|  | <span class="source-line-no">5241</span><span id="line-5241">      int count = 0;</span> | 
|  | <span class="source-line-no">5242</span><span id="line-5242">      while (count < incCounter) {</span> | 
|  | <span class="source-line-no">5243</span><span id="line-5243">        Increment inc = new Increment(incRow);</span> | 
|  | <span class="source-line-no">5244</span><span id="line-5244">        inc.addColumn(family, qualifier, ONE);</span> | 
|  | <span class="source-line-no">5245</span><span id="line-5245">        count++;</span> | 
|  | <span class="source-line-no">5246</span><span id="line-5246">        try {</span> | 
|  | <span class="source-line-no">5247</span><span id="line-5247">          region.increment(inc);</span> | 
|  | <span class="source-line-no">5248</span><span id="line-5248">        } catch (IOException e) {</span> | 
|  | <span class="source-line-no">5249</span><span id="line-5249">          LOG.info("Count=" + count + ", " + e);</span> | 
|  | <span class="source-line-no">5250</span><span id="line-5250">          break;</span> | 
|  | <span class="source-line-no">5251</span><span id="line-5251">        }</span> | 
|  | <span class="source-line-no">5252</span><span id="line-5252">      }</span> | 
|  | <span class="source-line-no">5253</span><span id="line-5253">    }</span> | 
|  | <span class="source-line-no">5254</span><span id="line-5254">  }</span> | 
|  | <span class="source-line-no">5255</span><span id="line-5255"></span> | 
|  | <span class="source-line-no">5256</span><span id="line-5256">  /**</span> | 
|  | <span class="source-line-no">5257</span><span id="line-5257">   * Test case to check increment function with memstore flushing</span> | 
|  | <span class="source-line-no">5258</span><span id="line-5258">   */</span> | 
|  | <span class="source-line-no">5259</span><span id="line-5259">  @Test</span> | 
|  | <span class="source-line-no">5260</span><span id="line-5260">  public void testParallelIncrementWithMemStoreFlush() throws Exception {</span> | 
|  | <span class="source-line-no">5261</span><span id="line-5261">    byte[] family = Incrementer.family;</span> | 
|  | <span class="source-line-no">5262</span><span id="line-5262">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">5263</span><span id="line-5263">    final HRegion region = this.region;</span> | 
|  | <span class="source-line-no">5264</span><span id="line-5264">    final AtomicBoolean incrementDone = new AtomicBoolean(false);</span> | 
|  | <span class="source-line-no">5265</span><span id="line-5265">    Runnable flusher = new Runnable() {</span> | 
|  | <span class="source-line-no">5266</span><span id="line-5266">      @Override</span> | 
|  | <span class="source-line-no">5267</span><span id="line-5267">      public void run() {</span> | 
|  | <span class="source-line-no">5268</span><span id="line-5268">        while (!incrementDone.get()) {</span> | 
|  | <span class="source-line-no">5269</span><span id="line-5269">          try {</span> | 
|  | <span class="source-line-no">5270</span><span id="line-5270">            region.flush(true);</span> | 
|  | <span class="source-line-no">5271</span><span id="line-5271">          } catch (Exception e) {</span> | 
|  | <span class="source-line-no">5272</span><span id="line-5272">            e.printStackTrace();</span> | 
|  | <span class="source-line-no">5273</span><span id="line-5273">          }</span> | 
|  | <span class="source-line-no">5274</span><span id="line-5274">        }</span> | 
|  | <span class="source-line-no">5275</span><span id="line-5275">      }</span> | 
|  | <span class="source-line-no">5276</span><span id="line-5276">    };</span> | 
|  | <span class="source-line-no">5277</span><span id="line-5277"></span> | 
|  | <span class="source-line-no">5278</span><span id="line-5278">    // after all increment finished, the row will increment to 20*100 = 2000</span> | 
|  | <span class="source-line-no">5279</span><span id="line-5279">    int threadNum = 20;</span> | 
|  | <span class="source-line-no">5280</span><span id="line-5280">    int incCounter = 100;</span> | 
|  | <span class="source-line-no">5281</span><span id="line-5281">    long expected = (long) threadNum * incCounter;</span> | 
|  | <span class="source-line-no">5282</span><span id="line-5282">    Thread[] incrementers = new Thread[threadNum];</span> | 
|  | <span class="source-line-no">5283</span><span id="line-5283">    Thread flushThread = new Thread(flusher);</span> | 
|  | <span class="source-line-no">5284</span><span id="line-5284">    for (int i = 0; i < threadNum; i++) {</span> | 
|  | <span class="source-line-no">5285</span><span id="line-5285">      incrementers[i] = new Thread(new Incrementer(this.region, incCounter));</span> | 
|  | <span class="source-line-no">5286</span><span id="line-5286">      incrementers[i].start();</span> | 
|  | <span class="source-line-no">5287</span><span id="line-5287">    }</span> | 
|  | <span class="source-line-no">5288</span><span id="line-5288">    flushThread.start();</span> | 
|  | <span class="source-line-no">5289</span><span id="line-5289">    for (int i = 0; i < threadNum; i++) {</span> | 
|  | <span class="source-line-no">5290</span><span id="line-5290">      incrementers[i].join();</span> | 
|  | <span class="source-line-no">5291</span><span id="line-5291">    }</span> | 
|  | <span class="source-line-no">5292</span><span id="line-5292"></span> | 
|  | <span class="source-line-no">5293</span><span id="line-5293">    incrementDone.set(true);</span> | 
|  | <span class="source-line-no">5294</span><span id="line-5294">    flushThread.join();</span> | 
|  | <span class="source-line-no">5295</span><span id="line-5295"></span> | 
|  | <span class="source-line-no">5296</span><span id="line-5296">    Get get = new Get(Incrementer.incRow);</span> | 
|  | <span class="source-line-no">5297</span><span id="line-5297">    get.addColumn(Incrementer.family, Incrementer.qualifier);</span> | 
|  | <span class="source-line-no">5298</span><span id="line-5298">    get.readVersions(1);</span> | 
|  | <span class="source-line-no">5299</span><span id="line-5299">    Result res = this.region.get(get);</span> | 
|  | <span class="source-line-no">5300</span><span id="line-5300">    List<Cell> kvs = res.getColumnCells(Incrementer.family, Incrementer.qualifier);</span> | 
|  | <span class="source-line-no">5301</span><span id="line-5301"></span> | 
|  | <span class="source-line-no">5302</span><span id="line-5302">    // we just got the latest version</span> | 
|  | <span class="source-line-no">5303</span><span id="line-5303">    assertEquals(1, kvs.size());</span> | 
|  | <span class="source-line-no">5304</span><span id="line-5304">    Cell kv = kvs.get(0);</span> | 
|  | <span class="source-line-no">5305</span><span id="line-5305">    assertEquals(expected, Bytes.toLong(kv.getValueArray(), kv.getValueOffset()));</span> | 
|  | <span class="source-line-no">5306</span><span id="line-5306">  }</span> | 
|  | <span class="source-line-no">5307</span><span id="line-5307"></span> | 
|  | <span class="source-line-no">5308</span><span id="line-5308">  /**</span> | 
|  | <span class="source-line-no">5309</span><span id="line-5309">   * TestCase for append</span> | 
|  | <span class="source-line-no">5310</span><span id="line-5310">   */</span> | 
|  | <span class="source-line-no">5311</span><span id="line-5311">  private static class Appender implements Runnable {</span> | 
|  | <span class="source-line-no">5312</span><span id="line-5312">    private HRegion region;</span> | 
|  | <span class="source-line-no">5313</span><span id="line-5313">    private final static byte[] appendRow = Bytes.toBytes("appendRow");</span> | 
|  | <span class="source-line-no">5314</span><span id="line-5314">    private final static byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">5315</span><span id="line-5315">    private final static byte[] qualifier = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">5316</span><span id="line-5316">    private final static byte[] CHAR = Bytes.toBytes("a");</span> | 
|  | <span class="source-line-no">5317</span><span id="line-5317">    private int appendCounter;</span> | 
|  | <span class="source-line-no">5318</span><span id="line-5318"></span> | 
|  | <span class="source-line-no">5319</span><span id="line-5319">    public Appender(HRegion region, int appendCounter) {</span> | 
|  | <span class="source-line-no">5320</span><span id="line-5320">      this.region = region;</span> | 
|  | <span class="source-line-no">5321</span><span id="line-5321">      this.appendCounter = appendCounter;</span> | 
|  | <span class="source-line-no">5322</span><span id="line-5322">    }</span> | 
|  | <span class="source-line-no">5323</span><span id="line-5323"></span> | 
|  | <span class="source-line-no">5324</span><span id="line-5324">    @Override</span> | 
|  | <span class="source-line-no">5325</span><span id="line-5325">    public void run() {</span> | 
|  | <span class="source-line-no">5326</span><span id="line-5326">      int count = 0;</span> | 
|  | <span class="source-line-no">5327</span><span id="line-5327">      while (count < appendCounter) {</span> | 
|  | <span class="source-line-no">5328</span><span id="line-5328">        Append app = new Append(appendRow);</span> | 
|  | <span class="source-line-no">5329</span><span id="line-5329">        app.addColumn(family, qualifier, CHAR);</span> | 
|  | <span class="source-line-no">5330</span><span id="line-5330">        count++;</span> | 
|  | <span class="source-line-no">5331</span><span id="line-5331">        try {</span> | 
|  | <span class="source-line-no">5332</span><span id="line-5332">          region.append(app);</span> | 
|  | <span class="source-line-no">5333</span><span id="line-5333">        } catch (IOException e) {</span> | 
|  | <span class="source-line-no">5334</span><span id="line-5334">          LOG.info("Count=" + count + ", max=" + appendCounter + ", " + e);</span> | 
|  | <span class="source-line-no">5335</span><span id="line-5335">          break;</span> | 
|  | <span class="source-line-no">5336</span><span id="line-5336">        }</span> | 
|  | <span class="source-line-no">5337</span><span id="line-5337">      }</span> | 
|  | <span class="source-line-no">5338</span><span id="line-5338">    }</span> | 
|  | <span class="source-line-no">5339</span><span id="line-5339">  }</span> | 
|  | <span class="source-line-no">5340</span><span id="line-5340"></span> | 
|  | <span class="source-line-no">5341</span><span id="line-5341">  /**</span> | 
|  | <span class="source-line-no">5342</span><span id="line-5342">   * Test case to check append function with memstore flushing</span> | 
|  | <span class="source-line-no">5343</span><span id="line-5343">   */</span> | 
|  | <span class="source-line-no">5344</span><span id="line-5344">  @Test</span> | 
|  | <span class="source-line-no">5345</span><span id="line-5345">  public void testParallelAppendWithMemStoreFlush() throws Exception {</span> | 
|  | <span class="source-line-no">5346</span><span id="line-5346">    byte[] family = Appender.family;</span> | 
|  | <span class="source-line-no">5347</span><span id="line-5347">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">5348</span><span id="line-5348">    final HRegion region = this.region;</span> | 
|  | <span class="source-line-no">5349</span><span id="line-5349">    final AtomicBoolean appendDone = new AtomicBoolean(false);</span> | 
|  | <span class="source-line-no">5350</span><span id="line-5350">    Runnable flusher = new Runnable() {</span> | 
|  | <span class="source-line-no">5351</span><span id="line-5351">      @Override</span> | 
|  | <span class="source-line-no">5352</span><span id="line-5352">      public void run() {</span> | 
|  | <span class="source-line-no">5353</span><span id="line-5353">        while (!appendDone.get()) {</span> | 
|  | <span class="source-line-no">5354</span><span id="line-5354">          try {</span> | 
|  | <span class="source-line-no">5355</span><span id="line-5355">            region.flush(true);</span> | 
|  | <span class="source-line-no">5356</span><span id="line-5356">          } catch (Exception e) {</span> | 
|  | <span class="source-line-no">5357</span><span id="line-5357">            e.printStackTrace();</span> | 
|  | <span class="source-line-no">5358</span><span id="line-5358">          }</span> | 
|  | <span class="source-line-no">5359</span><span id="line-5359">        }</span> | 
|  | <span class="source-line-no">5360</span><span id="line-5360">      }</span> | 
|  | <span class="source-line-no">5361</span><span id="line-5361">    };</span> | 
|  | <span class="source-line-no">5362</span><span id="line-5362"></span> | 
|  | <span class="source-line-no">5363</span><span id="line-5363">    // After all append finished, the value will append to threadNum *</span> | 
|  | <span class="source-line-no">5364</span><span id="line-5364">    // appendCounter Appender.CHAR</span> | 
|  | <span class="source-line-no">5365</span><span id="line-5365">    int threadNum = 20;</span> | 
|  | <span class="source-line-no">5366</span><span id="line-5366">    int appendCounter = 100;</span> | 
|  | <span class="source-line-no">5367</span><span id="line-5367">    byte[] expected = new byte[threadNum * appendCounter];</span> | 
|  | <span class="source-line-no">5368</span><span id="line-5368">    for (int i = 0; i < threadNum * appendCounter; i++) {</span> | 
|  | <span class="source-line-no">5369</span><span id="line-5369">      System.arraycopy(Appender.CHAR, 0, expected, i, 1);</span> | 
|  | <span class="source-line-no">5370</span><span id="line-5370">    }</span> | 
|  | <span class="source-line-no">5371</span><span id="line-5371">    Thread[] appenders = new Thread[threadNum];</span> | 
|  | <span class="source-line-no">5372</span><span id="line-5372">    Thread flushThread = new Thread(flusher);</span> | 
|  | <span class="source-line-no">5373</span><span id="line-5373">    for (int i = 0; i < threadNum; i++) {</span> | 
|  | <span class="source-line-no">5374</span><span id="line-5374">      appenders[i] = new Thread(new Appender(this.region, appendCounter));</span> | 
|  | <span class="source-line-no">5375</span><span id="line-5375">      appenders[i].start();</span> | 
|  | <span class="source-line-no">5376</span><span id="line-5376">    }</span> | 
|  | <span class="source-line-no">5377</span><span id="line-5377">    flushThread.start();</span> | 
|  | <span class="source-line-no">5378</span><span id="line-5378">    for (int i = 0; i < threadNum; i++) {</span> | 
|  | <span class="source-line-no">5379</span><span id="line-5379">      appenders[i].join();</span> | 
|  | <span class="source-line-no">5380</span><span id="line-5380">    }</span> | 
|  | <span class="source-line-no">5381</span><span id="line-5381"></span> | 
|  | <span class="source-line-no">5382</span><span id="line-5382">    appendDone.set(true);</span> | 
|  | <span class="source-line-no">5383</span><span id="line-5383">    flushThread.join();</span> | 
|  | <span class="source-line-no">5384</span><span id="line-5384"></span> | 
|  | <span class="source-line-no">5385</span><span id="line-5385">    Get get = new Get(Appender.appendRow);</span> | 
|  | <span class="source-line-no">5386</span><span id="line-5386">    get.addColumn(Appender.family, Appender.qualifier);</span> | 
|  | <span class="source-line-no">5387</span><span id="line-5387">    get.readVersions(1);</span> | 
|  | <span class="source-line-no">5388</span><span id="line-5388">    Result res = this.region.get(get);</span> | 
|  | <span class="source-line-no">5389</span><span id="line-5389">    List<Cell> kvs = res.getColumnCells(Appender.family, Appender.qualifier);</span> | 
|  | <span class="source-line-no">5390</span><span id="line-5390"></span> | 
|  | <span class="source-line-no">5391</span><span id="line-5391">    // we just got the latest version</span> | 
|  | <span class="source-line-no">5392</span><span id="line-5392">    assertEquals(1, kvs.size());</span> | 
|  | <span class="source-line-no">5393</span><span id="line-5393">    Cell kv = kvs.get(0);</span> | 
|  | <span class="source-line-no">5394</span><span id="line-5394">    byte[] appendResult = new byte[kv.getValueLength()];</span> | 
|  | <span class="source-line-no">5395</span><span id="line-5395">    System.arraycopy(kv.getValueArray(), kv.getValueOffset(), appendResult, 0, kv.getValueLength());</span> | 
|  | <span class="source-line-no">5396</span><span id="line-5396">    assertArrayEquals(expected, appendResult);</span> | 
|  | <span class="source-line-no">5397</span><span id="line-5397">  }</span> | 
|  | <span class="source-line-no">5398</span><span id="line-5398"></span> | 
|  | <span class="source-line-no">5399</span><span id="line-5399">  /**</span> | 
|  | <span class="source-line-no">5400</span><span id="line-5400">   * Test case to check put function with memstore flushing for same row, same ts</span> | 
|  | <span class="source-line-no">5401</span><span id="line-5401">   */</span> | 
|  | <span class="source-line-no">5402</span><span id="line-5402">  @Test</span> | 
|  | <span class="source-line-no">5403</span><span id="line-5403">  public void testPutWithMemStoreFlush() throws Exception {</span> | 
|  | <span class="source-line-no">5404</span><span id="line-5404">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">5405</span><span id="line-5405">    byte[] qualifier = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">5406</span><span id="line-5406">    byte[] row = Bytes.toBytes("putRow");</span> | 
|  | <span class="source-line-no">5407</span><span id="line-5407">    byte[] value = null;</span> | 
|  | <span class="source-line-no">5408</span><span id="line-5408">    this.region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">5409</span><span id="line-5409">    Put put = null;</span> | 
|  | <span class="source-line-no">5410</span><span id="line-5410">    Get get = null;</span> | 
|  | <span class="source-line-no">5411</span><span id="line-5411">    List<Cell> kvs = null;</span> | 
|  | <span class="source-line-no">5412</span><span id="line-5412">    Result res = null;</span> | 
|  | <span class="source-line-no">5413</span><span id="line-5413"></span> | 
|  | <span class="source-line-no">5414</span><span id="line-5414">    put = new Put(row);</span> | 
|  | <span class="source-line-no">5415</span><span id="line-5415">    value = Bytes.toBytes("value0");</span> | 
|  | <span class="source-line-no">5416</span><span id="line-5416">    put.addColumn(family, qualifier, 1234567L, value);</span> | 
|  | <span class="source-line-no">5417</span><span id="line-5417">    region.put(put);</span> | 
|  | <span class="source-line-no">5418</span><span id="line-5418">    get = new Get(row);</span> | 
|  | <span class="source-line-no">5419</span><span id="line-5419">    get.addColumn(family, qualifier);</span> | 
|  | <span class="source-line-no">5420</span><span id="line-5420">    get.readAllVersions();</span> | 
|  | <span class="source-line-no">5421</span><span id="line-5421">    res = this.region.get(get);</span> | 
|  | <span class="source-line-no">5422</span><span id="line-5422">    kvs = res.getColumnCells(family, qualifier);</span> | 
|  | <span class="source-line-no">5423</span><span id="line-5423">    assertEquals(1, kvs.size());</span> | 
|  | <span class="source-line-no">5424</span><span id="line-5424">    assertArrayEquals(Bytes.toBytes("value0"), CellUtil.cloneValue(kvs.get(0)));</span> | 
|  | <span class="source-line-no">5425</span><span id="line-5425"></span> | 
|  | <span class="source-line-no">5426</span><span id="line-5426">    region.flush(true);</span> | 
|  | <span class="source-line-no">5427</span><span id="line-5427">    get = new Get(row);</span> | 
|  | <span class="source-line-no">5428</span><span id="line-5428">    get.addColumn(family, qualifier);</span> | 
|  | <span class="source-line-no">5429</span><span id="line-5429">    get.readAllVersions();</span> | 
|  | <span class="source-line-no">5430</span><span id="line-5430">    res = this.region.get(get);</span> | 
|  | <span class="source-line-no">5431</span><span id="line-5431">    kvs = res.getColumnCells(family, qualifier);</span> | 
|  | <span class="source-line-no">5432</span><span id="line-5432">    assertEquals(1, kvs.size());</span> | 
|  | <span class="source-line-no">5433</span><span id="line-5433">    assertArrayEquals(Bytes.toBytes("value0"), CellUtil.cloneValue(kvs.get(0)));</span> | 
|  | <span class="source-line-no">5434</span><span id="line-5434"></span> | 
|  | <span class="source-line-no">5435</span><span id="line-5435">    put = new Put(row);</span> | 
|  | <span class="source-line-no">5436</span><span id="line-5436">    value = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">5437</span><span id="line-5437">    put.addColumn(family, qualifier, 1234567L, value);</span> | 
|  | <span class="source-line-no">5438</span><span id="line-5438">    region.put(put);</span> | 
|  | <span class="source-line-no">5439</span><span id="line-5439">    get = new Get(row);</span> | 
|  | <span class="source-line-no">5440</span><span id="line-5440">    get.addColumn(family, qualifier);</span> | 
|  | <span class="source-line-no">5441</span><span id="line-5441">    get.readAllVersions();</span> | 
|  | <span class="source-line-no">5442</span><span id="line-5442">    res = this.region.get(get);</span> | 
|  | <span class="source-line-no">5443</span><span id="line-5443">    kvs = res.getColumnCells(family, qualifier);</span> | 
|  | <span class="source-line-no">5444</span><span id="line-5444">    assertEquals(1, kvs.size());</span> | 
|  | <span class="source-line-no">5445</span><span id="line-5445">    assertArrayEquals(Bytes.toBytes("value1"), CellUtil.cloneValue(kvs.get(0)));</span> | 
|  | <span class="source-line-no">5446</span><span id="line-5446"></span> | 
|  | <span class="source-line-no">5447</span><span id="line-5447">    region.flush(true);</span> | 
|  | <span class="source-line-no">5448</span><span id="line-5448">    get = new Get(row);</span> | 
|  | <span class="source-line-no">5449</span><span id="line-5449">    get.addColumn(family, qualifier);</span> | 
|  | <span class="source-line-no">5450</span><span id="line-5450">    get.readAllVersions();</span> | 
|  | <span class="source-line-no">5451</span><span id="line-5451">    res = this.region.get(get);</span> | 
|  | <span class="source-line-no">5452</span><span id="line-5452">    kvs = res.getColumnCells(family, qualifier);</span> | 
|  | <span class="source-line-no">5453</span><span id="line-5453">    assertEquals(1, kvs.size());</span> | 
|  | <span class="source-line-no">5454</span><span id="line-5454">    assertArrayEquals(Bytes.toBytes("value1"), CellUtil.cloneValue(kvs.get(0)));</span> | 
|  | <span class="source-line-no">5455</span><span id="line-5455">  }</span> | 
|  | <span class="source-line-no">5456</span><span id="line-5456"></span> | 
|  | <span class="source-line-no">5457</span><span id="line-5457">  /**</span> | 
|  | <span class="source-line-no">5458</span><span id="line-5458">   * For this test,the spied {@link AsyncFSWAL} can not work properly because of a Mockito defect</span> | 
|  | <span class="source-line-no">5459</span><span id="line-5459">   * that can not deal with classes which have a field of an inner class. See discussions in</span> | 
|  | <span class="source-line-no">5460</span><span id="line-5460">   * HBASE-15536.When we reuse the code of {@link AsyncFSWAL} for {@link FSHLog}, this test could</span> | 
|  | <span class="source-line-no">5461</span><span id="line-5461">   * not work for {@link FSHLog} also.</span> | 
|  | <span class="source-line-no">5462</span><span id="line-5462">   */</span> | 
|  | <span class="source-line-no">5463</span><span id="line-5463">  @Test</span> | 
|  | <span class="source-line-no">5464</span><span id="line-5464">  @Ignore</span> | 
|  | <span class="source-line-no">5465</span><span id="line-5465">  public void testDurability() throws Exception {</span> | 
|  | <span class="source-line-no">5466</span><span id="line-5466">    // there are 5 x 5 cases:</span> | 
|  | <span class="source-line-no">5467</span><span id="line-5467">    // table durability(SYNC,FSYNC,ASYC,SKIP,USE_DEFAULT) x mutation</span> | 
|  | <span class="source-line-no">5468</span><span id="line-5468">    // durability(SYNC,FSYNC,ASYC,SKIP,USE_DEFAULT)</span> | 
|  | <span class="source-line-no">5469</span><span id="line-5469"></span> | 
|  | <span class="source-line-no">5470</span><span id="line-5470">    // expected cases for append and sync wal</span> | 
|  | <span class="source-line-no">5471</span><span id="line-5471">    durabilityTest(method, Durability.SYNC_WAL, Durability.SYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5472</span><span id="line-5472">    durabilityTest(method, Durability.SYNC_WAL, Durability.FSYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5473</span><span id="line-5473">    durabilityTest(method, Durability.SYNC_WAL, Durability.USE_DEFAULT, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5474</span><span id="line-5474"></span> | 
|  | <span class="source-line-no">5475</span><span id="line-5475">    durabilityTest(method, Durability.FSYNC_WAL, Durability.SYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5476</span><span id="line-5476">    durabilityTest(method, Durability.FSYNC_WAL, Durability.FSYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5477</span><span id="line-5477">    durabilityTest(method, Durability.FSYNC_WAL, Durability.USE_DEFAULT, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5478</span><span id="line-5478"></span> | 
|  | <span class="source-line-no">5479</span><span id="line-5479">    durabilityTest(method, Durability.ASYNC_WAL, Durability.SYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5480</span><span id="line-5480">    durabilityTest(method, Durability.ASYNC_WAL, Durability.FSYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5481</span><span id="line-5481"></span> | 
|  | <span class="source-line-no">5482</span><span id="line-5482">    durabilityTest(method, Durability.SKIP_WAL, Durability.SYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5483</span><span id="line-5483">    durabilityTest(method, Durability.SKIP_WAL, Durability.FSYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5484</span><span id="line-5484"></span> | 
|  | <span class="source-line-no">5485</span><span id="line-5485">    durabilityTest(method, Durability.USE_DEFAULT, Durability.SYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5486</span><span id="line-5486">    durabilityTest(method, Durability.USE_DEFAULT, Durability.FSYNC_WAL, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5487</span><span id="line-5487">    durabilityTest(method, Durability.USE_DEFAULT, Durability.USE_DEFAULT, 0, true, true, false);</span> | 
|  | <span class="source-line-no">5488</span><span id="line-5488"></span> | 
|  | <span class="source-line-no">5489</span><span id="line-5489">    // expected cases for async wal</span> | 
|  | <span class="source-line-no">5490</span><span id="line-5490">    durabilityTest(method, Durability.SYNC_WAL, Durability.ASYNC_WAL, 0, true, false, false);</span> | 
|  | <span class="source-line-no">5491</span><span id="line-5491">    durabilityTest(method, Durability.FSYNC_WAL, Durability.ASYNC_WAL, 0, true, false, false);</span> | 
|  | <span class="source-line-no">5492</span><span id="line-5492">    durabilityTest(method, Durability.ASYNC_WAL, Durability.ASYNC_WAL, 0, true, false, false);</span> | 
|  | <span class="source-line-no">5493</span><span id="line-5493">    durabilityTest(method, Durability.SKIP_WAL, Durability.ASYNC_WAL, 0, true, false, false);</span> | 
|  | <span class="source-line-no">5494</span><span id="line-5494">    durabilityTest(method, Durability.USE_DEFAULT, Durability.ASYNC_WAL, 0, true, false, false);</span> | 
|  | <span class="source-line-no">5495</span><span id="line-5495">    durabilityTest(method, Durability.ASYNC_WAL, Durability.USE_DEFAULT, 0, true, false, false);</span> | 
|  | <span class="source-line-no">5496</span><span id="line-5496"></span> | 
|  | <span class="source-line-no">5497</span><span id="line-5497">    durabilityTest(method, Durability.SYNC_WAL, Durability.ASYNC_WAL, 5000, true, false, true);</span> | 
|  | <span class="source-line-no">5498</span><span id="line-5498">    durabilityTest(method, Durability.FSYNC_WAL, Durability.ASYNC_WAL, 5000, true, false, true);</span> | 
|  | <span class="source-line-no">5499</span><span id="line-5499">    durabilityTest(method, Durability.ASYNC_WAL, Durability.ASYNC_WAL, 5000, true, false, true);</span> | 
|  | <span class="source-line-no">5500</span><span id="line-5500">    durabilityTest(method, Durability.SKIP_WAL, Durability.ASYNC_WAL, 5000, true, false, true);</span> | 
|  | <span class="source-line-no">5501</span><span id="line-5501">    durabilityTest(method, Durability.USE_DEFAULT, Durability.ASYNC_WAL, 5000, true, false, true);</span> | 
|  | <span class="source-line-no">5502</span><span id="line-5502">    durabilityTest(method, Durability.ASYNC_WAL, Durability.USE_DEFAULT, 5000, true, false, true);</span> | 
|  | <span class="source-line-no">5503</span><span id="line-5503"></span> | 
|  | <span class="source-line-no">5504</span><span id="line-5504">    // expect skip wal cases</span> | 
|  | <span class="source-line-no">5505</span><span id="line-5505">    durabilityTest(method, Durability.SYNC_WAL, Durability.SKIP_WAL, 0, false, false, false);</span> | 
|  | <span class="source-line-no">5506</span><span id="line-5506">    durabilityTest(method, Durability.FSYNC_WAL, Durability.SKIP_WAL, 0, false, false, false);</span> | 
|  | <span class="source-line-no">5507</span><span id="line-5507">    durabilityTest(method, Durability.ASYNC_WAL, Durability.SKIP_WAL, 0, false, false, false);</span> | 
|  | <span class="source-line-no">5508</span><span id="line-5508">    durabilityTest(method, Durability.SKIP_WAL, Durability.SKIP_WAL, 0, false, false, false);</span> | 
|  | <span class="source-line-no">5509</span><span id="line-5509">    durabilityTest(method, Durability.USE_DEFAULT, Durability.SKIP_WAL, 0, false, false, false);</span> | 
|  | <span class="source-line-no">5510</span><span id="line-5510">    durabilityTest(method, Durability.SKIP_WAL, Durability.USE_DEFAULT, 0, false, false, false);</span> | 
|  | <span class="source-line-no">5511</span><span id="line-5511"></span> | 
|  | <span class="source-line-no">5512</span><span id="line-5512">  }</span> | 
|  | <span class="source-line-no">5513</span><span id="line-5513"></span> | 
|  | <span class="source-line-no">5514</span><span id="line-5514">  private void durabilityTest(String method, Durability tableDurability,</span> | 
|  | <span class="source-line-no">5515</span><span id="line-5515">    Durability mutationDurability, long timeout, boolean expectAppend, final boolean expectSync,</span> | 
|  | <span class="source-line-no">5516</span><span id="line-5516">    final boolean expectSyncFromLogSyncer) throws Exception {</span> | 
|  | <span class="source-line-no">5517</span><span id="line-5517">    Configuration conf = HBaseConfiguration.create(CONF);</span> | 
|  | <span class="source-line-no">5518</span><span id="line-5518">    conf.setLong(AbstractFSWAL.WAL_SHUTDOWN_WAIT_TIMEOUT_MS, 60 * 60 * 1000);</span> | 
|  | <span class="source-line-no">5519</span><span id="line-5519">    method = method + "_" + tableDurability.name() + "_" + mutationDurability.name();</span> | 
|  | <span class="source-line-no">5520</span><span id="line-5520">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">5521</span><span id="line-5521">    Path logDir = new Path(new Path(dir + method), "log");</span> | 
|  | <span class="source-line-no">5522</span><span id="line-5522">    final Configuration walConf = new Configuration(conf);</span> | 
|  | <span class="source-line-no">5523</span><span id="line-5523">    CommonFSUtils.setRootDir(walConf, logDir);</span> | 
|  | <span class="source-line-no">5524</span><span id="line-5524">    // XXX: The spied AsyncFSWAL can not work properly because of a Mockito defect that can not</span> | 
|  | <span class="source-line-no">5525</span><span id="line-5525">    // deal with classes which have a field of an inner class. See discussions in HBASE-15536.</span> | 
|  | <span class="source-line-no">5526</span><span id="line-5526">    walConf.set(WALFactory.WAL_PROVIDER, "filesystem");</span> | 
|  | <span class="source-line-no">5527</span><span id="line-5527">    final WALFactory wals = new WALFactory(walConf, HBaseTestingUtil.getRandomUUID().toString());</span> | 
|  | <span class="source-line-no">5528</span><span id="line-5528">    final WAL wal = spy(wals.getWAL(RegionInfoBuilder.newBuilder(tableName).build()));</span> | 
|  | <span class="source-line-no">5529</span><span id="line-5529">    this.region = initHRegion(tableName, HConstants.EMPTY_START_ROW, HConstants.EMPTY_END_ROW, CONF,</span> | 
|  | <span class="source-line-no">5530</span><span id="line-5530">      false, tableDurability, wal, new byte[][] { family });</span> | 
|  | <span class="source-line-no">5531</span><span id="line-5531"></span> | 
|  | <span class="source-line-no">5532</span><span id="line-5532">    Put put = new Put(Bytes.toBytes("r1"));</span> | 
|  | <span class="source-line-no">5533</span><span id="line-5533">    put.addColumn(family, Bytes.toBytes("q1"), Bytes.toBytes("v1"));</span> | 
|  | <span class="source-line-no">5534</span><span id="line-5534">    put.setDurability(mutationDurability);</span> | 
|  | <span class="source-line-no">5535</span><span id="line-5535">    region.put(put);</span> | 
|  | <span class="source-line-no">5536</span><span id="line-5536"></span> | 
|  | <span class="source-line-no">5537</span><span id="line-5537">    // verify append called or not</span> | 
|  | <span class="source-line-no">5538</span><span id="line-5538">    verify(wal, expectAppend ? times(1) : never()).appendData((RegionInfo) any(),</span> | 
|  | <span class="source-line-no">5539</span><span id="line-5539">      (WALKeyImpl) any(), (WALEdit) any());</span> | 
|  | <span class="source-line-no">5540</span><span id="line-5540"></span> | 
|  | <span class="source-line-no">5541</span><span id="line-5541">    // verify sync called or not</span> | 
|  | <span class="source-line-no">5542</span><span id="line-5542">    if (expectSync || expectSyncFromLogSyncer) {</span> | 
|  | <span class="source-line-no">5543</span><span id="line-5543">      TEST_UTIL.waitFor(timeout, new Waiter.Predicate<Exception>() {</span> | 
|  | <span class="source-line-no">5544</span><span id="line-5544">        @Override</span> | 
|  | <span class="source-line-no">5545</span><span id="line-5545">        public boolean evaluate() throws Exception {</span> | 
|  | <span class="source-line-no">5546</span><span id="line-5546">          try {</span> | 
|  | <span class="source-line-no">5547</span><span id="line-5547">            if (expectSync) {</span> | 
|  | <span class="source-line-no">5548</span><span id="line-5548">              verify(wal, times(1)).sync(anyLong()); // Hregion calls this one</span> | 
|  | <span class="source-line-no">5549</span><span id="line-5549">            } else if (expectSyncFromLogSyncer) {</span> | 
|  | <span class="source-line-no">5550</span><span id="line-5550">              verify(wal, times(1)).sync(); // wal syncer calls this one</span> | 
|  | <span class="source-line-no">5551</span><span id="line-5551">            }</span> | 
|  | <span class="source-line-no">5552</span><span id="line-5552">          } catch (Throwable ignore) {</span> | 
|  | <span class="source-line-no">5553</span><span id="line-5553">          }</span> | 
|  | <span class="source-line-no">5554</span><span id="line-5554">          return true;</span> | 
|  | <span class="source-line-no">5555</span><span id="line-5555">        }</span> | 
|  | <span class="source-line-no">5556</span><span id="line-5556">      });</span> | 
|  | <span class="source-line-no">5557</span><span id="line-5557">    } else {</span> | 
|  | <span class="source-line-no">5558</span><span id="line-5558">      // verify(wal, never()).sync(anyLong());</span> | 
|  | <span class="source-line-no">5559</span><span id="line-5559">      verify(wal, never()).sync();</span> | 
|  | <span class="source-line-no">5560</span><span id="line-5560">    }</span> | 
|  | <span class="source-line-no">5561</span><span id="line-5561"></span> | 
|  | <span class="source-line-no">5562</span><span id="line-5562">    HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">5563</span><span id="line-5563">    wals.close();</span> | 
|  | <span class="source-line-no">5564</span><span id="line-5564">    this.region = null;</span> | 
|  | <span class="source-line-no">5565</span><span id="line-5565">  }</span> | 
|  | <span class="source-line-no">5566</span><span id="line-5566"></span> | 
|  | <span class="source-line-no">5567</span><span id="line-5567">  @Test</span> | 
|  | <span class="source-line-no">5568</span><span id="line-5568">  public void testRegionReplicaSecondary() throws IOException {</span> | 
|  | <span class="source-line-no">5569</span><span id="line-5569">    // create a primary region, load some data and flush</span> | 
|  | <span class="source-line-no">5570</span><span id="line-5570">    // create a secondary region, and do a get against that</span> | 
|  | <span class="source-line-no">5571</span><span id="line-5571">    Path rootDir = new Path(dir + name.getMethodName());</span> | 
|  | <span class="source-line-no">5572</span><span id="line-5572">    CommonFSUtils.setRootDir(TEST_UTIL.getConfiguration(), rootDir);</span> | 
|  | <span class="source-line-no">5573</span><span id="line-5573"></span> | 
|  | <span class="source-line-no">5574</span><span id="line-5574">    byte[][] families =</span> | 
|  | <span class="source-line-no">5575</span><span id="line-5575">      new byte[][] { Bytes.toBytes("cf1"), Bytes.toBytes("cf2"), Bytes.toBytes("cf3") };</span> | 
|  | <span class="source-line-no">5576</span><span id="line-5576">    byte[] cq = Bytes.toBytes("cq");</span> | 
|  | <span class="source-line-no">5577</span><span id="line-5577">    TableDescriptorBuilder builder =</span> | 
|  | <span class="source-line-no">5578</span><span id="line-5578">      TableDescriptorBuilder.newBuilder(TableName.valueOf(name.getMethodName()));</span> | 
|  | <span class="source-line-no">5579</span><span id="line-5579">    for (byte[] family : families) {</span> | 
|  | <span class="source-line-no">5580</span><span id="line-5580">      builder.setColumnFamily(ColumnFamilyDescriptorBuilder.of(family));</span> | 
|  | <span class="source-line-no">5581</span><span id="line-5581">    }</span> | 
|  | <span class="source-line-no">5582</span><span id="line-5582">    TableDescriptor tableDescriptor = builder.build();</span> | 
|  | <span class="source-line-no">5583</span><span id="line-5583">    long time = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">5584</span><span id="line-5584">    RegionInfo primaryHri = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName())</span> | 
|  | <span class="source-line-no">5585</span><span id="line-5585">      .setRegionId(time).setReplicaId(0).build();</span> | 
|  | <span class="source-line-no">5586</span><span id="line-5586">    RegionInfo secondaryHri = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName())</span> | 
|  | <span class="source-line-no">5587</span><span id="line-5587">      .setRegionId(time).setReplicaId(1).build();</span> | 
|  | <span class="source-line-no">5588</span><span id="line-5588"></span> | 
|  | <span class="source-line-no">5589</span><span id="line-5589">    HRegion primaryRegion = null, secondaryRegion = null;</span> | 
|  | <span class="source-line-no">5590</span><span id="line-5590"></span> | 
|  | <span class="source-line-no">5591</span><span id="line-5591">    try {</span> | 
|  | <span class="source-line-no">5592</span><span id="line-5592">      primaryRegion = HBaseTestingUtil.createRegionAndWAL(primaryHri, rootDir,</span> | 
|  | <span class="source-line-no">5593</span><span id="line-5593">        TEST_UTIL.getConfiguration(), tableDescriptor);</span> | 
|  | <span class="source-line-no">5594</span><span id="line-5594"></span> | 
|  | <span class="source-line-no">5595</span><span id="line-5595">      // load some data</span> | 
|  | <span class="source-line-no">5596</span><span id="line-5596">      putData(primaryRegion, 0, 1000, cq, families);</span> | 
|  | <span class="source-line-no">5597</span><span id="line-5597"></span> | 
|  | <span class="source-line-no">5598</span><span id="line-5598">      // flush region</span> | 
|  | <span class="source-line-no">5599</span><span id="line-5599">      primaryRegion.flush(true);</span> | 
|  | <span class="source-line-no">5600</span><span id="line-5600"></span> | 
|  | <span class="source-line-no">5601</span><span id="line-5601">      // open secondary region</span> | 
|  | <span class="source-line-no">5602</span><span id="line-5602">      secondaryRegion = HRegion.openHRegion(rootDir, secondaryHri, tableDescriptor, null, CONF);</span> | 
|  | <span class="source-line-no">5603</span><span id="line-5603"></span> | 
|  | <span class="source-line-no">5604</span><span id="line-5604">      verifyData(secondaryRegion, 0, 1000, cq, families);</span> | 
|  | <span class="source-line-no">5605</span><span id="line-5605">    } finally {</span> | 
|  | <span class="source-line-no">5606</span><span id="line-5606">      if (primaryRegion != null) {</span> | 
|  | <span class="source-line-no">5607</span><span id="line-5607">        HBaseTestingUtil.closeRegionAndWAL(primaryRegion);</span> | 
|  | <span class="source-line-no">5608</span><span id="line-5608">      }</span> | 
|  | <span class="source-line-no">5609</span><span id="line-5609">      if (secondaryRegion != null) {</span> | 
|  | <span class="source-line-no">5610</span><span id="line-5610">        HBaseTestingUtil.closeRegionAndWAL(secondaryRegion);</span> | 
|  | <span class="source-line-no">5611</span><span id="line-5611">      }</span> | 
|  | <span class="source-line-no">5612</span><span id="line-5612">    }</span> | 
|  | <span class="source-line-no">5613</span><span id="line-5613">  }</span> | 
|  | <span class="source-line-no">5614</span><span id="line-5614"></span> | 
|  | <span class="source-line-no">5615</span><span id="line-5615">  @Test</span> | 
|  | <span class="source-line-no">5616</span><span id="line-5616">  public void testRegionReplicaSecondaryIsReadOnly() throws IOException {</span> | 
|  | <span class="source-line-no">5617</span><span id="line-5617">    // create a primary region, load some data and flush</span> | 
|  | <span class="source-line-no">5618</span><span id="line-5618">    // create a secondary region, and do a put against that</span> | 
|  | <span class="source-line-no">5619</span><span id="line-5619">    Path rootDir = new Path(dir + name.getMethodName());</span> | 
|  | <span class="source-line-no">5620</span><span id="line-5620">    CommonFSUtils.setRootDir(TEST_UTIL.getConfiguration(), rootDir);</span> | 
|  | <span class="source-line-no">5621</span><span id="line-5621"></span> | 
|  | <span class="source-line-no">5622</span><span id="line-5622">    byte[][] families =</span> | 
|  | <span class="source-line-no">5623</span><span id="line-5623">      new byte[][] { Bytes.toBytes("cf1"), Bytes.toBytes("cf2"), Bytes.toBytes("cf3") };</span> | 
|  | <span class="source-line-no">5624</span><span id="line-5624">    byte[] cq = Bytes.toBytes("cq");</span> | 
|  | <span class="source-line-no">5625</span><span id="line-5625">    TableDescriptorBuilder builder =</span> | 
|  | <span class="source-line-no">5626</span><span id="line-5626">      TableDescriptorBuilder.newBuilder(TableName.valueOf(name.getMethodName()));</span> | 
|  | <span class="source-line-no">5627</span><span id="line-5627">    for (byte[] family : families) {</span> | 
|  | <span class="source-line-no">5628</span><span id="line-5628">      builder.setColumnFamily(ColumnFamilyDescriptorBuilder.of(family));</span> | 
|  | <span class="source-line-no">5629</span><span id="line-5629">    }</span> | 
|  | <span class="source-line-no">5630</span><span id="line-5630">    TableDescriptor tableDescriptor = builder.build();</span> | 
|  | <span class="source-line-no">5631</span><span id="line-5631">    long time = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">5632</span><span id="line-5632">    RegionInfo primaryHri = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName())</span> | 
|  | <span class="source-line-no">5633</span><span id="line-5633">      .setRegionId(time).setReplicaId(0).build();</span> | 
|  | <span class="source-line-no">5634</span><span id="line-5634">    RegionInfo secondaryHri = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName())</span> | 
|  | <span class="source-line-no">5635</span><span id="line-5635">      .setRegionId(time).setReplicaId(1).build();</span> | 
|  | <span class="source-line-no">5636</span><span id="line-5636"></span> | 
|  | <span class="source-line-no">5637</span><span id="line-5637">    HRegion primaryRegion = null, secondaryRegion = null;</span> | 
|  | <span class="source-line-no">5638</span><span id="line-5638"></span> | 
|  | <span class="source-line-no">5639</span><span id="line-5639">    try {</span> | 
|  | <span class="source-line-no">5640</span><span id="line-5640">      primaryRegion = HBaseTestingUtil.createRegionAndWAL(primaryHri, rootDir,</span> | 
|  | <span class="source-line-no">5641</span><span id="line-5641">        TEST_UTIL.getConfiguration(), tableDescriptor);</span> | 
|  | <span class="source-line-no">5642</span><span id="line-5642"></span> | 
|  | <span class="source-line-no">5643</span><span id="line-5643">      // load some data</span> | 
|  | <span class="source-line-no">5644</span><span id="line-5644">      putData(primaryRegion, 0, 1000, cq, families);</span> | 
|  | <span class="source-line-no">5645</span><span id="line-5645"></span> | 
|  | <span class="source-line-no">5646</span><span id="line-5646">      // flush region</span> | 
|  | <span class="source-line-no">5647</span><span id="line-5647">      primaryRegion.flush(true);</span> | 
|  | <span class="source-line-no">5648</span><span id="line-5648"></span> | 
|  | <span class="source-line-no">5649</span><span id="line-5649">      // open secondary region</span> | 
|  | <span class="source-line-no">5650</span><span id="line-5650">      secondaryRegion = HRegion.openHRegion(rootDir, secondaryHri, tableDescriptor, null, CONF);</span> | 
|  | <span class="source-line-no">5651</span><span id="line-5651"></span> | 
|  | <span class="source-line-no">5652</span><span id="line-5652">      try {</span> | 
|  | <span class="source-line-no">5653</span><span id="line-5653">        putData(secondaryRegion, 0, 1000, cq, families);</span> | 
|  | <span class="source-line-no">5654</span><span id="line-5654">        fail("Should have thrown exception");</span> | 
|  | <span class="source-line-no">5655</span><span id="line-5655">      } catch (IOException ex) {</span> | 
|  | <span class="source-line-no">5656</span><span id="line-5656">        // expected</span> | 
|  | <span class="source-line-no">5657</span><span id="line-5657">      }</span> | 
|  | <span class="source-line-no">5658</span><span id="line-5658">    } finally {</span> | 
|  | <span class="source-line-no">5659</span><span id="line-5659">      if (primaryRegion != null) {</span> | 
|  | <span class="source-line-no">5660</span><span id="line-5660">        HBaseTestingUtil.closeRegionAndWAL(primaryRegion);</span> | 
|  | <span class="source-line-no">5661</span><span id="line-5661">      }</span> | 
|  | <span class="source-line-no">5662</span><span id="line-5662">      if (secondaryRegion != null) {</span> | 
|  | <span class="source-line-no">5663</span><span id="line-5663">        HBaseTestingUtil.closeRegionAndWAL(secondaryRegion);</span> | 
|  | <span class="source-line-no">5664</span><span id="line-5664">      }</span> | 
|  | <span class="source-line-no">5665</span><span id="line-5665">    }</span> | 
|  | <span class="source-line-no">5666</span><span id="line-5666">  }</span> | 
|  | <span class="source-line-no">5667</span><span id="line-5667"></span> | 
|  | <span class="source-line-no">5668</span><span id="line-5668">  static WALFactory createWALFactory(Configuration conf, Path rootDir) throws IOException {</span> | 
|  | <span class="source-line-no">5669</span><span id="line-5669">    Configuration confForWAL = new Configuration(conf);</span> | 
|  | <span class="source-line-no">5670</span><span id="line-5670">    confForWAL.set(HConstants.HBASE_DIR, rootDir.toString());</span> | 
|  | <span class="source-line-no">5671</span><span id="line-5671">    return new WALFactory(confForWAL, "hregion-" + RandomStringUtils.randomNumeric(8));</span> | 
|  | <span class="source-line-no">5672</span><span id="line-5672">  }</span> | 
|  | <span class="source-line-no">5673</span><span id="line-5673"></span> | 
|  | <span class="source-line-no">5674</span><span id="line-5674">  @Test</span> | 
|  | <span class="source-line-no">5675</span><span id="line-5675">  public void testCompactionFromPrimary() throws IOException {</span> | 
|  | <span class="source-line-no">5676</span><span id="line-5676">    Path rootDir = new Path(dir + name.getMethodName());</span> | 
|  | <span class="source-line-no">5677</span><span id="line-5677">    CommonFSUtils.setRootDir(TEST_UTIL.getConfiguration(), rootDir);</span> | 
|  | <span class="source-line-no">5678</span><span id="line-5678"></span> | 
|  | <span class="source-line-no">5679</span><span id="line-5679">    byte[][] families =</span> | 
|  | <span class="source-line-no">5680</span><span id="line-5680">      new byte[][] { Bytes.toBytes("cf1"), Bytes.toBytes("cf2"), Bytes.toBytes("cf3") };</span> | 
|  | <span class="source-line-no">5681</span><span id="line-5681">    byte[] cq = Bytes.toBytes("cq");</span> | 
|  | <span class="source-line-no">5682</span><span id="line-5682">    TableDescriptorBuilder builder =</span> | 
|  | <span class="source-line-no">5683</span><span id="line-5683">      TableDescriptorBuilder.newBuilder(TableName.valueOf(name.getMethodName()));</span> | 
|  | <span class="source-line-no">5684</span><span id="line-5684">    for (byte[] family : families) {</span> | 
|  | <span class="source-line-no">5685</span><span id="line-5685">      builder.setColumnFamily(ColumnFamilyDescriptorBuilder.of(family));</span> | 
|  | <span class="source-line-no">5686</span><span id="line-5686">    }</span> | 
|  | <span class="source-line-no">5687</span><span id="line-5687">    TableDescriptor tableDescriptor = builder.build();</span> | 
|  | <span class="source-line-no">5688</span><span id="line-5688">    long time = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">5689</span><span id="line-5689">    RegionInfo primaryHri = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName())</span> | 
|  | <span class="source-line-no">5690</span><span id="line-5690">      .setRegionId(time).setReplicaId(0).build();</span> | 
|  | <span class="source-line-no">5691</span><span id="line-5691">    RegionInfo secondaryHri = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName())</span> | 
|  | <span class="source-line-no">5692</span><span id="line-5692">      .setRegionId(time).setReplicaId(1).build();</span> | 
|  | <span class="source-line-no">5693</span><span id="line-5693"></span> | 
|  | <span class="source-line-no">5694</span><span id="line-5694">    HRegion primaryRegion = null, secondaryRegion = null;</span> | 
|  | <span class="source-line-no">5695</span><span id="line-5695"></span> | 
|  | <span class="source-line-no">5696</span><span id="line-5696">    try {</span> | 
|  | <span class="source-line-no">5697</span><span id="line-5697">      primaryRegion = HBaseTestingUtil.createRegionAndWAL(primaryHri, rootDir,</span> | 
|  | <span class="source-line-no">5698</span><span id="line-5698">        TEST_UTIL.getConfiguration(), tableDescriptor);</span> | 
|  | <span class="source-line-no">5699</span><span id="line-5699"></span> | 
|  | <span class="source-line-no">5700</span><span id="line-5700">      // load some data</span> | 
|  | <span class="source-line-no">5701</span><span id="line-5701">      putData(primaryRegion, 0, 1000, cq, families);</span> | 
|  | <span class="source-line-no">5702</span><span id="line-5702"></span> | 
|  | <span class="source-line-no">5703</span><span id="line-5703">      // flush region</span> | 
|  | <span class="source-line-no">5704</span><span id="line-5704">      primaryRegion.flush(true);</span> | 
|  | <span class="source-line-no">5705</span><span id="line-5705"></span> | 
|  | <span class="source-line-no">5706</span><span id="line-5706">      // open secondary region</span> | 
|  | <span class="source-line-no">5707</span><span id="line-5707">      secondaryRegion = HRegion.openHRegion(rootDir, secondaryHri, tableDescriptor, null, CONF);</span> | 
|  | <span class="source-line-no">5708</span><span id="line-5708"></span> | 
|  | <span class="source-line-no">5709</span><span id="line-5709">      // move the file of the primary region to the archive, simulating a compaction</span> | 
|  | <span class="source-line-no">5710</span><span id="line-5710">      Collection<HStoreFile> storeFiles = primaryRegion.getStore(families[0]).getStorefiles();</span> | 
|  | <span class="source-line-no">5711</span><span id="line-5711">      primaryRegion.getRegionFileSystem().removeStoreFiles(Bytes.toString(families[0]), storeFiles);</span> | 
|  | <span class="source-line-no">5712</span><span id="line-5712">      Collection<StoreFileInfo> storeFileInfos =</span> | 
|  | <span class="source-line-no">5713</span><span id="line-5713">        primaryRegion.getRegionFileSystem().getStoreFiles(Bytes.toString(families[0]));</span> | 
|  | <span class="source-line-no">5714</span><span id="line-5714">      Assert.assertTrue(storeFileInfos == null || storeFileInfos.isEmpty());</span> | 
|  | <span class="source-line-no">5715</span><span id="line-5715"></span> | 
|  | <span class="source-line-no">5716</span><span id="line-5716">      verifyData(secondaryRegion, 0, 1000, cq, families);</span> | 
|  | <span class="source-line-no">5717</span><span id="line-5717">    } finally {</span> | 
|  | <span class="source-line-no">5718</span><span id="line-5718">      if (primaryRegion != null) {</span> | 
|  | <span class="source-line-no">5719</span><span id="line-5719">        HBaseTestingUtil.closeRegionAndWAL(primaryRegion);</span> | 
|  | <span class="source-line-no">5720</span><span id="line-5720">      }</span> | 
|  | <span class="source-line-no">5721</span><span id="line-5721">      if (secondaryRegion != null) {</span> | 
|  | <span class="source-line-no">5722</span><span id="line-5722">        HBaseTestingUtil.closeRegionAndWAL(secondaryRegion);</span> | 
|  | <span class="source-line-no">5723</span><span id="line-5723">      }</span> | 
|  | <span class="source-line-no">5724</span><span id="line-5724">    }</span> | 
|  | <span class="source-line-no">5725</span><span id="line-5725">  }</span> | 
|  | <span class="source-line-no">5726</span><span id="line-5726"></span> | 
|  | <span class="source-line-no">5727</span><span id="line-5727">  private void putData(int startRow, int numRows, byte[] qf, byte[]... families)</span> | 
|  | <span class="source-line-no">5728</span><span id="line-5728">    throws IOException {</span> | 
|  | <span class="source-line-no">5729</span><span id="line-5729">    putData(this.region, startRow, numRows, qf, families);</span> | 
|  | <span class="source-line-no">5730</span><span id="line-5730">  }</span> | 
|  | <span class="source-line-no">5731</span><span id="line-5731"></span> | 
|  | <span class="source-line-no">5732</span><span id="line-5732">  private void putData(HRegion region, int startRow, int numRows, byte[] qf, byte[]... families)</span> | 
|  | <span class="source-line-no">5733</span><span id="line-5733">    throws IOException {</span> | 
|  | <span class="source-line-no">5734</span><span id="line-5734">    putData(region, Durability.SKIP_WAL, startRow, numRows, qf, families);</span> | 
|  | <span class="source-line-no">5735</span><span id="line-5735">  }</span> | 
|  | <span class="source-line-no">5736</span><span id="line-5736"></span> | 
|  | <span class="source-line-no">5737</span><span id="line-5737">  static void putData(HRegion region, Durability durability, int startRow, int numRows, byte[] qf,</span> | 
|  | <span class="source-line-no">5738</span><span id="line-5738">    byte[]... families) throws IOException {</span> | 
|  | <span class="source-line-no">5739</span><span id="line-5739">    for (int i = startRow; i < startRow + numRows; i++) {</span> | 
|  | <span class="source-line-no">5740</span><span id="line-5740">      Put put = new Put(Bytes.toBytes("" + i));</span> | 
|  | <span class="source-line-no">5741</span><span id="line-5741">      put.setDurability(durability);</span> | 
|  | <span class="source-line-no">5742</span><span id="line-5742">      for (byte[] family : families) {</span> | 
|  | <span class="source-line-no">5743</span><span id="line-5743">        put.addColumn(family, qf, null);</span> | 
|  | <span class="source-line-no">5744</span><span id="line-5744">      }</span> | 
|  | <span class="source-line-no">5745</span><span id="line-5745">      region.put(put);</span> | 
|  | <span class="source-line-no">5746</span><span id="line-5746">      LOG.info(put.toString());</span> | 
|  | <span class="source-line-no">5747</span><span id="line-5747">    }</span> | 
|  | <span class="source-line-no">5748</span><span id="line-5748">  }</span> | 
|  | <span class="source-line-no">5749</span><span id="line-5749"></span> | 
|  | <span class="source-line-no">5750</span><span id="line-5750">  static void verifyData(HRegion newReg, int startRow, int numRows, byte[] qf, byte[]... families)</span> | 
|  | <span class="source-line-no">5751</span><span id="line-5751">    throws IOException {</span> | 
|  | <span class="source-line-no">5752</span><span id="line-5752">    for (int i = startRow; i < startRow + numRows; i++) {</span> | 
|  | <span class="source-line-no">5753</span><span id="line-5753">      byte[] row = Bytes.toBytes("" + i);</span> | 
|  | <span class="source-line-no">5754</span><span id="line-5754">      Get get = new Get(row);</span> | 
|  | <span class="source-line-no">5755</span><span id="line-5755">      for (byte[] family : families) {</span> | 
|  | <span class="source-line-no">5756</span><span id="line-5756">        get.addColumn(family, qf);</span> | 
|  | <span class="source-line-no">5757</span><span id="line-5757">      }</span> | 
|  | <span class="source-line-no">5758</span><span id="line-5758">      Result result = newReg.get(get);</span> | 
|  | <span class="source-line-no">5759</span><span id="line-5759">      Cell[] raw = result.rawCells();</span> | 
|  | <span class="source-line-no">5760</span><span id="line-5760">      assertEquals(families.length, result.size());</span> | 
|  | <span class="source-line-no">5761</span><span id="line-5761">      for (int j = 0; j < families.length; j++) {</span> | 
|  | <span class="source-line-no">5762</span><span id="line-5762">        assertTrue(CellUtil.matchingRows(raw[j], row));</span> | 
|  | <span class="source-line-no">5763</span><span id="line-5763">        assertTrue(CellUtil.matchingFamily(raw[j], families[j]));</span> | 
|  | <span class="source-line-no">5764</span><span id="line-5764">        assertTrue(CellUtil.matchingQualifier(raw[j], qf));</span> | 
|  | <span class="source-line-no">5765</span><span id="line-5765">      }</span> | 
|  | <span class="source-line-no">5766</span><span id="line-5766">    }</span> | 
|  | <span class="source-line-no">5767</span><span id="line-5767">  }</span> | 
|  | <span class="source-line-no">5768</span><span id="line-5768"></span> | 
|  | <span class="source-line-no">5769</span><span id="line-5769">  static void assertGet(final HRegion r, final byte[] family, final byte[] k) throws IOException {</span> | 
|  | <span class="source-line-no">5770</span><span id="line-5770">    // Now I have k, get values out and assert they are as expected.</span> | 
|  | <span class="source-line-no">5771</span><span id="line-5771">    Get get = new Get(k).addFamily(family).readAllVersions();</span> | 
|  | <span class="source-line-no">5772</span><span id="line-5772">    Cell[] results = r.get(get).rawCells();</span> | 
|  | <span class="source-line-no">5773</span><span id="line-5773">    for (int j = 0; j < results.length; j++) {</span> | 
|  | <span class="source-line-no">5774</span><span id="line-5774">      byte[] tmp = CellUtil.cloneValue(results[j]);</span> | 
|  | <span class="source-line-no">5775</span><span id="line-5775">      // Row should be equal to value every time.</span> | 
|  | <span class="source-line-no">5776</span><span id="line-5776">      assertTrue(Bytes.equals(k, tmp));</span> | 
|  | <span class="source-line-no">5777</span><span id="line-5777">    }</span> | 
|  | <span class="source-line-no">5778</span><span id="line-5778">  }</span> | 
|  | <span class="source-line-no">5779</span><span id="line-5779"></span> | 
|  | <span class="source-line-no">5780</span><span id="line-5780">  /*</span> | 
|  | <span class="source-line-no">5781</span><span id="line-5781">   * Assert first value in the passed region is <code>firstValue</code>.</span> | 
|  | <span class="source-line-no">5782</span><span id="line-5782">   */</span> | 
|  | <span class="source-line-no">5783</span><span id="line-5783">  protected void assertScan(final HRegion r, final byte[] fs, final byte[] firstValue)</span> | 
|  | <span class="source-line-no">5784</span><span id="line-5784">    throws IOException {</span> | 
|  | <span class="source-line-no">5785</span><span id="line-5785">    byte[][] families = { fs };</span> | 
|  | <span class="source-line-no">5786</span><span id="line-5786">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">5787</span><span id="line-5787">    for (int i = 0; i < families.length; i++)</span> | 
|  | <span class="source-line-no">5788</span><span id="line-5788">      scan.addFamily(families[i]);</span> | 
|  | <span class="source-line-no">5789</span><span id="line-5789">    try (InternalScanner s = r.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">5790</span><span id="line-5790">      List<Cell> curVals = new ArrayList<>();</span> | 
|  | <span class="source-line-no">5791</span><span id="line-5791">      boolean first = true;</span> | 
|  | <span class="source-line-no">5792</span><span id="line-5792">      OUTER_LOOP: while (s.next(curVals)) {</span> | 
|  | <span class="source-line-no">5793</span><span id="line-5793">        for (Cell kv : curVals) {</span> | 
|  | <span class="source-line-no">5794</span><span id="line-5794">          byte[] val = CellUtil.cloneValue(kv);</span> | 
|  | <span class="source-line-no">5795</span><span id="line-5795">          byte[] curval = val;</span> | 
|  | <span class="source-line-no">5796</span><span id="line-5796">          if (first) {</span> | 
|  | <span class="source-line-no">5797</span><span id="line-5797">            first = false;</span> | 
|  | <span class="source-line-no">5798</span><span id="line-5798">            assertTrue(Bytes.compareTo(curval, firstValue) == 0);</span> | 
|  | <span class="source-line-no">5799</span><span id="line-5799">          } else {</span> | 
|  | <span class="source-line-no">5800</span><span id="line-5800">            // Not asserting anything. Might as well break.</span> | 
|  | <span class="source-line-no">5801</span><span id="line-5801">            break OUTER_LOOP;</span> | 
|  | <span class="source-line-no">5802</span><span id="line-5802">          }</span> | 
|  | <span class="source-line-no">5803</span><span id="line-5803">        }</span> | 
|  | <span class="source-line-no">5804</span><span id="line-5804">      }</span> | 
|  | <span class="source-line-no">5805</span><span id="line-5805">    }</span> | 
|  | <span class="source-line-no">5806</span><span id="line-5806">  }</span> | 
|  | <span class="source-line-no">5807</span><span id="line-5807"></span> | 
|  | <span class="source-line-no">5808</span><span id="line-5808">  /**</span> | 
|  | <span class="source-line-no">5809</span><span id="line-5809">   * Test that we get the expected flush results back</span> | 
|  | <span class="source-line-no">5810</span><span id="line-5810">   */</span> | 
|  | <span class="source-line-no">5811</span><span id="line-5811">  @Test</span> | 
|  | <span class="source-line-no">5812</span><span id="line-5812">  public void testFlushResult() throws IOException {</span> | 
|  | <span class="source-line-no">5813</span><span id="line-5813">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">5814</span><span id="line-5814"></span> | 
|  | <span class="source-line-no">5815</span><span id="line-5815">    this.region = initHRegion(tableName, method, family);</span> | 
|  | <span class="source-line-no">5816</span><span id="line-5816"></span> | 
|  | <span class="source-line-no">5817</span><span id="line-5817">    // empty memstore, flush doesn't run</span> | 
|  | <span class="source-line-no">5818</span><span id="line-5818">    HRegion.FlushResult fr = region.flush(true);</span> | 
|  | <span class="source-line-no">5819</span><span id="line-5819">    assertFalse(fr.isFlushSucceeded());</span> | 
|  | <span class="source-line-no">5820</span><span id="line-5820">    assertFalse(fr.isCompactionNeeded());</span> | 
|  | <span class="source-line-no">5821</span><span id="line-5821"></span> | 
|  | <span class="source-line-no">5822</span><span id="line-5822">    // Flush enough files to get up to the threshold, doesn't need compactions</span> | 
|  | <span class="source-line-no">5823</span><span id="line-5823">    for (int i = 0; i < 2; i++) {</span> | 
|  | <span class="source-line-no">5824</span><span id="line-5824">      Put put = new Put(tableName.toBytes()).addColumn(family, family, tableName.toBytes());</span> | 
|  | <span class="source-line-no">5825</span><span id="line-5825">      region.put(put);</span> | 
|  | <span class="source-line-no">5826</span><span id="line-5826">      fr = region.flush(true);</span> | 
|  | <span class="source-line-no">5827</span><span id="line-5827">      assertTrue(fr.isFlushSucceeded());</span> | 
|  | <span class="source-line-no">5828</span><span id="line-5828">      assertFalse(fr.isCompactionNeeded());</span> | 
|  | <span class="source-line-no">5829</span><span id="line-5829">    }</span> | 
|  | <span class="source-line-no">5830</span><span id="line-5830"></span> | 
|  | <span class="source-line-no">5831</span><span id="line-5831">    // Two flushes after the threshold, compactions are needed</span> | 
|  | <span class="source-line-no">5832</span><span id="line-5832">    for (int i = 0; i < 2; i++) {</span> | 
|  | <span class="source-line-no">5833</span><span id="line-5833">      Put put = new Put(tableName.toBytes()).addColumn(family, family, tableName.toBytes());</span> | 
|  | <span class="source-line-no">5834</span><span id="line-5834">      region.put(put);</span> | 
|  | <span class="source-line-no">5835</span><span id="line-5835">      fr = region.flush(true);</span> | 
|  | <span class="source-line-no">5836</span><span id="line-5836">      assertTrue(fr.isFlushSucceeded());</span> | 
|  | <span class="source-line-no">5837</span><span id="line-5837">      assertTrue(fr.isCompactionNeeded());</span> | 
|  | <span class="source-line-no">5838</span><span id="line-5838">    }</span> | 
|  | <span class="source-line-no">5839</span><span id="line-5839">  }</span> | 
|  | <span class="source-line-no">5840</span><span id="line-5840"></span> | 
|  | <span class="source-line-no">5841</span><span id="line-5841">  protected Configuration initSplit() {</span> | 
|  | <span class="source-line-no">5842</span><span id="line-5842">    // Always compact if there is more than one store file.</span> | 
|  | <span class="source-line-no">5843</span><span id="line-5843">    CONF.setInt("hbase.hstore.compactionThreshold", 2);</span> | 
|  | <span class="source-line-no">5844</span><span id="line-5844"></span> | 
|  | <span class="source-line-no">5845</span><span id="line-5845">    CONF.setInt(HConstants.HBASE_CLIENT_SCANNER_TIMEOUT_PERIOD, 10 * 1000);</span> | 
|  | <span class="source-line-no">5846</span><span id="line-5846"></span> | 
|  | <span class="source-line-no">5847</span><span id="line-5847">    // Increase the amount of time between client retries</span> | 
|  | <span class="source-line-no">5848</span><span id="line-5848">    CONF.setLong("hbase.client.pause", 15 * 1000);</span> | 
|  | <span class="source-line-no">5849</span><span id="line-5849"></span> | 
|  | <span class="source-line-no">5850</span><span id="line-5850">    // This size should make it so we always split using the addContent</span> | 
|  | <span class="source-line-no">5851</span><span id="line-5851">    // below. After adding all data, the first region is 1.3M</span> | 
|  | <span class="source-line-no">5852</span><span id="line-5852">    CONF.setLong(HConstants.HREGION_MAX_FILESIZE, 1024 * 128);</span> | 
|  | <span class="source-line-no">5853</span><span id="line-5853">    return CONF;</span> | 
|  | <span class="source-line-no">5854</span><span id="line-5854">  }</span> | 
|  | <span class="source-line-no">5855</span><span id="line-5855"></span> | 
|  | <span class="source-line-no">5856</span><span id="line-5856">  /**</span> | 
|  | <span class="source-line-no">5857</span><span id="line-5857">   * @return A region on which you must call {@link HBaseTestingUtil#closeRegionAndWAL(HRegion)}</span> | 
|  | <span class="source-line-no">5858</span><span id="line-5858">   *         when done.</span> | 
|  | <span class="source-line-no">5859</span><span id="line-5859">   */</span> | 
|  | <span class="source-line-no">5860</span><span id="line-5860">  protected HRegion initHRegion(TableName tableName, String callingMethod, Configuration conf,</span> | 
|  | <span class="source-line-no">5861</span><span id="line-5861">    byte[]... families) throws IOException {</span> | 
|  | <span class="source-line-no">5862</span><span id="line-5862">    return initHRegion(tableName, callingMethod, conf, false, families);</span> | 
|  | <span class="source-line-no">5863</span><span id="line-5863">  }</span> | 
|  | <span class="source-line-no">5864</span><span id="line-5864"></span> | 
|  | <span class="source-line-no">5865</span><span id="line-5865">  /**</span> | 
|  | <span class="source-line-no">5866</span><span id="line-5866">   * @return A region on which you must call {@link HBaseTestingUtil#closeRegionAndWAL(HRegion)}</span> | 
|  | <span class="source-line-no">5867</span><span id="line-5867">   *         when done.</span> | 
|  | <span class="source-line-no">5868</span><span id="line-5868">   */</span> | 
|  | <span class="source-line-no">5869</span><span id="line-5869">  private HRegion initHRegion(TableName tableName, String callingMethod, Configuration conf,</span> | 
|  | <span class="source-line-no">5870</span><span id="line-5870">    boolean isReadOnly, byte[]... families) throws IOException {</span> | 
|  | <span class="source-line-no">5871</span><span id="line-5871">    return initHRegion(tableName, null, null, callingMethod, conf, isReadOnly, families);</span> | 
|  | <span class="source-line-no">5872</span><span id="line-5872">  }</span> | 
|  | <span class="source-line-no">5873</span><span id="line-5873"></span> | 
|  | <span class="source-line-no">5874</span><span id="line-5874">  private HRegion initHRegion(TableName tableName, byte[] startKey, byte[] stopKey,</span> | 
|  | <span class="source-line-no">5875</span><span id="line-5875">    String callingMethod, Configuration conf, boolean isReadOnly, byte[]... families)</span> | 
|  | <span class="source-line-no">5876</span><span id="line-5876">    throws IOException {</span> | 
|  | <span class="source-line-no">5877</span><span id="line-5877">    Path logDir = TEST_UTIL.getDataTestDirOnTestFS(callingMethod + ".log");</span> | 
|  | <span class="source-line-no">5878</span><span id="line-5878">    RegionInfo hri =</span> | 
|  | <span class="source-line-no">5879</span><span id="line-5879">      RegionInfoBuilder.newBuilder(tableName).setStartKey(startKey).setEndKey(stopKey).build();</span> | 
|  | <span class="source-line-no">5880</span><span id="line-5880">    final WAL wal = HBaseTestingUtil.createWal(conf, logDir, hri);</span> | 
|  | <span class="source-line-no">5881</span><span id="line-5881">    return initHRegion(tableName, startKey, stopKey, conf, isReadOnly, Durability.SYNC_WAL, wal,</span> | 
|  | <span class="source-line-no">5882</span><span id="line-5882">      families);</span> | 
|  | <span class="source-line-no">5883</span><span id="line-5883">  }</span> | 
|  | <span class="source-line-no">5884</span><span id="line-5884"></span> | 
|  | <span class="source-line-no">5885</span><span id="line-5885">  /**</span> | 
|  | <span class="source-line-no">5886</span><span id="line-5886">   * @return A region on which you must call {@link HBaseTestingUtil#closeRegionAndWAL(HRegion)}</span> | 
|  | <span class="source-line-no">5887</span><span id="line-5887">   *         when done.</span> | 
|  | <span class="source-line-no">5888</span><span id="line-5888">   */</span> | 
|  | <span class="source-line-no">5889</span><span id="line-5889">  protected HRegion initHRegion(TableName tableName, byte[] startKey, byte[] stopKey,</span> | 
|  | <span class="source-line-no">5890</span><span id="line-5890">    Configuration conf, boolean isReadOnly, Durability durability, WAL wal, byte[]... families)</span> | 
|  | <span class="source-line-no">5891</span><span id="line-5891">    throws IOException {</span> | 
|  | <span class="source-line-no">5892</span><span id="line-5892">    ChunkCreator.initialize(MemStoreLAB.CHUNK_SIZE_DEFAULT, false, 0, 0, 0, null,</span> | 
|  | <span class="source-line-no">5893</span><span id="line-5893">      MemStoreLAB.INDEX_CHUNK_SIZE_PERCENTAGE_DEFAULT);</span> | 
|  | <span class="source-line-no">5894</span><span id="line-5894">    return TEST_UTIL.createLocalHRegion(tableName, startKey, stopKey, conf, isReadOnly, durability,</span> | 
|  | <span class="source-line-no">5895</span><span id="line-5895">      wal, families);</span> | 
|  | <span class="source-line-no">5896</span><span id="line-5896">  }</span> | 
|  | <span class="source-line-no">5897</span><span id="line-5897"></span> | 
|  | <span class="source-line-no">5898</span><span id="line-5898">  /**</span> | 
|  | <span class="source-line-no">5899</span><span id="line-5899">   * Assert that the passed in Cell has expected contents for the specified row, column & timestamp.</span> | 
|  | <span class="source-line-no">5900</span><span id="line-5900">   */</span> | 
|  | <span class="source-line-no">5901</span><span id="line-5901">  private void checkOneCell(Cell kv, byte[] cf, int rowIdx, int colIdx, long ts) {</span> | 
|  | <span class="source-line-no">5902</span><span id="line-5902">    String ctx = "rowIdx=" + rowIdx + "; colIdx=" + colIdx + "; ts=" + ts;</span> | 
|  | <span class="source-line-no">5903</span><span id="line-5903">    assertEquals("Row mismatch which checking: " + ctx, "row:" + rowIdx,</span> | 
|  | <span class="source-line-no">5904</span><span id="line-5904">      Bytes.toString(CellUtil.cloneRow(kv)));</span> | 
|  | <span class="source-line-no">5905</span><span id="line-5905">    assertEquals("ColumnFamily mismatch while checking: " + ctx, Bytes.toString(cf),</span> | 
|  | <span class="source-line-no">5906</span><span id="line-5906">      Bytes.toString(CellUtil.cloneFamily(kv)));</span> | 
|  | <span class="source-line-no">5907</span><span id="line-5907">    assertEquals("Column qualifier mismatch while checking: " + ctx, "column:" + colIdx,</span> | 
|  | <span class="source-line-no">5908</span><span id="line-5908">      Bytes.toString(CellUtil.cloneQualifier(kv)));</span> | 
|  | <span class="source-line-no">5909</span><span id="line-5909">    assertEquals("Timestamp mismatch while checking: " + ctx, ts, kv.getTimestamp());</span> | 
|  | <span class="source-line-no">5910</span><span id="line-5910">    assertEquals("Value mismatch while checking: " + ctx, "value-version-" + ts,</span> | 
|  | <span class="source-line-no">5911</span><span id="line-5911">      Bytes.toString(CellUtil.cloneValue(kv)));</span> | 
|  | <span class="source-line-no">5912</span><span id="line-5912">  }</span> | 
|  | <span class="source-line-no">5913</span><span id="line-5913"></span> | 
|  | <span class="source-line-no">5914</span><span id="line-5914">  @Test</span> | 
|  | <span class="source-line-no">5915</span><span id="line-5915">  public void testReverseScanner_FromMemStore_SingleCF_Normal() throws IOException {</span> | 
|  | <span class="source-line-no">5916</span><span id="line-5916">    byte[] rowC = Bytes.toBytes("rowC");</span> | 
|  | <span class="source-line-no">5917</span><span id="line-5917">    byte[] rowA = Bytes.toBytes("rowA");</span> | 
|  | <span class="source-line-no">5918</span><span id="line-5918">    byte[] rowB = Bytes.toBytes("rowB");</span> | 
|  | <span class="source-line-no">5919</span><span id="line-5919">    byte[] cf = Bytes.toBytes("CF");</span> | 
|  | <span class="source-line-no">5920</span><span id="line-5920">    byte[][] families = { cf };</span> | 
|  | <span class="source-line-no">5921</span><span id="line-5921">    byte[] col = Bytes.toBytes("C");</span> | 
|  | <span class="source-line-no">5922</span><span id="line-5922">    long ts = 1;</span> | 
|  | <span class="source-line-no">5923</span><span id="line-5923">    this.region = initHRegion(tableName, method, families);</span> | 
|  | <span class="source-line-no">5924</span><span id="line-5924">    KeyValue kv1 = new KeyValue(rowC, cf, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">5925</span><span id="line-5925">    KeyValue kv11 = new KeyValue(rowC, cf, col, ts + 1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">5926</span><span id="line-5926">    KeyValue kv2 = new KeyValue(rowA, cf, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">5927</span><span id="line-5927">    KeyValue kv3 = new KeyValue(rowB, cf, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">5928</span><span id="line-5928">    Put put = null;</span> | 
|  | <span class="source-line-no">5929</span><span id="line-5929">    put = new Put(rowC);</span> | 
|  | <span class="source-line-no">5930</span><span id="line-5930">    put.add(kv1);</span> | 
|  | <span class="source-line-no">5931</span><span id="line-5931">    put.add(kv11);</span> | 
|  | <span class="source-line-no">5932</span><span id="line-5932">    region.put(put);</span> | 
|  | <span class="source-line-no">5933</span><span id="line-5933">    put = new Put(rowA);</span> | 
|  | <span class="source-line-no">5934</span><span id="line-5934">    put.add(kv2);</span> | 
|  | <span class="source-line-no">5935</span><span id="line-5935">    region.put(put);</span> | 
|  | <span class="source-line-no">5936</span><span id="line-5936">    put = new Put(rowB);</span> | 
|  | <span class="source-line-no">5937</span><span id="line-5937">    put.add(kv3);</span> | 
|  | <span class="source-line-no">5938</span><span id="line-5938">    region.put(put);</span> | 
|  | <span class="source-line-no">5939</span><span id="line-5939"></span> | 
|  | <span class="source-line-no">5940</span><span id="line-5940">    Scan scan = new Scan().withStartRow(rowC);</span> | 
|  | <span class="source-line-no">5941</span><span id="line-5941">    scan.readVersions(5);</span> | 
|  | <span class="source-line-no">5942</span><span id="line-5942">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">5943</span><span id="line-5943">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">5944</span><span id="line-5944">      List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">5945</span><span id="line-5945">      boolean hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">5946</span><span id="line-5946">      assertEquals(2, currRow.size());</span> | 
|  | <span class="source-line-no">5947</span><span id="line-5947">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">5948</span><span id="line-5948">        currRow.get(0).getRowLength(), rowC, 0, rowC.length));</span> | 
|  | <span class="source-line-no">5949</span><span id="line-5949">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">5950</span><span id="line-5950">      currRow.clear();</span> | 
|  | <span class="source-line-no">5951</span><span id="line-5951">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">5952</span><span id="line-5952">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">5953</span><span id="line-5953">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">5954</span><span id="line-5954">        currRow.get(0).getRowLength(), rowB, 0, rowB.length));</span> | 
|  | <span class="source-line-no">5955</span><span id="line-5955">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">5956</span><span id="line-5956">      currRow.clear();</span> | 
|  | <span class="source-line-no">5957</span><span id="line-5957">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">5958</span><span id="line-5958">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">5959</span><span id="line-5959">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">5960</span><span id="line-5960">        currRow.get(0).getRowLength(), rowA, 0, rowA.length));</span> | 
|  | <span class="source-line-no">5961</span><span id="line-5961">      assertFalse(hasNext);</span> | 
|  | <span class="source-line-no">5962</span><span id="line-5962">    }</span> | 
|  | <span class="source-line-no">5963</span><span id="line-5963">  }</span> | 
|  | <span class="source-line-no">5964</span><span id="line-5964"></span> | 
|  | <span class="source-line-no">5965</span><span id="line-5965">  @Test</span> | 
|  | <span class="source-line-no">5966</span><span id="line-5966">  public void testReverseScanner_FromMemStore_SingleCF_LargerKey() throws IOException {</span> | 
|  | <span class="source-line-no">5967</span><span id="line-5967">    byte[] rowC = Bytes.toBytes("rowC");</span> | 
|  | <span class="source-line-no">5968</span><span id="line-5968">    byte[] rowA = Bytes.toBytes("rowA");</span> | 
|  | <span class="source-line-no">5969</span><span id="line-5969">    byte[] rowB = Bytes.toBytes("rowB");</span> | 
|  | <span class="source-line-no">5970</span><span id="line-5970">    byte[] rowD = Bytes.toBytes("rowD");</span> | 
|  | <span class="source-line-no">5971</span><span id="line-5971">    byte[] cf = Bytes.toBytes("CF");</span> | 
|  | <span class="source-line-no">5972</span><span id="line-5972">    byte[][] families = { cf };</span> | 
|  | <span class="source-line-no">5973</span><span id="line-5973">    byte[] col = Bytes.toBytes("C");</span> | 
|  | <span class="source-line-no">5974</span><span id="line-5974">    long ts = 1;</span> | 
|  | <span class="source-line-no">5975</span><span id="line-5975">    this.region = initHRegion(tableName, method, families);</span> | 
|  | <span class="source-line-no">5976</span><span id="line-5976">    KeyValue kv1 = new KeyValue(rowC, cf, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">5977</span><span id="line-5977">    KeyValue kv11 = new KeyValue(rowC, cf, col, ts + 1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">5978</span><span id="line-5978">    KeyValue kv2 = new KeyValue(rowA, cf, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">5979</span><span id="line-5979">    KeyValue kv3 = new KeyValue(rowB, cf, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">5980</span><span id="line-5980">    Put put = null;</span> | 
|  | <span class="source-line-no">5981</span><span id="line-5981">    put = new Put(rowC);</span> | 
|  | <span class="source-line-no">5982</span><span id="line-5982">    put.add(kv1);</span> | 
|  | <span class="source-line-no">5983</span><span id="line-5983">    put.add(kv11);</span> | 
|  | <span class="source-line-no">5984</span><span id="line-5984">    region.put(put);</span> | 
|  | <span class="source-line-no">5985</span><span id="line-5985">    put = new Put(rowA);</span> | 
|  | <span class="source-line-no">5986</span><span id="line-5986">    put.add(kv2);</span> | 
|  | <span class="source-line-no">5987</span><span id="line-5987">    region.put(put);</span> | 
|  | <span class="source-line-no">5988</span><span id="line-5988">    put = new Put(rowB);</span> | 
|  | <span class="source-line-no">5989</span><span id="line-5989">    put.add(kv3);</span> | 
|  | <span class="source-line-no">5990</span><span id="line-5990">    region.put(put);</span> | 
|  | <span class="source-line-no">5991</span><span id="line-5991"></span> | 
|  | <span class="source-line-no">5992</span><span id="line-5992">    Scan scan = new Scan().withStartRow(rowD);</span> | 
|  | <span class="source-line-no">5993</span><span id="line-5993">    List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">5994</span><span id="line-5994">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">5995</span><span id="line-5995">    scan.readVersions(5);</span> | 
|  | <span class="source-line-no">5996</span><span id="line-5996">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">5997</span><span id="line-5997">      boolean hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">5998</span><span id="line-5998">      assertEquals(2, currRow.size());</span> | 
|  | <span class="source-line-no">5999</span><span id="line-5999">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6000</span><span id="line-6000">        currRow.get(0).getRowLength(), rowC, 0, rowC.length));</span> | 
|  | <span class="source-line-no">6001</span><span id="line-6001">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6002</span><span id="line-6002">      currRow.clear();</span> | 
|  | <span class="source-line-no">6003</span><span id="line-6003">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6004</span><span id="line-6004">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6005</span><span id="line-6005">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6006</span><span id="line-6006">        currRow.get(0).getRowLength(), rowB, 0, rowB.length));</span> | 
|  | <span class="source-line-no">6007</span><span id="line-6007">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6008</span><span id="line-6008">      currRow.clear();</span> | 
|  | <span class="source-line-no">6009</span><span id="line-6009">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6010</span><span id="line-6010">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6011</span><span id="line-6011">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6012</span><span id="line-6012">        currRow.get(0).getRowLength(), rowA, 0, rowA.length));</span> | 
|  | <span class="source-line-no">6013</span><span id="line-6013">      assertFalse(hasNext);</span> | 
|  | <span class="source-line-no">6014</span><span id="line-6014">    }</span> | 
|  | <span class="source-line-no">6015</span><span id="line-6015">  }</span> | 
|  | <span class="source-line-no">6016</span><span id="line-6016"></span> | 
|  | <span class="source-line-no">6017</span><span id="line-6017">  @Test</span> | 
|  | <span class="source-line-no">6018</span><span id="line-6018">  public void testReverseScanner_FromMemStore_SingleCF_FullScan() throws IOException {</span> | 
|  | <span class="source-line-no">6019</span><span id="line-6019">    byte[] rowC = Bytes.toBytes("rowC");</span> | 
|  | <span class="source-line-no">6020</span><span id="line-6020">    byte[] rowA = Bytes.toBytes("rowA");</span> | 
|  | <span class="source-line-no">6021</span><span id="line-6021">    byte[] rowB = Bytes.toBytes("rowB");</span> | 
|  | <span class="source-line-no">6022</span><span id="line-6022">    byte[] cf = Bytes.toBytes("CF");</span> | 
|  | <span class="source-line-no">6023</span><span id="line-6023">    byte[][] families = { cf };</span> | 
|  | <span class="source-line-no">6024</span><span id="line-6024">    byte[] col = Bytes.toBytes("C");</span> | 
|  | <span class="source-line-no">6025</span><span id="line-6025">    long ts = 1;</span> | 
|  | <span class="source-line-no">6026</span><span id="line-6026">    this.region = initHRegion(tableName, method, families);</span> | 
|  | <span class="source-line-no">6027</span><span id="line-6027">    KeyValue kv1 = new KeyValue(rowC, cf, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6028</span><span id="line-6028">    KeyValue kv11 = new KeyValue(rowC, cf, col, ts + 1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6029</span><span id="line-6029">    KeyValue kv2 = new KeyValue(rowA, cf, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6030</span><span id="line-6030">    KeyValue kv3 = new KeyValue(rowB, cf, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6031</span><span id="line-6031">    Put put = null;</span> | 
|  | <span class="source-line-no">6032</span><span id="line-6032">    put = new Put(rowC);</span> | 
|  | <span class="source-line-no">6033</span><span id="line-6033">    put.add(kv1);</span> | 
|  | <span class="source-line-no">6034</span><span id="line-6034">    put.add(kv11);</span> | 
|  | <span class="source-line-no">6035</span><span id="line-6035">    region.put(put);</span> | 
|  | <span class="source-line-no">6036</span><span id="line-6036">    put = new Put(rowA);</span> | 
|  | <span class="source-line-no">6037</span><span id="line-6037">    put.add(kv2);</span> | 
|  | <span class="source-line-no">6038</span><span id="line-6038">    region.put(put);</span> | 
|  | <span class="source-line-no">6039</span><span id="line-6039">    put = new Put(rowB);</span> | 
|  | <span class="source-line-no">6040</span><span id="line-6040">    put.add(kv3);</span> | 
|  | <span class="source-line-no">6041</span><span id="line-6041">    region.put(put);</span> | 
|  | <span class="source-line-no">6042</span><span id="line-6042">    Scan scan = new Scan();</span> | 
|  | <span class="source-line-no">6043</span><span id="line-6043">    List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">6044</span><span id="line-6044">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6045</span><span id="line-6045">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6046</span><span id="line-6046">      boolean hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6047</span><span id="line-6047">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6048</span><span id="line-6048">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6049</span><span id="line-6049">        currRow.get(0).getRowLength(), rowC, 0, rowC.length));</span> | 
|  | <span class="source-line-no">6050</span><span id="line-6050">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6051</span><span id="line-6051">      currRow.clear();</span> | 
|  | <span class="source-line-no">6052</span><span id="line-6052">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6053</span><span id="line-6053">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6054</span><span id="line-6054">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6055</span><span id="line-6055">        currRow.get(0).getRowLength(), rowB, 0, rowB.length));</span> | 
|  | <span class="source-line-no">6056</span><span id="line-6056">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6057</span><span id="line-6057">      currRow.clear();</span> | 
|  | <span class="source-line-no">6058</span><span id="line-6058">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6059</span><span id="line-6059">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6060</span><span id="line-6060">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6061</span><span id="line-6061">        currRow.get(0).getRowLength(), rowA, 0, rowA.length));</span> | 
|  | <span class="source-line-no">6062</span><span id="line-6062">      assertFalse(hasNext);</span> | 
|  | <span class="source-line-no">6063</span><span id="line-6063">    }</span> | 
|  | <span class="source-line-no">6064</span><span id="line-6064">  }</span> | 
|  | <span class="source-line-no">6065</span><span id="line-6065"></span> | 
|  | <span class="source-line-no">6066</span><span id="line-6066">  @Test</span> | 
|  | <span class="source-line-no">6067</span><span id="line-6067">  public void testReverseScanner_moreRowsMayExistAfter() throws IOException {</span> | 
|  | <span class="source-line-no">6068</span><span id="line-6068">    // case for "INCLUDE_AND_SEEK_NEXT_ROW & SEEK_NEXT_ROW" endless loop</span> | 
|  | <span class="source-line-no">6069</span><span id="line-6069">    byte[] rowA = Bytes.toBytes("rowA");</span> | 
|  | <span class="source-line-no">6070</span><span id="line-6070">    byte[] rowB = Bytes.toBytes("rowB");</span> | 
|  | <span class="source-line-no">6071</span><span id="line-6071">    byte[] rowC = Bytes.toBytes("rowC");</span> | 
|  | <span class="source-line-no">6072</span><span id="line-6072">    byte[] rowD = Bytes.toBytes("rowD");</span> | 
|  | <span class="source-line-no">6073</span><span id="line-6073">    byte[] rowE = Bytes.toBytes("rowE");</span> | 
|  | <span class="source-line-no">6074</span><span id="line-6074">    byte[] cf = Bytes.toBytes("CF");</span> | 
|  | <span class="source-line-no">6075</span><span id="line-6075">    byte[][] families = { cf };</span> | 
|  | <span class="source-line-no">6076</span><span id="line-6076">    byte[] col1 = Bytes.toBytes("col1");</span> | 
|  | <span class="source-line-no">6077</span><span id="line-6077">    byte[] col2 = Bytes.toBytes("col2");</span> | 
|  | <span class="source-line-no">6078</span><span id="line-6078">    long ts = 1;</span> | 
|  | <span class="source-line-no">6079</span><span id="line-6079">    this.region = initHRegion(tableName, method, families);</span> | 
|  | <span class="source-line-no">6080</span><span id="line-6080">    KeyValue kv1 = new KeyValue(rowA, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6081</span><span id="line-6081">    KeyValue kv2 = new KeyValue(rowB, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6082</span><span id="line-6082">    KeyValue kv3 = new KeyValue(rowC, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6083</span><span id="line-6083">    KeyValue kv4_1 = new KeyValue(rowD, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6084</span><span id="line-6084">    KeyValue kv4_2 = new KeyValue(rowD, cf, col2, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6085</span><span id="line-6085">    KeyValue kv5 = new KeyValue(rowE, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6086</span><span id="line-6086">    Put put = null;</span> | 
|  | <span class="source-line-no">6087</span><span id="line-6087">    put = new Put(rowA);</span> | 
|  | <span class="source-line-no">6088</span><span id="line-6088">    put.add(kv1);</span> | 
|  | <span class="source-line-no">6089</span><span id="line-6089">    region.put(put);</span> | 
|  | <span class="source-line-no">6090</span><span id="line-6090">    put = new Put(rowB);</span> | 
|  | <span class="source-line-no">6091</span><span id="line-6091">    put.add(kv2);</span> | 
|  | <span class="source-line-no">6092</span><span id="line-6092">    region.put(put);</span> | 
|  | <span class="source-line-no">6093</span><span id="line-6093">    put = new Put(rowC);</span> | 
|  | <span class="source-line-no">6094</span><span id="line-6094">    put.add(kv3);</span> | 
|  | <span class="source-line-no">6095</span><span id="line-6095">    region.put(put);</span> | 
|  | <span class="source-line-no">6096</span><span id="line-6096">    put = new Put(rowD);</span> | 
|  | <span class="source-line-no">6097</span><span id="line-6097">    put.add(kv4_1);</span> | 
|  | <span class="source-line-no">6098</span><span id="line-6098">    region.put(put);</span> | 
|  | <span class="source-line-no">6099</span><span id="line-6099">    put = new Put(rowD);</span> | 
|  | <span class="source-line-no">6100</span><span id="line-6100">    put.add(kv4_2);</span> | 
|  | <span class="source-line-no">6101</span><span id="line-6101">    region.put(put);</span> | 
|  | <span class="source-line-no">6102</span><span id="line-6102">    put = new Put(rowE);</span> | 
|  | <span class="source-line-no">6103</span><span id="line-6103">    put.add(kv5);</span> | 
|  | <span class="source-line-no">6104</span><span id="line-6104">    region.put(put);</span> | 
|  | <span class="source-line-no">6105</span><span id="line-6105">    region.flush(true);</span> | 
|  | <span class="source-line-no">6106</span><span id="line-6106">    Scan scan = new Scan().withStartRow(rowD).withStopRow(rowA);</span> | 
|  | <span class="source-line-no">6107</span><span id="line-6107">    scan.addColumn(families[0], col1);</span> | 
|  | <span class="source-line-no">6108</span><span id="line-6108">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6109</span><span id="line-6109">    List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">6110</span><span id="line-6110">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6111</span><span id="line-6111">      boolean hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6112</span><span id="line-6112">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6113</span><span id="line-6113">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6114</span><span id="line-6114">        currRow.get(0).getRowLength(), rowD, 0, rowD.length));</span> | 
|  | <span class="source-line-no">6115</span><span id="line-6115">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6116</span><span id="line-6116">      currRow.clear();</span> | 
|  | <span class="source-line-no">6117</span><span id="line-6117">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6118</span><span id="line-6118">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6119</span><span id="line-6119">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6120</span><span id="line-6120">        currRow.get(0).getRowLength(), rowC, 0, rowC.length));</span> | 
|  | <span class="source-line-no">6121</span><span id="line-6121">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6122</span><span id="line-6122">      currRow.clear();</span> | 
|  | <span class="source-line-no">6123</span><span id="line-6123">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6124</span><span id="line-6124">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6125</span><span id="line-6125">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6126</span><span id="line-6126">        currRow.get(0).getRowLength(), rowB, 0, rowB.length));</span> | 
|  | <span class="source-line-no">6127</span><span id="line-6127">      assertFalse(hasNext);</span> | 
|  | <span class="source-line-no">6128</span><span id="line-6128">    }</span> | 
|  | <span class="source-line-no">6129</span><span id="line-6129"></span> | 
|  | <span class="source-line-no">6130</span><span id="line-6130">    scan = new Scan().withStartRow(rowD).withStopRow(rowA);</span> | 
|  | <span class="source-line-no">6131</span><span id="line-6131">    scan.addColumn(families[0], col2);</span> | 
|  | <span class="source-line-no">6132</span><span id="line-6132">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6133</span><span id="line-6133">    currRow.clear();</span> | 
|  | <span class="source-line-no">6134</span><span id="line-6134">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6135</span><span id="line-6135">      boolean hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6136</span><span id="line-6136">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6137</span><span id="line-6137">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6138</span><span id="line-6138">        currRow.get(0).getRowLength(), rowD, 0, rowD.length));</span> | 
|  | <span class="source-line-no">6139</span><span id="line-6139">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6140</span><span id="line-6140">    }</span> | 
|  | <span class="source-line-no">6141</span><span id="line-6141">  }</span> | 
|  | <span class="source-line-no">6142</span><span id="line-6142"></span> | 
|  | <span class="source-line-no">6143</span><span id="line-6143">  @Test</span> | 
|  | <span class="source-line-no">6144</span><span id="line-6144">  public void testReverseScanner_smaller_blocksize() throws IOException {</span> | 
|  | <span class="source-line-no">6145</span><span id="line-6145">    // case to ensure no conflict with HFile index optimization</span> | 
|  | <span class="source-line-no">6146</span><span id="line-6146">    byte[] rowA = Bytes.toBytes("rowA");</span> | 
|  | <span class="source-line-no">6147</span><span id="line-6147">    byte[] rowB = Bytes.toBytes("rowB");</span> | 
|  | <span class="source-line-no">6148</span><span id="line-6148">    byte[] rowC = Bytes.toBytes("rowC");</span> | 
|  | <span class="source-line-no">6149</span><span id="line-6149">    byte[] rowD = Bytes.toBytes("rowD");</span> | 
|  | <span class="source-line-no">6150</span><span id="line-6150">    byte[] rowE = Bytes.toBytes("rowE");</span> | 
|  | <span class="source-line-no">6151</span><span id="line-6151">    byte[] cf = Bytes.toBytes("CF");</span> | 
|  | <span class="source-line-no">6152</span><span id="line-6152">    byte[][] families = { cf };</span> | 
|  | <span class="source-line-no">6153</span><span id="line-6153">    byte[] col1 = Bytes.toBytes("col1");</span> | 
|  | <span class="source-line-no">6154</span><span id="line-6154">    byte[] col2 = Bytes.toBytes("col2");</span> | 
|  | <span class="source-line-no">6155</span><span id="line-6155">    long ts = 1;</span> | 
|  | <span class="source-line-no">6156</span><span id="line-6156">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">6157</span><span id="line-6157">    conf.setInt("test.block.size", 1);</span> | 
|  | <span class="source-line-no">6158</span><span id="line-6158">    this.region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">6159</span><span id="line-6159">    KeyValue kv1 = new KeyValue(rowA, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6160</span><span id="line-6160">    KeyValue kv2 = new KeyValue(rowB, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6161</span><span id="line-6161">    KeyValue kv3 = new KeyValue(rowC, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6162</span><span id="line-6162">    KeyValue kv4_1 = new KeyValue(rowD, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6163</span><span id="line-6163">    KeyValue kv4_2 = new KeyValue(rowD, cf, col2, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6164</span><span id="line-6164">    KeyValue kv5 = new KeyValue(rowE, cf, col1, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6165</span><span id="line-6165">    Put put = null;</span> | 
|  | <span class="source-line-no">6166</span><span id="line-6166">    put = new Put(rowA);</span> | 
|  | <span class="source-line-no">6167</span><span id="line-6167">    put.add(kv1);</span> | 
|  | <span class="source-line-no">6168</span><span id="line-6168">    region.put(put);</span> | 
|  | <span class="source-line-no">6169</span><span id="line-6169">    put = new Put(rowB);</span> | 
|  | <span class="source-line-no">6170</span><span id="line-6170">    put.add(kv2);</span> | 
|  | <span class="source-line-no">6171</span><span id="line-6171">    region.put(put);</span> | 
|  | <span class="source-line-no">6172</span><span id="line-6172">    put = new Put(rowC);</span> | 
|  | <span class="source-line-no">6173</span><span id="line-6173">    put.add(kv3);</span> | 
|  | <span class="source-line-no">6174</span><span id="line-6174">    region.put(put);</span> | 
|  | <span class="source-line-no">6175</span><span id="line-6175">    put = new Put(rowD);</span> | 
|  | <span class="source-line-no">6176</span><span id="line-6176">    put.add(kv4_1);</span> | 
|  | <span class="source-line-no">6177</span><span id="line-6177">    region.put(put);</span> | 
|  | <span class="source-line-no">6178</span><span id="line-6178">    put = new Put(rowD);</span> | 
|  | <span class="source-line-no">6179</span><span id="line-6179">    put.add(kv4_2);</span> | 
|  | <span class="source-line-no">6180</span><span id="line-6180">    region.put(put);</span> | 
|  | <span class="source-line-no">6181</span><span id="line-6181">    put = new Put(rowE);</span> | 
|  | <span class="source-line-no">6182</span><span id="line-6182">    put.add(kv5);</span> | 
|  | <span class="source-line-no">6183</span><span id="line-6183">    region.put(put);</span> | 
|  | <span class="source-line-no">6184</span><span id="line-6184">    region.flush(true);</span> | 
|  | <span class="source-line-no">6185</span><span id="line-6185">    Scan scan = new Scan().withStartRow(rowD).withStopRow(rowA);</span> | 
|  | <span class="source-line-no">6186</span><span id="line-6186">    scan.addColumn(families[0], col1);</span> | 
|  | <span class="source-line-no">6187</span><span id="line-6187">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6188</span><span id="line-6188">    List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">6189</span><span id="line-6189">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6190</span><span id="line-6190">      boolean hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6191</span><span id="line-6191">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6192</span><span id="line-6192">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6193</span><span id="line-6193">        currRow.get(0).getRowLength(), rowD, 0, rowD.length));</span> | 
|  | <span class="source-line-no">6194</span><span id="line-6194">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6195</span><span id="line-6195">      currRow.clear();</span> | 
|  | <span class="source-line-no">6196</span><span id="line-6196">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6197</span><span id="line-6197">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6198</span><span id="line-6198">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6199</span><span id="line-6199">        currRow.get(0).getRowLength(), rowC, 0, rowC.length));</span> | 
|  | <span class="source-line-no">6200</span><span id="line-6200">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6201</span><span id="line-6201">      currRow.clear();</span> | 
|  | <span class="source-line-no">6202</span><span id="line-6202">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6203</span><span id="line-6203">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6204</span><span id="line-6204">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6205</span><span id="line-6205">        currRow.get(0).getRowLength(), rowB, 0, rowB.length));</span> | 
|  | <span class="source-line-no">6206</span><span id="line-6206">      assertFalse(hasNext);</span> | 
|  | <span class="source-line-no">6207</span><span id="line-6207">    }</span> | 
|  | <span class="source-line-no">6208</span><span id="line-6208"></span> | 
|  | <span class="source-line-no">6209</span><span id="line-6209">    scan = new Scan().withStartRow(rowD).withStopRow(rowA);</span> | 
|  | <span class="source-line-no">6210</span><span id="line-6210">    scan.addColumn(families[0], col2);</span> | 
|  | <span class="source-line-no">6211</span><span id="line-6211">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6212</span><span id="line-6212">    currRow.clear();</span> | 
|  | <span class="source-line-no">6213</span><span id="line-6213">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6214</span><span id="line-6214">      boolean hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6215</span><span id="line-6215">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6216</span><span id="line-6216">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6217</span><span id="line-6217">        currRow.get(0).getRowLength(), rowD, 0, rowD.length));</span> | 
|  | <span class="source-line-no">6218</span><span id="line-6218">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6219</span><span id="line-6219">    }</span> | 
|  | <span class="source-line-no">6220</span><span id="line-6220">  }</span> | 
|  | <span class="source-line-no">6221</span><span id="line-6221"></span> | 
|  | <span class="source-line-no">6222</span><span id="line-6222">  @Test</span> | 
|  | <span class="source-line-no">6223</span><span id="line-6223">  public void testReverseScanner_FromMemStoreAndHFiles_MultiCFs1() throws IOException {</span> | 
|  | <span class="source-line-no">6224</span><span id="line-6224">    byte[] row0 = Bytes.toBytes("row0"); // 1 kv</span> | 
|  | <span class="source-line-no">6225</span><span id="line-6225">    byte[] row1 = Bytes.toBytes("row1"); // 2 kv</span> | 
|  | <span class="source-line-no">6226</span><span id="line-6226">    byte[] row2 = Bytes.toBytes("row2"); // 4 kv</span> | 
|  | <span class="source-line-no">6227</span><span id="line-6227">    byte[] row3 = Bytes.toBytes("row3"); // 2 kv</span> | 
|  | <span class="source-line-no">6228</span><span id="line-6228">    byte[] row4 = Bytes.toBytes("row4"); // 5 kv</span> | 
|  | <span class="source-line-no">6229</span><span id="line-6229">    byte[] row5 = Bytes.toBytes("row5"); // 2 kv</span> | 
|  | <span class="source-line-no">6230</span><span id="line-6230">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">6231</span><span id="line-6231">    byte[] cf2 = Bytes.toBytes("CF2");</span> | 
|  | <span class="source-line-no">6232</span><span id="line-6232">    byte[] cf3 = Bytes.toBytes("CF3");</span> | 
|  | <span class="source-line-no">6233</span><span id="line-6233">    byte[][] families = { cf1, cf2, cf3 };</span> | 
|  | <span class="source-line-no">6234</span><span id="line-6234">    byte[] col = Bytes.toBytes("C");</span> | 
|  | <span class="source-line-no">6235</span><span id="line-6235">    long ts = 1;</span> | 
|  | <span class="source-line-no">6236</span><span id="line-6236">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">6237</span><span id="line-6237">    // disable compactions in this test.</span> | 
|  | <span class="source-line-no">6238</span><span id="line-6238">    conf.setInt("hbase.hstore.compactionThreshold", 10000);</span> | 
|  | <span class="source-line-no">6239</span><span id="line-6239">    this.region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">6240</span><span id="line-6240">    // kv naming style: kv(row number) totalKvCountInThisRow seq no</span> | 
|  | <span class="source-line-no">6241</span><span id="line-6241">    KeyValue kv0_1_1 = new KeyValue(row0, cf1, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6242</span><span id="line-6242">    KeyValue kv1_2_1 = new KeyValue(row1, cf2, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6243</span><span id="line-6243">    KeyValue kv1_2_2 = new KeyValue(row1, cf1, col, ts + 1, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6244</span><span id="line-6244">    KeyValue kv2_4_1 = new KeyValue(row2, cf2, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6245</span><span id="line-6245">    KeyValue kv2_4_2 = new KeyValue(row2, cf1, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6246</span><span id="line-6246">    KeyValue kv2_4_3 = new KeyValue(row2, cf3, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6247</span><span id="line-6247">    KeyValue kv2_4_4 = new KeyValue(row2, cf1, col, ts + 4, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6248</span><span id="line-6248">    KeyValue kv3_2_1 = new KeyValue(row3, cf2, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6249</span><span id="line-6249">    KeyValue kv3_2_2 = new KeyValue(row3, cf1, col, ts + 4, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6250</span><span id="line-6250">    KeyValue kv4_5_1 = new KeyValue(row4, cf1, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6251</span><span id="line-6251">    KeyValue kv4_5_2 = new KeyValue(row4, cf3, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6252</span><span id="line-6252">    KeyValue kv4_5_3 = new KeyValue(row4, cf3, col, ts + 5, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6253</span><span id="line-6253">    KeyValue kv4_5_4 = new KeyValue(row4, cf2, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6254</span><span id="line-6254">    KeyValue kv4_5_5 = new KeyValue(row4, cf1, col, ts + 3, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6255</span><span id="line-6255">    KeyValue kv5_2_1 = new KeyValue(row5, cf2, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6256</span><span id="line-6256">    KeyValue kv5_2_2 = new KeyValue(row5, cf3, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6257</span><span id="line-6257">    // hfiles(cf1/cf2) :"row1"(1 kv) / "row2"(1 kv) / "row4"(2 kv)</span> | 
|  | <span class="source-line-no">6258</span><span id="line-6258">    Put put = null;</span> | 
|  | <span class="source-line-no">6259</span><span id="line-6259">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">6260</span><span id="line-6260">    put.add(kv1_2_1);</span> | 
|  | <span class="source-line-no">6261</span><span id="line-6261">    region.put(put);</span> | 
|  | <span class="source-line-no">6262</span><span id="line-6262">    put = new Put(row2);</span> | 
|  | <span class="source-line-no">6263</span><span id="line-6263">    put.add(kv2_4_1);</span> | 
|  | <span class="source-line-no">6264</span><span id="line-6264">    region.put(put);</span> | 
|  | <span class="source-line-no">6265</span><span id="line-6265">    put = new Put(row4);</span> | 
|  | <span class="source-line-no">6266</span><span id="line-6266">    put.add(kv4_5_4);</span> | 
|  | <span class="source-line-no">6267</span><span id="line-6267">    put.add(kv4_5_5);</span> | 
|  | <span class="source-line-no">6268</span><span id="line-6268">    region.put(put);</span> | 
|  | <span class="source-line-no">6269</span><span id="line-6269">    region.flush(true);</span> | 
|  | <span class="source-line-no">6270</span><span id="line-6270">    // hfiles(cf1/cf3) : "row1" (1 kvs) / "row2" (1 kv) / "row4" (2 kv)</span> | 
|  | <span class="source-line-no">6271</span><span id="line-6271">    put = new Put(row4);</span> | 
|  | <span class="source-line-no">6272</span><span id="line-6272">    put.add(kv4_5_1);</span> | 
|  | <span class="source-line-no">6273</span><span id="line-6273">    put.add(kv4_5_3);</span> | 
|  | <span class="source-line-no">6274</span><span id="line-6274">    region.put(put);</span> | 
|  | <span class="source-line-no">6275</span><span id="line-6275">    put = new Put(row1);</span> | 
|  | <span class="source-line-no">6276</span><span id="line-6276">    put.add(kv1_2_2);</span> | 
|  | <span class="source-line-no">6277</span><span id="line-6277">    region.put(put);</span> | 
|  | <span class="source-line-no">6278</span><span id="line-6278">    put = new Put(row2);</span> | 
|  | <span class="source-line-no">6279</span><span id="line-6279">    put.add(kv2_4_4);</span> | 
|  | <span class="source-line-no">6280</span><span id="line-6280">    region.put(put);</span> | 
|  | <span class="source-line-no">6281</span><span id="line-6281">    region.flush(true);</span> | 
|  | <span class="source-line-no">6282</span><span id="line-6282">    // hfiles(cf1/cf3) : "row2"(2 kv) / "row3"(1 kvs) / "row4" (1 kv)</span> | 
|  | <span class="source-line-no">6283</span><span id="line-6283">    put = new Put(row4);</span> | 
|  | <span class="source-line-no">6284</span><span id="line-6284">    put.add(kv4_5_2);</span> | 
|  | <span class="source-line-no">6285</span><span id="line-6285">    region.put(put);</span> | 
|  | <span class="source-line-no">6286</span><span id="line-6286">    put = new Put(row2);</span> | 
|  | <span class="source-line-no">6287</span><span id="line-6287">    put.add(kv2_4_2);</span> | 
|  | <span class="source-line-no">6288</span><span id="line-6288">    put.add(kv2_4_3);</span> | 
|  | <span class="source-line-no">6289</span><span id="line-6289">    region.put(put);</span> | 
|  | <span class="source-line-no">6290</span><span id="line-6290">    put = new Put(row3);</span> | 
|  | <span class="source-line-no">6291</span><span id="line-6291">    put.add(kv3_2_2);</span> | 
|  | <span class="source-line-no">6292</span><span id="line-6292">    region.put(put);</span> | 
|  | <span class="source-line-no">6293</span><span id="line-6293">    region.flush(true);</span> | 
|  | <span class="source-line-no">6294</span><span id="line-6294">    // memstore(cf1/cf2/cf3) : "row0" (1 kvs) / "row3" ( 1 kv) / "row5" (max)</span> | 
|  | <span class="source-line-no">6295</span><span id="line-6295">    // ( 2 kv)</span> | 
|  | <span class="source-line-no">6296</span><span id="line-6296">    put = new Put(row0);</span> | 
|  | <span class="source-line-no">6297</span><span id="line-6297">    put.add(kv0_1_1);</span> | 
|  | <span class="source-line-no">6298</span><span id="line-6298">    region.put(put);</span> | 
|  | <span class="source-line-no">6299</span><span id="line-6299">    put = new Put(row3);</span> | 
|  | <span class="source-line-no">6300</span><span id="line-6300">    put.add(kv3_2_1);</span> | 
|  | <span class="source-line-no">6301</span><span id="line-6301">    region.put(put);</span> | 
|  | <span class="source-line-no">6302</span><span id="line-6302">    put = new Put(row5);</span> | 
|  | <span class="source-line-no">6303</span><span id="line-6303">    put.add(kv5_2_1);</span> | 
|  | <span class="source-line-no">6304</span><span id="line-6304">    put.add(kv5_2_2);</span> | 
|  | <span class="source-line-no">6305</span><span id="line-6305">    region.put(put);</span> | 
|  | <span class="source-line-no">6306</span><span id="line-6306">    // scan range = ["row4", min), skip the max "row5"</span> | 
|  | <span class="source-line-no">6307</span><span id="line-6307">    Scan scan = new Scan().withStartRow(row4);</span> | 
|  | <span class="source-line-no">6308</span><span id="line-6308">    scan.readVersions(5);</span> | 
|  | <span class="source-line-no">6309</span><span id="line-6309">    scan.setBatch(3);</span> | 
|  | <span class="source-line-no">6310</span><span id="line-6310">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6311</span><span id="line-6311">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6312</span><span id="line-6312">      List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">6313</span><span id="line-6313">      boolean hasNext = false;</span> | 
|  | <span class="source-line-no">6314</span><span id="line-6314">      // 1. scan out "row4" (5 kvs), "row5" can't be scanned out since not</span> | 
|  | <span class="source-line-no">6315</span><span id="line-6315">      // included in scan range</span> | 
|  | <span class="source-line-no">6316</span><span id="line-6316">      // "row4" takes 2 next() calls since batch=3</span> | 
|  | <span class="source-line-no">6317</span><span id="line-6317">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6318</span><span id="line-6318">      assertEquals(3, currRow.size());</span> | 
|  | <span class="source-line-no">6319</span><span id="line-6319">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6320</span><span id="line-6320">        currRow.get(0).getRowLength(), row4, 0, row4.length));</span> | 
|  | <span class="source-line-no">6321</span><span id="line-6321">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6322</span><span id="line-6322">      currRow.clear();</span> | 
|  | <span class="source-line-no">6323</span><span id="line-6323">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6324</span><span id="line-6324">      assertEquals(2, currRow.size());</span> | 
|  | <span class="source-line-no">6325</span><span id="line-6325">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6326</span><span id="line-6326">        currRow.get(0).getRowLength(), row4, 0, row4.length));</span> | 
|  | <span class="source-line-no">6327</span><span id="line-6327">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6328</span><span id="line-6328">      // 2. scan out "row3" (2 kv)</span> | 
|  | <span class="source-line-no">6329</span><span id="line-6329">      currRow.clear();</span> | 
|  | <span class="source-line-no">6330</span><span id="line-6330">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6331</span><span id="line-6331">      assertEquals(2, currRow.size());</span> | 
|  | <span class="source-line-no">6332</span><span id="line-6332">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6333</span><span id="line-6333">        currRow.get(0).getRowLength(), row3, 0, row3.length));</span> | 
|  | <span class="source-line-no">6334</span><span id="line-6334">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6335</span><span id="line-6335">      // 3. scan out "row2" (4 kvs)</span> | 
|  | <span class="source-line-no">6336</span><span id="line-6336">      // "row2" takes 2 next() calls since batch=3</span> | 
|  | <span class="source-line-no">6337</span><span id="line-6337">      currRow.clear();</span> | 
|  | <span class="source-line-no">6338</span><span id="line-6338">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6339</span><span id="line-6339">      assertEquals(3, currRow.size());</span> | 
|  | <span class="source-line-no">6340</span><span id="line-6340">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6341</span><span id="line-6341">        currRow.get(0).getRowLength(), row2, 0, row2.length));</span> | 
|  | <span class="source-line-no">6342</span><span id="line-6342">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6343</span><span id="line-6343">      currRow.clear();</span> | 
|  | <span class="source-line-no">6344</span><span id="line-6344">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6345</span><span id="line-6345">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6346</span><span id="line-6346">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6347</span><span id="line-6347">        currRow.get(0).getRowLength(), row2, 0, row2.length));</span> | 
|  | <span class="source-line-no">6348</span><span id="line-6348">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6349</span><span id="line-6349">      // 4. scan out "row1" (2 kv)</span> | 
|  | <span class="source-line-no">6350</span><span id="line-6350">      currRow.clear();</span> | 
|  | <span class="source-line-no">6351</span><span id="line-6351">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6352</span><span id="line-6352">      assertEquals(2, currRow.size());</span> | 
|  | <span class="source-line-no">6353</span><span id="line-6353">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6354</span><span id="line-6354">        currRow.get(0).getRowLength(), row1, 0, row1.length));</span> | 
|  | <span class="source-line-no">6355</span><span id="line-6355">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6356</span><span id="line-6356">      // 5. scan out "row0" (1 kv)</span> | 
|  | <span class="source-line-no">6357</span><span id="line-6357">      currRow.clear();</span> | 
|  | <span class="source-line-no">6358</span><span id="line-6358">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6359</span><span id="line-6359">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6360</span><span id="line-6360">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6361</span><span id="line-6361">        currRow.get(0).getRowLength(), row0, 0, row0.length));</span> | 
|  | <span class="source-line-no">6362</span><span id="line-6362">      assertFalse(hasNext);</span> | 
|  | <span class="source-line-no">6363</span><span id="line-6363">    }</span> | 
|  | <span class="source-line-no">6364</span><span id="line-6364">  }</span> | 
|  | <span class="source-line-no">6365</span><span id="line-6365"></span> | 
|  | <span class="source-line-no">6366</span><span id="line-6366">  @Test</span> | 
|  | <span class="source-line-no">6367</span><span id="line-6367">  public void testReverseScanner_FromMemStoreAndHFiles_MultiCFs2() throws IOException {</span> | 
|  | <span class="source-line-no">6368</span><span id="line-6368">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">6369</span><span id="line-6369">    byte[] row2 = Bytes.toBytes("row2");</span> | 
|  | <span class="source-line-no">6370</span><span id="line-6370">    byte[] row3 = Bytes.toBytes("row3");</span> | 
|  | <span class="source-line-no">6371</span><span id="line-6371">    byte[] row4 = Bytes.toBytes("row4");</span> | 
|  | <span class="source-line-no">6372</span><span id="line-6372">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">6373</span><span id="line-6373">    byte[] cf2 = Bytes.toBytes("CF2");</span> | 
|  | <span class="source-line-no">6374</span><span id="line-6374">    byte[] cf3 = Bytes.toBytes("CF3");</span> | 
|  | <span class="source-line-no">6375</span><span id="line-6375">    byte[] cf4 = Bytes.toBytes("CF4");</span> | 
|  | <span class="source-line-no">6376</span><span id="line-6376">    byte[][] families = { cf1, cf2, cf3, cf4 };</span> | 
|  | <span class="source-line-no">6377</span><span id="line-6377">    byte[] col = Bytes.toBytes("C");</span> | 
|  | <span class="source-line-no">6378</span><span id="line-6378">    long ts = 1;</span> | 
|  | <span class="source-line-no">6379</span><span id="line-6379">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">6380</span><span id="line-6380">    // disable compactions in this test.</span> | 
|  | <span class="source-line-no">6381</span><span id="line-6381">    conf.setInt("hbase.hstore.compactionThreshold", 10000);</span> | 
|  | <span class="source-line-no">6382</span><span id="line-6382">    this.region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">6383</span><span id="line-6383">    KeyValue kv1 = new KeyValue(row1, cf1, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6384</span><span id="line-6384">    KeyValue kv2 = new KeyValue(row2, cf2, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6385</span><span id="line-6385">    KeyValue kv3 = new KeyValue(row3, cf3, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6386</span><span id="line-6386">    KeyValue kv4 = new KeyValue(row4, cf4, col, ts, KeyValue.Type.Put, null);</span> | 
|  | <span class="source-line-no">6387</span><span id="line-6387">    // storefile1</span> | 
|  | <span class="source-line-no">6388</span><span id="line-6388">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">6389</span><span id="line-6389">    put.add(kv1);</span> | 
|  | <span class="source-line-no">6390</span><span id="line-6390">    region.put(put);</span> | 
|  | <span class="source-line-no">6391</span><span id="line-6391">    region.flush(true);</span> | 
|  | <span class="source-line-no">6392</span><span id="line-6392">    // storefile2</span> | 
|  | <span class="source-line-no">6393</span><span id="line-6393">    put = new Put(row2);</span> | 
|  | <span class="source-line-no">6394</span><span id="line-6394">    put.add(kv2);</span> | 
|  | <span class="source-line-no">6395</span><span id="line-6395">    region.put(put);</span> | 
|  | <span class="source-line-no">6396</span><span id="line-6396">    region.flush(true);</span> | 
|  | <span class="source-line-no">6397</span><span id="line-6397">    // storefile3</span> | 
|  | <span class="source-line-no">6398</span><span id="line-6398">    put = new Put(row3);</span> | 
|  | <span class="source-line-no">6399</span><span id="line-6399">    put.add(kv3);</span> | 
|  | <span class="source-line-no">6400</span><span id="line-6400">    region.put(put);</span> | 
|  | <span class="source-line-no">6401</span><span id="line-6401">    region.flush(true);</span> | 
|  | <span class="source-line-no">6402</span><span id="line-6402">    // memstore</span> | 
|  | <span class="source-line-no">6403</span><span id="line-6403">    put = new Put(row4);</span> | 
|  | <span class="source-line-no">6404</span><span id="line-6404">    put.add(kv4);</span> | 
|  | <span class="source-line-no">6405</span><span id="line-6405">    region.put(put);</span> | 
|  | <span class="source-line-no">6406</span><span id="line-6406">    // scan range = ["row4", min)</span> | 
|  | <span class="source-line-no">6407</span><span id="line-6407">    Scan scan = new Scan().withStartRow(row4);</span> | 
|  | <span class="source-line-no">6408</span><span id="line-6408">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6409</span><span id="line-6409">    scan.setBatch(10);</span> | 
|  | <span class="source-line-no">6410</span><span id="line-6410">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6411</span><span id="line-6411">      List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">6412</span><span id="line-6412">      boolean hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6413</span><span id="line-6413">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6414</span><span id="line-6414">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6415</span><span id="line-6415">        currRow.get(0).getRowLength(), row4, 0, row4.length));</span> | 
|  | <span class="source-line-no">6416</span><span id="line-6416">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6417</span><span id="line-6417">      currRow.clear();</span> | 
|  | <span class="source-line-no">6418</span><span id="line-6418">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6419</span><span id="line-6419">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6420</span><span id="line-6420">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6421</span><span id="line-6421">        currRow.get(0).getRowLength(), row3, 0, row3.length));</span> | 
|  | <span class="source-line-no">6422</span><span id="line-6422">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6423</span><span id="line-6423">      currRow.clear();</span> | 
|  | <span class="source-line-no">6424</span><span id="line-6424">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6425</span><span id="line-6425">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6426</span><span id="line-6426">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6427</span><span id="line-6427">        currRow.get(0).getRowLength(), row2, 0, row2.length));</span> | 
|  | <span class="source-line-no">6428</span><span id="line-6428">      assertTrue(hasNext);</span> | 
|  | <span class="source-line-no">6429</span><span id="line-6429">      currRow.clear();</span> | 
|  | <span class="source-line-no">6430</span><span id="line-6430">      hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6431</span><span id="line-6431">      assertEquals(1, currRow.size());</span> | 
|  | <span class="source-line-no">6432</span><span id="line-6432">      assertTrue(Bytes.equals(currRow.get(0).getRowArray(), currRow.get(0).getRowOffset(),</span> | 
|  | <span class="source-line-no">6433</span><span id="line-6433">        currRow.get(0).getRowLength(), row1, 0, row1.length));</span> | 
|  | <span class="source-line-no">6434</span><span id="line-6434">      assertFalse(hasNext);</span> | 
|  | <span class="source-line-no">6435</span><span id="line-6435">    }</span> | 
|  | <span class="source-line-no">6436</span><span id="line-6436">  }</span> | 
|  | <span class="source-line-no">6437</span><span id="line-6437"></span> | 
|  | <span class="source-line-no">6438</span><span id="line-6438">  /**</span> | 
|  | <span class="source-line-no">6439</span><span id="line-6439">   * Test for HBASE-14497: Reverse Scan threw StackOverflow caused by readPt checking</span> | 
|  | <span class="source-line-no">6440</span><span id="line-6440">   */</span> | 
|  | <span class="source-line-no">6441</span><span id="line-6441">  @Test</span> | 
|  | <span class="source-line-no">6442</span><span id="line-6442">  public void testReverseScanner_StackOverflow() throws IOException {</span> | 
|  | <span class="source-line-no">6443</span><span id="line-6443">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">6444</span><span id="line-6444">    byte[][] families = { cf1 };</span> | 
|  | <span class="source-line-no">6445</span><span id="line-6445">    byte[] col = Bytes.toBytes("C");</span> | 
|  | <span class="source-line-no">6446</span><span id="line-6446">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">6447</span><span id="line-6447">    this.region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">6448</span><span id="line-6448">    // setup with one storefile and one memstore, to create scanner and get an earlier readPt</span> | 
|  | <span class="source-line-no">6449</span><span id="line-6449">    Put put = new Put(Bytes.toBytes("19998"));</span> | 
|  | <span class="source-line-no">6450</span><span id="line-6450">    put.addColumn(cf1, col, Bytes.toBytes("val"));</span> | 
|  | <span class="source-line-no">6451</span><span id="line-6451">    region.put(put);</span> | 
|  | <span class="source-line-no">6452</span><span id="line-6452">    region.flushcache(true, true, FlushLifeCycleTracker.DUMMY);</span> | 
|  | <span class="source-line-no">6453</span><span id="line-6453">    Put put2 = new Put(Bytes.toBytes("19997"));</span> | 
|  | <span class="source-line-no">6454</span><span id="line-6454">    put2.addColumn(cf1, col, Bytes.toBytes("val"));</span> | 
|  | <span class="source-line-no">6455</span><span id="line-6455">    region.put(put2);</span> | 
|  | <span class="source-line-no">6456</span><span id="line-6456"></span> | 
|  | <span class="source-line-no">6457</span><span id="line-6457">    Scan scan = new Scan().withStartRow(Bytes.toBytes("19998"));</span> | 
|  | <span class="source-line-no">6458</span><span id="line-6458">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6459</span><span id="line-6459">    try (InternalScanner scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6460</span><span id="line-6460">      // create one storefile contains many rows will be skipped</span> | 
|  | <span class="source-line-no">6461</span><span id="line-6461">      // to check StoreFileScanner.seekToPreviousRow</span> | 
|  | <span class="source-line-no">6462</span><span id="line-6462">      for (int i = 10000; i < 20000; i++) {</span> | 
|  | <span class="source-line-no">6463</span><span id="line-6463">        Put p = new Put(Bytes.toBytes("" + i));</span> | 
|  | <span class="source-line-no">6464</span><span id="line-6464">        p.addColumn(cf1, col, Bytes.toBytes("" + i));</span> | 
|  | <span class="source-line-no">6465</span><span id="line-6465">        region.put(p);</span> | 
|  | <span class="source-line-no">6466</span><span id="line-6466">      }</span> | 
|  | <span class="source-line-no">6467</span><span id="line-6467">      region.flushcache(true, true, FlushLifeCycleTracker.DUMMY);</span> | 
|  | <span class="source-line-no">6468</span><span id="line-6468"></span> | 
|  | <span class="source-line-no">6469</span><span id="line-6469">      // create one memstore contains many rows will be skipped</span> | 
|  | <span class="source-line-no">6470</span><span id="line-6470">      // to check MemStoreScanner.seekToPreviousRow</span> | 
|  | <span class="source-line-no">6471</span><span id="line-6471">      for (int i = 10000; i < 20000; i++) {</span> | 
|  | <span class="source-line-no">6472</span><span id="line-6472">        Put p = new Put(Bytes.toBytes("" + i));</span> | 
|  | <span class="source-line-no">6473</span><span id="line-6473">        p.addColumn(cf1, col, Bytes.toBytes("" + i));</span> | 
|  | <span class="source-line-no">6474</span><span id="line-6474">        region.put(p);</span> | 
|  | <span class="source-line-no">6475</span><span id="line-6475">      }</span> | 
|  | <span class="source-line-no">6476</span><span id="line-6476"></span> | 
|  | <span class="source-line-no">6477</span><span id="line-6477">      List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">6478</span><span id="line-6478">      boolean hasNext;</span> | 
|  | <span class="source-line-no">6479</span><span id="line-6479">      do {</span> | 
|  | <span class="source-line-no">6480</span><span id="line-6480">        hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6481</span><span id="line-6481">      } while (hasNext);</span> | 
|  | <span class="source-line-no">6482</span><span id="line-6482">      assertEquals(2, currRow.size());</span> | 
|  | <span class="source-line-no">6483</span><span id="line-6483">      assertEquals("19998", Bytes.toString(currRow.get(0).getRowArray(),</span> | 
|  | <span class="source-line-no">6484</span><span id="line-6484">        currRow.get(0).getRowOffset(), currRow.get(0).getRowLength()));</span> | 
|  | <span class="source-line-no">6485</span><span id="line-6485">      assertEquals("19997", Bytes.toString(currRow.get(1).getRowArray(),</span> | 
|  | <span class="source-line-no">6486</span><span id="line-6486">        currRow.get(1).getRowOffset(), currRow.get(1).getRowLength()));</span> | 
|  | <span class="source-line-no">6487</span><span id="line-6487">    }</span> | 
|  | <span class="source-line-no">6488</span><span id="line-6488">  }</span> | 
|  | <span class="source-line-no">6489</span><span id="line-6489"></span> | 
|  | <span class="source-line-no">6490</span><span id="line-6490">  @Test</span> | 
|  | <span class="source-line-no">6491</span><span id="line-6491">  public void testReverseScanShouldNotScanMemstoreIfReadPtLesser() throws Exception {</span> | 
|  | <span class="source-line-no">6492</span><span id="line-6492">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">6493</span><span id="line-6493">    byte[][] families = { cf1 };</span> | 
|  | <span class="source-line-no">6494</span><span id="line-6494">    byte[] col = Bytes.toBytes("C");</span> | 
|  | <span class="source-line-no">6495</span><span id="line-6495">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">6496</span><span id="line-6496">    // setup with one storefile and one memstore, to create scanner and get an earlier readPt</span> | 
|  | <span class="source-line-no">6497</span><span id="line-6497">    Put put = new Put(Bytes.toBytes("19996"));</span> | 
|  | <span class="source-line-no">6498</span><span id="line-6498">    put.addColumn(cf1, col, Bytes.toBytes("val"));</span> | 
|  | <span class="source-line-no">6499</span><span id="line-6499">    region.put(put);</span> | 
|  | <span class="source-line-no">6500</span><span id="line-6500">    Put put2 = new Put(Bytes.toBytes("19995"));</span> | 
|  | <span class="source-line-no">6501</span><span id="line-6501">    put2.addColumn(cf1, col, Bytes.toBytes("val"));</span> | 
|  | <span class="source-line-no">6502</span><span id="line-6502">    region.put(put2);</span> | 
|  | <span class="source-line-no">6503</span><span id="line-6503">    // create a reverse scan</span> | 
|  | <span class="source-line-no">6504</span><span id="line-6504">    Scan scan = new Scan().withStartRow(Bytes.toBytes("19996"));</span> | 
|  | <span class="source-line-no">6505</span><span id="line-6505">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6506</span><span id="line-6506">    try (RegionScannerImpl scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6507</span><span id="line-6507">      // flush the cache. This will reset the store scanner</span> | 
|  | <span class="source-line-no">6508</span><span id="line-6508">      region.flushcache(true, true, FlushLifeCycleTracker.DUMMY);</span> | 
|  | <span class="source-line-no">6509</span><span id="line-6509"></span> | 
|  | <span class="source-line-no">6510</span><span id="line-6510">      // create one memstore contains many rows will be skipped</span> | 
|  | <span class="source-line-no">6511</span><span id="line-6511">      // to check MemStoreScanner.seekToPreviousRow</span> | 
|  | <span class="source-line-no">6512</span><span id="line-6512">      for (int i = 10000; i < 20000; i++) {</span> | 
|  | <span class="source-line-no">6513</span><span id="line-6513">        Put p = new Put(Bytes.toBytes("" + i));</span> | 
|  | <span class="source-line-no">6514</span><span id="line-6514">        p.addColumn(cf1, col, Bytes.toBytes("" + i));</span> | 
|  | <span class="source-line-no">6515</span><span id="line-6515">        region.put(p);</span> | 
|  | <span class="source-line-no">6516</span><span id="line-6516">      }</span> | 
|  | <span class="source-line-no">6517</span><span id="line-6517">      List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">6518</span><span id="line-6518">      boolean hasNext;</span> | 
|  | <span class="source-line-no">6519</span><span id="line-6519">      boolean assertDone = false;</span> | 
|  | <span class="source-line-no">6520</span><span id="line-6520">      do {</span> | 
|  | <span class="source-line-no">6521</span><span id="line-6521">        hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6522</span><span id="line-6522">        // With HBASE-15871, after the scanner is reset the memstore scanner should not be</span> | 
|  | <span class="source-line-no">6523</span><span id="line-6523">        // added here</span> | 
|  | <span class="source-line-no">6524</span><span id="line-6524">        if (!assertDone) {</span> | 
|  | <span class="source-line-no">6525</span><span id="line-6525">          StoreScanner current = (StoreScanner) (scanner.storeHeap).getCurrentForTesting();</span> | 
|  | <span class="source-line-no">6526</span><span id="line-6526">          List<KeyValueScanner> scanners = current.getAllScannersForTesting();</span> | 
|  | <span class="source-line-no">6527</span><span id="line-6527">          assertEquals("There should be only one scanner the store file scanner", 1,</span> | 
|  | <span class="source-line-no">6528</span><span id="line-6528">            scanners.size());</span> | 
|  | <span class="source-line-no">6529</span><span id="line-6529">          assertDone = true;</span> | 
|  | <span class="source-line-no">6530</span><span id="line-6530">        }</span> | 
|  | <span class="source-line-no">6531</span><span id="line-6531">      } while (hasNext);</span> | 
|  | <span class="source-line-no">6532</span><span id="line-6532">      assertEquals(2, currRow.size());</span> | 
|  | <span class="source-line-no">6533</span><span id="line-6533">      assertEquals("19996", Bytes.toString(currRow.get(0).getRowArray(),</span> | 
|  | <span class="source-line-no">6534</span><span id="line-6534">        currRow.get(0).getRowOffset(), currRow.get(0).getRowLength()));</span> | 
|  | <span class="source-line-no">6535</span><span id="line-6535">      assertEquals("19995", Bytes.toString(currRow.get(1).getRowArray(),</span> | 
|  | <span class="source-line-no">6536</span><span id="line-6536">        currRow.get(1).getRowOffset(), currRow.get(1).getRowLength()));</span> | 
|  | <span class="source-line-no">6537</span><span id="line-6537">    }</span> | 
|  | <span class="source-line-no">6538</span><span id="line-6538">  }</span> | 
|  | <span class="source-line-no">6539</span><span id="line-6539"></span> | 
|  | <span class="source-line-no">6540</span><span id="line-6540">  @Test</span> | 
|  | <span class="source-line-no">6541</span><span id="line-6541">  public void testReverseScanWhenPutCellsAfterOpenReverseScan() throws Exception {</span> | 
|  | <span class="source-line-no">6542</span><span id="line-6542">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">6543</span><span id="line-6543">    byte[][] families = { cf1 };</span> | 
|  | <span class="source-line-no">6544</span><span id="line-6544">    byte[] col = Bytes.toBytes("C");</span> | 
|  | <span class="source-line-no">6545</span><span id="line-6545"></span> | 
|  | <span class="source-line-no">6546</span><span id="line-6546">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">6547</span><span id="line-6547"></span> | 
|  | <span class="source-line-no">6548</span><span id="line-6548">    Put put = new Put(Bytes.toBytes("199996"));</span> | 
|  | <span class="source-line-no">6549</span><span id="line-6549">    put.addColumn(cf1, col, Bytes.toBytes("val"));</span> | 
|  | <span class="source-line-no">6550</span><span id="line-6550">    region.put(put);</span> | 
|  | <span class="source-line-no">6551</span><span id="line-6551">    Put put2 = new Put(Bytes.toBytes("199995"));</span> | 
|  | <span class="source-line-no">6552</span><span id="line-6552">    put2.addColumn(cf1, col, Bytes.toBytes("val"));</span> | 
|  | <span class="source-line-no">6553</span><span id="line-6553">    region.put(put2);</span> | 
|  | <span class="source-line-no">6554</span><span id="line-6554"></span> | 
|  | <span class="source-line-no">6555</span><span id="line-6555">    // Create a reverse scan</span> | 
|  | <span class="source-line-no">6556</span><span id="line-6556">    Scan scan = new Scan().withStartRow(Bytes.toBytes("199996"));</span> | 
|  | <span class="source-line-no">6557</span><span id="line-6557">    scan.setReversed(true);</span> | 
|  | <span class="source-line-no">6558</span><span id="line-6558">    try (RegionScannerImpl scanner = region.getScanner(scan)) {</span> | 
|  | <span class="source-line-no">6559</span><span id="line-6559">      // Put a lot of cells that have sequenceIDs grater than the readPt of the reverse scan</span> | 
|  | <span class="source-line-no">6560</span><span id="line-6560">      for (int i = 100000; i < 200000; i++) {</span> | 
|  | <span class="source-line-no">6561</span><span id="line-6561">        Put p = new Put(Bytes.toBytes("" + i));</span> | 
|  | <span class="source-line-no">6562</span><span id="line-6562">        p.addColumn(cf1, col, Bytes.toBytes("" + i));</span> | 
|  | <span class="source-line-no">6563</span><span id="line-6563">        region.put(p);</span> | 
|  | <span class="source-line-no">6564</span><span id="line-6564">      }</span> | 
|  | <span class="source-line-no">6565</span><span id="line-6565">      List<Cell> currRow = new ArrayList<>();</span> | 
|  | <span class="source-line-no">6566</span><span id="line-6566">      boolean hasNext;</span> | 
|  | <span class="source-line-no">6567</span><span id="line-6567">      do {</span> | 
|  | <span class="source-line-no">6568</span><span id="line-6568">        hasNext = scanner.next(currRow);</span> | 
|  | <span class="source-line-no">6569</span><span id="line-6569">      } while (hasNext);</span> | 
|  | <span class="source-line-no">6570</span><span id="line-6570"></span> | 
|  | <span class="source-line-no">6571</span><span id="line-6571">      assertEquals(2, currRow.size());</span> | 
|  | <span class="source-line-no">6572</span><span id="line-6572">      assertEquals("199996", Bytes.toString(currRow.get(0).getRowArray(),</span> | 
|  | <span class="source-line-no">6573</span><span id="line-6573">        currRow.get(0).getRowOffset(), currRow.get(0).getRowLength()));</span> | 
|  | <span class="source-line-no">6574</span><span id="line-6574">      assertEquals("199995", Bytes.toString(currRow.get(1).getRowArray(),</span> | 
|  | <span class="source-line-no">6575</span><span id="line-6575">        currRow.get(1).getRowOffset(), currRow.get(1).getRowLength()));</span> | 
|  | <span class="source-line-no">6576</span><span id="line-6576">    }</span> | 
|  | <span class="source-line-no">6577</span><span id="line-6577">  }</span> | 
|  | <span class="source-line-no">6578</span><span id="line-6578"></span> | 
|  | <span class="source-line-no">6579</span><span id="line-6579">  @Test</span> | 
|  | <span class="source-line-no">6580</span><span id="line-6580">  public void testWriteRequestsCounter() throws IOException {</span> | 
|  | <span class="source-line-no">6581</span><span id="line-6581">    byte[] fam = Bytes.toBytes("info");</span> | 
|  | <span class="source-line-no">6582</span><span id="line-6582">    byte[][] families = { fam };</span> | 
|  | <span class="source-line-no">6583</span><span id="line-6583">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">6584</span><span id="line-6584"></span> | 
|  | <span class="source-line-no">6585</span><span id="line-6585">    Assert.assertEquals(0L, region.getWriteRequestsCount());</span> | 
|  | <span class="source-line-no">6586</span><span id="line-6586"></span> | 
|  | <span class="source-line-no">6587</span><span id="line-6587">    Put put = new Put(row);</span> | 
|  | <span class="source-line-no">6588</span><span id="line-6588">    put.addColumn(fam, fam, fam);</span> | 
|  | <span class="source-line-no">6589</span><span id="line-6589"></span> | 
|  | <span class="source-line-no">6590</span><span id="line-6590">    Assert.assertEquals(0L, region.getWriteRequestsCount());</span> | 
|  | <span class="source-line-no">6591</span><span id="line-6591">    region.put(put);</span> | 
|  | <span class="source-line-no">6592</span><span id="line-6592">    Assert.assertEquals(1L, region.getWriteRequestsCount());</span> | 
|  | <span class="source-line-no">6593</span><span id="line-6593">    region.put(put);</span> | 
|  | <span class="source-line-no">6594</span><span id="line-6594">    Assert.assertEquals(2L, region.getWriteRequestsCount());</span> | 
|  | <span class="source-line-no">6595</span><span id="line-6595">    region.put(put);</span> | 
|  | <span class="source-line-no">6596</span><span id="line-6596">    Assert.assertEquals(3L, region.getWriteRequestsCount());</span> | 
|  | <span class="source-line-no">6597</span><span id="line-6597"></span> | 
|  | <span class="source-line-no">6598</span><span id="line-6598">    region.delete(new Delete(row));</span> | 
|  | <span class="source-line-no">6599</span><span id="line-6599">    Assert.assertEquals(4L, region.getWriteRequestsCount());</span> | 
|  | <span class="source-line-no">6600</span><span id="line-6600">  }</span> | 
|  | <span class="source-line-no">6601</span><span id="line-6601"></span> | 
|  | <span class="source-line-no">6602</span><span id="line-6602">  @Test</span> | 
|  | <span class="source-line-no">6603</span><span id="line-6603">  public void testOpenRegionWrittenToWAL() throws Exception {</span> | 
|  | <span class="source-line-no">6604</span><span id="line-6604">    final ServerName serverName = ServerName.valueOf(name.getMethodName(), 100, 42);</span> | 
|  | <span class="source-line-no">6605</span><span id="line-6605">    final RegionServerServices rss = spy(TEST_UTIL.createMockRegionServerService(serverName));</span> | 
|  | <span class="source-line-no">6606</span><span id="line-6606"></span> | 
|  | <span class="source-line-no">6607</span><span id="line-6607">    TableDescriptor htd = TableDescriptorBuilder.newBuilder(TableName.valueOf(name.getMethodName()))</span> | 
|  | <span class="source-line-no">6608</span><span id="line-6608">      .setColumnFamily(ColumnFamilyDescriptorBuilder.of(fam1))</span> | 
|  | <span class="source-line-no">6609</span><span id="line-6609">      .setColumnFamily(ColumnFamilyDescriptorBuilder.of(fam2)).build();</span> | 
|  | <span class="source-line-no">6610</span><span id="line-6610">    RegionInfo hri = RegionInfoBuilder.newBuilder(htd.getTableName()).build();</span> | 
|  | <span class="source-line-no">6611</span><span id="line-6611"></span> | 
|  | <span class="source-line-no">6612</span><span id="line-6612">    // open the region w/o rss and wal and flush some files</span> | 
|  | <span class="source-line-no">6613</span><span id="line-6613">    region = HBaseTestingUtil.createRegionAndWAL(hri, TEST_UTIL.getDataTestDir(),</span> | 
|  | <span class="source-line-no">6614</span><span id="line-6614">      TEST_UTIL.getConfiguration(), htd);</span> | 
|  | <span class="source-line-no">6615</span><span id="line-6615">    assertNotNull(region);</span> | 
|  | <span class="source-line-no">6616</span><span id="line-6616"></span> | 
|  | <span class="source-line-no">6617</span><span id="line-6617">    // create a file in fam1 for the region before opening in OpenRegionHandler</span> | 
|  | <span class="source-line-no">6618</span><span id="line-6618">    region.put(new Put(Bytes.toBytes("a")).addColumn(fam1, fam1, fam1));</span> | 
|  | <span class="source-line-no">6619</span><span id="line-6619">    region.flush(true);</span> | 
|  | <span class="source-line-no">6620</span><span id="line-6620">    HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">6621</span><span id="line-6621"></span> | 
|  | <span class="source-line-no">6622</span><span id="line-6622">    ArgumentCaptor<WALEdit> editCaptor = ArgumentCaptor.forClass(WALEdit.class);</span> | 
|  | <span class="source-line-no">6623</span><span id="line-6623"></span> | 
|  | <span class="source-line-no">6624</span><span id="line-6624">    // capture append() calls</span> | 
|  | <span class="source-line-no">6625</span><span id="line-6625">    WAL wal = mockWAL();</span> | 
|  | <span class="source-line-no">6626</span><span id="line-6626">    when(rss.getWAL(any(RegionInfo.class))).thenReturn(wal);</span> | 
|  | <span class="source-line-no">6627</span><span id="line-6627"></span> | 
|  | <span class="source-line-no">6628</span><span id="line-6628">    region =</span> | 
|  | <span class="source-line-no">6629</span><span id="line-6629">      HRegion.openHRegion(hri, htd, rss.getWAL(hri), TEST_UTIL.getConfiguration(), rss, null);</span> | 
|  | <span class="source-line-no">6630</span><span id="line-6630"></span> | 
|  | <span class="source-line-no">6631</span><span id="line-6631">    verify(wal, times(1)).appendMarker(any(RegionInfo.class), any(WALKeyImpl.class),</span> | 
|  | <span class="source-line-no">6632</span><span id="line-6632">      editCaptor.capture());</span> | 
|  | <span class="source-line-no">6633</span><span id="line-6633"></span> | 
|  | <span class="source-line-no">6634</span><span id="line-6634">    WALEdit edit = editCaptor.getValue();</span> | 
|  | <span class="source-line-no">6635</span><span id="line-6635">    assertNotNull(edit);</span> | 
|  | <span class="source-line-no">6636</span><span id="line-6636">    assertNotNull(edit.getCells());</span> | 
|  | <span class="source-line-no">6637</span><span id="line-6637">    assertEquals(1, edit.getCells().size());</span> | 
|  | <span class="source-line-no">6638</span><span id="line-6638">    RegionEventDescriptor desc = WALEdit.getRegionEventDescriptor(edit.getCells().get(0));</span> | 
|  | <span class="source-line-no">6639</span><span id="line-6639">    assertNotNull(desc);</span> | 
|  | <span class="source-line-no">6640</span><span id="line-6640"></span> | 
|  | <span class="source-line-no">6641</span><span id="line-6641">    LOG.info("RegionEventDescriptor from WAL: " + desc);</span> | 
|  | <span class="source-line-no">6642</span><span id="line-6642"></span> | 
|  | <span class="source-line-no">6643</span><span id="line-6643">    assertEquals(RegionEventDescriptor.EventType.REGION_OPEN, desc.getEventType());</span> | 
|  | <span class="source-line-no">6644</span><span id="line-6644">    assertTrue(Bytes.equals(desc.getTableName().toByteArray(), htd.getTableName().toBytes()));</span> | 
|  | <span class="source-line-no">6645</span><span id="line-6645">    assertTrue(</span> | 
|  | <span class="source-line-no">6646</span><span id="line-6646">      Bytes.equals(desc.getEncodedRegionName().toByteArray(), hri.getEncodedNameAsBytes()));</span> | 
|  | <span class="source-line-no">6647</span><span id="line-6647">    assertTrue(desc.getLogSequenceNumber() > 0);</span> | 
|  | <span class="source-line-no">6648</span><span id="line-6648">    assertEquals(serverName, ProtobufUtil.toServerName(desc.getServer()));</span> | 
|  | <span class="source-line-no">6649</span><span id="line-6649">    assertEquals(2, desc.getStoresCount());</span> | 
|  | <span class="source-line-no">6650</span><span id="line-6650"></span> | 
|  | <span class="source-line-no">6651</span><span id="line-6651">    StoreDescriptor store = desc.getStores(0);</span> | 
|  | <span class="source-line-no">6652</span><span id="line-6652">    assertTrue(Bytes.equals(store.getFamilyName().toByteArray(), fam1));</span> | 
|  | <span class="source-line-no">6653</span><span id="line-6653">    assertEquals(store.getStoreHomeDir(), Bytes.toString(fam1));</span> | 
|  | <span class="source-line-no">6654</span><span id="line-6654">    assertEquals(1, store.getStoreFileCount()); // 1store file</span> | 
|  | <span class="source-line-no">6655</span><span id="line-6655">    assertFalse(store.getStoreFile(0).contains("/")); // ensure path is relative</span> | 
|  | <span class="source-line-no">6656</span><span id="line-6656"></span> | 
|  | <span class="source-line-no">6657</span><span id="line-6657">    store = desc.getStores(1);</span> | 
|  | <span class="source-line-no">6658</span><span id="line-6658">    assertTrue(Bytes.equals(store.getFamilyName().toByteArray(), fam2));</span> | 
|  | <span class="source-line-no">6659</span><span id="line-6659">    assertEquals(store.getStoreHomeDir(), Bytes.toString(fam2));</span> | 
|  | <span class="source-line-no">6660</span><span id="line-6660">    assertEquals(0, store.getStoreFileCount()); // no store files</span> | 
|  | <span class="source-line-no">6661</span><span id="line-6661">  }</span> | 
|  | <span class="source-line-no">6662</span><span id="line-6662"></span> | 
|  | <span class="source-line-no">6663</span><span id="line-6663">  // Helper for test testOpenRegionWrittenToWALForLogReplay</span> | 
|  | <span class="source-line-no">6664</span><span id="line-6664">  static class HRegionWithSeqId extends HRegion {</span> | 
|  | <span class="source-line-no">6665</span><span id="line-6665">    public HRegionWithSeqId(final Path tableDir, final WAL wal, final FileSystem fs,</span> | 
|  | <span class="source-line-no">6666</span><span id="line-6666">      final Configuration confParam, final RegionInfo regionInfo, final TableDescriptor htd,</span> | 
|  | <span class="source-line-no">6667</span><span id="line-6667">      final RegionServerServices rsServices) {</span> | 
|  | <span class="source-line-no">6668</span><span id="line-6668">      super(tableDir, wal, fs, confParam, regionInfo, htd, rsServices);</span> | 
|  | <span class="source-line-no">6669</span><span id="line-6669">    }</span> | 
|  | <span class="source-line-no">6670</span><span id="line-6670"></span> | 
|  | <span class="source-line-no">6671</span><span id="line-6671">    @Override</span> | 
|  | <span class="source-line-no">6672</span><span id="line-6672">    protected long getNextSequenceId(WAL wal) throws IOException {</span> | 
|  | <span class="source-line-no">6673</span><span id="line-6673">      return 42;</span> | 
|  | <span class="source-line-no">6674</span><span id="line-6674">    }</span> | 
|  | <span class="source-line-no">6675</span><span id="line-6675">  }</span> | 
|  | <span class="source-line-no">6676</span><span id="line-6676"></span> | 
|  | <span class="source-line-no">6677</span><span id="line-6677">  @Test</span> | 
|  | <span class="source-line-no">6678</span><span id="line-6678">  public void testFlushedFileWithNoTags() throws Exception {</span> | 
|  | <span class="source-line-no">6679</span><span id="line-6679">    final TableName tableName = TableName.valueOf(name.getMethodName());</span> | 
|  | <span class="source-line-no">6680</span><span id="line-6680">    TableDescriptor tableDescriptor = TableDescriptorBuilder.newBuilder(tableName)</span> | 
|  | <span class="source-line-no">6681</span><span id="line-6681">      .setColumnFamily(ColumnFamilyDescriptorBuilder.of(fam1)).build();</span> | 
|  | <span class="source-line-no">6682</span><span id="line-6682">    RegionInfo info = RegionInfoBuilder.newBuilder(tableName).build();</span> | 
|  | <span class="source-line-no">6683</span><span id="line-6683">    Path path = TEST_UTIL.getDataTestDir(getClass().getSimpleName());</span> | 
|  | <span class="source-line-no">6684</span><span id="line-6684">    region = HBaseTestingUtil.createRegionAndWAL(info, path, TEST_UTIL.getConfiguration(),</span> | 
|  | <span class="source-line-no">6685</span><span id="line-6685">      tableDescriptor);</span> | 
|  | <span class="source-line-no">6686</span><span id="line-6686">    Put put = new Put(Bytes.toBytes("a-b-0-0"));</span> | 
|  | <span class="source-line-no">6687</span><span id="line-6687">    put.addColumn(fam1, qual1, Bytes.toBytes("c1-value"));</span> | 
|  | <span class="source-line-no">6688</span><span id="line-6688">    region.put(put);</span> | 
|  | <span class="source-line-no">6689</span><span id="line-6689">    region.flush(true);</span> | 
|  | <span class="source-line-no">6690</span><span id="line-6690">    HStore store = region.getStore(fam1);</span> | 
|  | <span class="source-line-no">6691</span><span id="line-6691">    Collection<HStoreFile> storefiles = store.getStorefiles();</span> | 
|  | <span class="source-line-no">6692</span><span id="line-6692">    for (HStoreFile sf : storefiles) {</span> | 
|  | <span class="source-line-no">6693</span><span id="line-6693">      assertFalse("Tags should not be present ",</span> | 
|  | <span class="source-line-no">6694</span><span id="line-6694">        sf.getReader().getHFileReader().getFileContext().isIncludesTags());</span> | 
|  | <span class="source-line-no">6695</span><span id="line-6695">    }</span> | 
|  | <span class="source-line-no">6696</span><span id="line-6696">  }</span> | 
|  | <span class="source-line-no">6697</span><span id="line-6697"></span> | 
|  | <span class="source-line-no">6698</span><span id="line-6698">  /**</span> | 
|  | <span class="source-line-no">6699</span><span id="line-6699">   * Utility method to setup a WAL mock.</span> | 
|  | <span class="source-line-no">6700</span><span id="line-6700">   * <p/></span> | 
|  | <span class="source-line-no">6701</span><span id="line-6701">   * Needs to do the bit where we close latch on the WALKeyImpl on append else test hangs.</span> | 
|  | <span class="source-line-no">6702</span><span id="line-6702">   * @return a mock WAL</span> | 
|  | <span class="source-line-no">6703</span><span id="line-6703">   */</span> | 
|  | <span class="source-line-no">6704</span><span id="line-6704">  private WAL mockWAL() throws IOException {</span> | 
|  | <span class="source-line-no">6705</span><span id="line-6705">    WAL wal = mock(WAL.class);</span> | 
|  | <span class="source-line-no">6706</span><span id="line-6706">    when(wal.appendData(any(RegionInfo.class), any(WALKeyImpl.class), any(WALEdit.class)))</span> | 
|  | <span class="source-line-no">6707</span><span id="line-6707">      .thenAnswer(new Answer<Long>() {</span> | 
|  | <span class="source-line-no">6708</span><span id="line-6708">        @Override</span> | 
|  | <span class="source-line-no">6709</span><span id="line-6709">        public Long answer(InvocationOnMock invocation) throws Throwable {</span> | 
|  | <span class="source-line-no">6710</span><span id="line-6710">          WALKeyImpl key = invocation.getArgument(1);</span> | 
|  | <span class="source-line-no">6711</span><span id="line-6711">          MultiVersionConcurrencyControl.WriteEntry we = key.getMvcc().begin();</span> | 
|  | <span class="source-line-no">6712</span><span id="line-6712">          key.setWriteEntry(we);</span> | 
|  | <span class="source-line-no">6713</span><span id="line-6713">          return 1L;</span> | 
|  | <span class="source-line-no">6714</span><span id="line-6714">        }</span> | 
|  | <span class="source-line-no">6715</span><span id="line-6715">      });</span> | 
|  | <span class="source-line-no">6716</span><span id="line-6716">    when(wal.appendMarker(any(RegionInfo.class), any(WALKeyImpl.class), any(WALEdit.class)))</span> | 
|  | <span class="source-line-no">6717</span><span id="line-6717">      .thenAnswer(new Answer<Long>() {</span> | 
|  | <span class="source-line-no">6718</span><span id="line-6718">        @Override</span> | 
|  | <span class="source-line-no">6719</span><span id="line-6719">        public Long answer(InvocationOnMock invocation) throws Throwable {</span> | 
|  | <span class="source-line-no">6720</span><span id="line-6720">          WALKeyImpl key = invocation.getArgument(1);</span> | 
|  | <span class="source-line-no">6721</span><span id="line-6721">          MultiVersionConcurrencyControl.WriteEntry we = key.getMvcc().begin();</span> | 
|  | <span class="source-line-no">6722</span><span id="line-6722">          key.setWriteEntry(we);</span> | 
|  | <span class="source-line-no">6723</span><span id="line-6723">          return 1L;</span> | 
|  | <span class="source-line-no">6724</span><span id="line-6724">        }</span> | 
|  | <span class="source-line-no">6725</span><span id="line-6725">      });</span> | 
|  | <span class="source-line-no">6726</span><span id="line-6726">    return wal;</span> | 
|  | <span class="source-line-no">6727</span><span id="line-6727">  }</span> | 
|  | <span class="source-line-no">6728</span><span id="line-6728"></span> | 
|  | <span class="source-line-no">6729</span><span id="line-6729">  @Test</span> | 
|  | <span class="source-line-no">6730</span><span id="line-6730">  public void testCloseRegionWrittenToWAL() throws Exception {</span> | 
|  | <span class="source-line-no">6731</span><span id="line-6731">    Path rootDir = new Path(dir + name.getMethodName());</span> | 
|  | <span class="source-line-no">6732</span><span id="line-6732">    CommonFSUtils.setRootDir(TEST_UTIL.getConfiguration(), rootDir);</span> | 
|  | <span class="source-line-no">6733</span><span id="line-6733"></span> | 
|  | <span class="source-line-no">6734</span><span id="line-6734">    final ServerName serverName = ServerName.valueOf("testCloseRegionWrittenToWAL", 100, 42);</span> | 
|  | <span class="source-line-no">6735</span><span id="line-6735">    final RegionServerServices rss = spy(TEST_UTIL.createMockRegionServerService(serverName));</span> | 
|  | <span class="source-line-no">6736</span><span id="line-6736"></span> | 
|  | <span class="source-line-no">6737</span><span id="line-6737">    TableDescriptor htd = TableDescriptorBuilder.newBuilder(TableName.valueOf(name.getMethodName()))</span> | 
|  | <span class="source-line-no">6738</span><span id="line-6738">      .setColumnFamily(ColumnFamilyDescriptorBuilder.of(fam1))</span> | 
|  | <span class="source-line-no">6739</span><span id="line-6739">      .setColumnFamily(ColumnFamilyDescriptorBuilder.of(fam2)).build();</span> | 
|  | <span class="source-line-no">6740</span><span id="line-6740">    RegionInfo hri = RegionInfoBuilder.newBuilder(htd.getTableName()).build();</span> | 
|  | <span class="source-line-no">6741</span><span id="line-6741"></span> | 
|  | <span class="source-line-no">6742</span><span id="line-6742">    ArgumentCaptor<WALEdit> editCaptor = ArgumentCaptor.forClass(WALEdit.class);</span> | 
|  | <span class="source-line-no">6743</span><span id="line-6743"></span> | 
|  | <span class="source-line-no">6744</span><span id="line-6744">    // capture append() calls</span> | 
|  | <span class="source-line-no">6745</span><span id="line-6745">    WAL wal = mockWAL();</span> | 
|  | <span class="source-line-no">6746</span><span id="line-6746">    when(rss.getWAL(any(RegionInfo.class))).thenReturn(wal);</span> | 
|  | <span class="source-line-no">6747</span><span id="line-6747"></span> | 
|  | <span class="source-line-no">6748</span><span id="line-6748">    // create the region</span> | 
|  | <span class="source-line-no">6749</span><span id="line-6749">    region = HBaseTestingUtil.createRegionAndWAL(hri, rootDir, CONF, htd);</span> | 
|  | <span class="source-line-no">6750</span><span id="line-6750">    HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">6751</span><span id="line-6751">    region = null;</span> | 
|  | <span class="source-line-no">6752</span><span id="line-6752">    // open the region first and then close it</span> | 
|  | <span class="source-line-no">6753</span><span id="line-6753">    HRegion.openHRegion(hri, htd, rss.getWAL(hri), TEST_UTIL.getConfiguration(), rss, null).close();</span> | 
|  | <span class="source-line-no">6754</span><span id="line-6754"></span> | 
|  | <span class="source-line-no">6755</span><span id="line-6755">    // 2 times, one for region open, the other close region</span> | 
|  | <span class="source-line-no">6756</span><span id="line-6756">    verify(wal, times(2)).appendMarker(any(RegionInfo.class), (WALKeyImpl) any(WALKeyImpl.class),</span> | 
|  | <span class="source-line-no">6757</span><span id="line-6757">      editCaptor.capture());</span> | 
|  | <span class="source-line-no">6758</span><span id="line-6758"></span> | 
|  | <span class="source-line-no">6759</span><span id="line-6759">    WALEdit edit = editCaptor.getAllValues().get(1);</span> | 
|  | <span class="source-line-no">6760</span><span id="line-6760">    assertNotNull(edit);</span> | 
|  | <span class="source-line-no">6761</span><span id="line-6761">    assertNotNull(edit.getCells());</span> | 
|  | <span class="source-line-no">6762</span><span id="line-6762">    assertEquals(1, edit.getCells().size());</span> | 
|  | <span class="source-line-no">6763</span><span id="line-6763">    RegionEventDescriptor desc = WALEdit.getRegionEventDescriptor(edit.getCells().get(0));</span> | 
|  | <span class="source-line-no">6764</span><span id="line-6764">    assertNotNull(desc);</span> | 
|  | <span class="source-line-no">6765</span><span id="line-6765"></span> | 
|  | <span class="source-line-no">6766</span><span id="line-6766">    LOG.info("RegionEventDescriptor from WAL: " + desc);</span> | 
|  | <span class="source-line-no">6767</span><span id="line-6767"></span> | 
|  | <span class="source-line-no">6768</span><span id="line-6768">    assertEquals(RegionEventDescriptor.EventType.REGION_CLOSE, desc.getEventType());</span> | 
|  | <span class="source-line-no">6769</span><span id="line-6769">    assertTrue(Bytes.equals(desc.getTableName().toByteArray(), htd.getTableName().toBytes()));</span> | 
|  | <span class="source-line-no">6770</span><span id="line-6770">    assertTrue(</span> | 
|  | <span class="source-line-no">6771</span><span id="line-6771">      Bytes.equals(desc.getEncodedRegionName().toByteArray(), hri.getEncodedNameAsBytes()));</span> | 
|  | <span class="source-line-no">6772</span><span id="line-6772">    assertTrue(desc.getLogSequenceNumber() > 0);</span> | 
|  | <span class="source-line-no">6773</span><span id="line-6773">    assertEquals(serverName, ProtobufUtil.toServerName(desc.getServer()));</span> | 
|  | <span class="source-line-no">6774</span><span id="line-6774">    assertEquals(2, desc.getStoresCount());</span> | 
|  | <span class="source-line-no">6775</span><span id="line-6775"></span> | 
|  | <span class="source-line-no">6776</span><span id="line-6776">    StoreDescriptor store = desc.getStores(0);</span> | 
|  | <span class="source-line-no">6777</span><span id="line-6777">    assertTrue(Bytes.equals(store.getFamilyName().toByteArray(), fam1));</span> | 
|  | <span class="source-line-no">6778</span><span id="line-6778">    assertEquals(store.getStoreHomeDir(), Bytes.toString(fam1));</span> | 
|  | <span class="source-line-no">6779</span><span id="line-6779">    assertEquals(0, store.getStoreFileCount()); // no store files</span> | 
|  | <span class="source-line-no">6780</span><span id="line-6780"></span> | 
|  | <span class="source-line-no">6781</span><span id="line-6781">    store = desc.getStores(1);</span> | 
|  | <span class="source-line-no">6782</span><span id="line-6782">    assertTrue(Bytes.equals(store.getFamilyName().toByteArray(), fam2));</span> | 
|  | <span class="source-line-no">6783</span><span id="line-6783">    assertEquals(store.getStoreHomeDir(), Bytes.toString(fam2));</span> | 
|  | <span class="source-line-no">6784</span><span id="line-6784">    assertEquals(0, store.getStoreFileCount()); // no store files</span> | 
|  | <span class="source-line-no">6785</span><span id="line-6785">  }</span> | 
|  | <span class="source-line-no">6786</span><span id="line-6786"></span> | 
|  | <span class="source-line-no">6787</span><span id="line-6787">  /**</span> | 
|  | <span class="source-line-no">6788</span><span id="line-6788">   * Test RegionTooBusyException thrown when region is busy</span> | 
|  | <span class="source-line-no">6789</span><span id="line-6789">   */</span> | 
|  | <span class="source-line-no">6790</span><span id="line-6790">  @Test</span> | 
|  | <span class="source-line-no">6791</span><span id="line-6791">  public void testRegionTooBusy() throws IOException {</span> | 
|  | <span class="source-line-no">6792</span><span id="line-6792">    byte[] family = Bytes.toBytes("family");</span> | 
|  | <span class="source-line-no">6793</span><span id="line-6793">    long defaultBusyWaitDuration =</span> | 
|  | <span class="source-line-no">6794</span><span id="line-6794">      CONF.getLong("hbase.busy.wait.duration", HRegion.DEFAULT_BUSY_WAIT_DURATION);</span> | 
|  | <span class="source-line-no">6795</span><span id="line-6795">    CONF.setLong("hbase.busy.wait.duration", 1000);</span> | 
|  | <span class="source-line-no">6796</span><span id="line-6796">    region = initHRegion(tableName, method, CONF, family);</span> | 
|  | <span class="source-line-no">6797</span><span id="line-6797">    final AtomicBoolean stopped = new AtomicBoolean(true);</span> | 
|  | <span class="source-line-no">6798</span><span id="line-6798">    Thread t = new Thread(new Runnable() {</span> | 
|  | <span class="source-line-no">6799</span><span id="line-6799">      @Override</span> | 
|  | <span class="source-line-no">6800</span><span id="line-6800">      public void run() {</span> | 
|  | <span class="source-line-no">6801</span><span id="line-6801">        try {</span> | 
|  | <span class="source-line-no">6802</span><span id="line-6802">          region.lock.writeLock().lock();</span> | 
|  | <span class="source-line-no">6803</span><span id="line-6803">          stopped.set(false);</span> | 
|  | <span class="source-line-no">6804</span><span id="line-6804">          while (!stopped.get()) {</span> | 
|  | <span class="source-line-no">6805</span><span id="line-6805">            Thread.sleep(100);</span> | 
|  | <span class="source-line-no">6806</span><span id="line-6806">          }</span> | 
|  | <span class="source-line-no">6807</span><span id="line-6807">        } catch (InterruptedException ie) {</span> | 
|  | <span class="source-line-no">6808</span><span id="line-6808">        } finally {</span> | 
|  | <span class="source-line-no">6809</span><span id="line-6809">          region.lock.writeLock().unlock();</span> | 
|  | <span class="source-line-no">6810</span><span id="line-6810">        }</span> | 
|  | <span class="source-line-no">6811</span><span id="line-6811">      }</span> | 
|  | <span class="source-line-no">6812</span><span id="line-6812">    });</span> | 
|  | <span class="source-line-no">6813</span><span id="line-6813">    t.start();</span> | 
|  | <span class="source-line-no">6814</span><span id="line-6814">    Get get = new Get(row);</span> | 
|  | <span class="source-line-no">6815</span><span id="line-6815">    try {</span> | 
|  | <span class="source-line-no">6816</span><span id="line-6816">      while (stopped.get()) {</span> | 
|  | <span class="source-line-no">6817</span><span id="line-6817">        Thread.sleep(100);</span> | 
|  | <span class="source-line-no">6818</span><span id="line-6818">      }</span> | 
|  | <span class="source-line-no">6819</span><span id="line-6819">      region.get(get);</span> | 
|  | <span class="source-line-no">6820</span><span id="line-6820">      fail("Should throw RegionTooBusyException");</span> | 
|  | <span class="source-line-no">6821</span><span id="line-6821">    } catch (InterruptedException ie) {</span> | 
|  | <span class="source-line-no">6822</span><span id="line-6822">      fail("test interrupted");</span> | 
|  | <span class="source-line-no">6823</span><span id="line-6823">    } catch (RegionTooBusyException e) {</span> | 
|  | <span class="source-line-no">6824</span><span id="line-6824">      // Good, expected</span> | 
|  | <span class="source-line-no">6825</span><span id="line-6825">    } finally {</span> | 
|  | <span class="source-line-no">6826</span><span id="line-6826">      stopped.set(true);</span> | 
|  | <span class="source-line-no">6827</span><span id="line-6827">      try {</span> | 
|  | <span class="source-line-no">6828</span><span id="line-6828">        t.join();</span> | 
|  | <span class="source-line-no">6829</span><span id="line-6829">      } catch (Throwable e) {</span> | 
|  | <span class="source-line-no">6830</span><span id="line-6830">      }</span> | 
|  | <span class="source-line-no">6831</span><span id="line-6831"></span> | 
|  | <span class="source-line-no">6832</span><span id="line-6832">      HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">6833</span><span id="line-6833">      region = null;</span> | 
|  | <span class="source-line-no">6834</span><span id="line-6834">      CONF.setLong("hbase.busy.wait.duration", defaultBusyWaitDuration);</span> | 
|  | <span class="source-line-no">6835</span><span id="line-6835">    }</span> | 
|  | <span class="source-line-no">6836</span><span id="line-6836">  }</span> | 
|  | <span class="source-line-no">6837</span><span id="line-6837"></span> | 
|  | <span class="source-line-no">6838</span><span id="line-6838">  @Test</span> | 
|  | <span class="source-line-no">6839</span><span id="line-6839">  public void testCellTTLs() throws IOException {</span> | 
|  | <span class="source-line-no">6840</span><span id="line-6840">    IncrementingEnvironmentEdge edge = new IncrementingEnvironmentEdge();</span> | 
|  | <span class="source-line-no">6841</span><span id="line-6841">    EnvironmentEdgeManager.injectEdge(edge);</span> | 
|  | <span class="source-line-no">6842</span><span id="line-6842"></span> | 
|  | <span class="source-line-no">6843</span><span id="line-6843">    final byte[] row = Bytes.toBytes("testRow");</span> | 
|  | <span class="source-line-no">6844</span><span id="line-6844">    final byte[] q1 = Bytes.toBytes("q1");</span> | 
|  | <span class="source-line-no">6845</span><span id="line-6845">    final byte[] q2 = Bytes.toBytes("q2");</span> | 
|  | <span class="source-line-no">6846</span><span id="line-6846">    final byte[] q3 = Bytes.toBytes("q3");</span> | 
|  | <span class="source-line-no">6847</span><span id="line-6847">    final byte[] q4 = Bytes.toBytes("q4");</span> | 
|  | <span class="source-line-no">6848</span><span id="line-6848"></span> | 
|  | <span class="source-line-no">6849</span><span id="line-6849">    // 10 seconds</span> | 
|  | <span class="source-line-no">6850</span><span id="line-6850">    TableDescriptor tableDescriptor =</span> | 
|  | <span class="source-line-no">6851</span><span id="line-6851">      TableDescriptorBuilder.newBuilder(TableName.valueOf(name.getMethodName()))</span> | 
|  | <span class="source-line-no">6852</span><span id="line-6852">        .setColumnFamily(ColumnFamilyDescriptorBuilder.newBuilder(fam1).setTimeToLive(10).build())</span> | 
|  | <span class="source-line-no">6853</span><span id="line-6853">        .build();</span> | 
|  | <span class="source-line-no">6854</span><span id="line-6854"></span> | 
|  | <span class="source-line-no">6855</span><span id="line-6855">    Configuration conf = new Configuration(TEST_UTIL.getConfiguration());</span> | 
|  | <span class="source-line-no">6856</span><span id="line-6856">    conf.setInt(HFile.FORMAT_VERSION_KEY, HFile.MIN_FORMAT_VERSION_WITH_TAGS);</span> | 
|  | <span class="source-line-no">6857</span><span id="line-6857"></span> | 
|  | <span class="source-line-no">6858</span><span id="line-6858">    region = HBaseTestingUtil.createRegionAndWAL(</span> | 
|  | <span class="source-line-no">6859</span><span id="line-6859">      RegionInfoBuilder.newBuilder(tableDescriptor.getTableName()).build(),</span> | 
|  | <span class="source-line-no">6860</span><span id="line-6860">      TEST_UTIL.getDataTestDir(), conf, tableDescriptor);</span> | 
|  | <span class="source-line-no">6861</span><span id="line-6861">    assertNotNull(region);</span> | 
|  | <span class="source-line-no">6862</span><span id="line-6862">    long now = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">6863</span><span id="line-6863">    // Add a cell that will expire in 5 seconds via cell TTL</span> | 
|  | <span class="source-line-no">6864</span><span id="line-6864">    region.put(new Put(row).add(new KeyValue(row, fam1, q1, now, HConstants.EMPTY_BYTE_ARRAY,</span> | 
|  | <span class="source-line-no">6865</span><span id="line-6865">      new ArrayBackedTag[] {</span> | 
|  | <span class="source-line-no">6866</span><span id="line-6866">        // TTL tags specify ts in milliseconds</span> | 
|  | <span class="source-line-no">6867</span><span id="line-6867">        new ArrayBackedTag(TagType.TTL_TAG_TYPE, Bytes.toBytes(5000L)) })));</span> | 
|  | <span class="source-line-no">6868</span><span id="line-6868">    // Add a cell that will expire after 10 seconds via family setting</span> | 
|  | <span class="source-line-no">6869</span><span id="line-6869">    region.put(new Put(row).addColumn(fam1, q2, now, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">6870</span><span id="line-6870">    // Add a cell that will expire in 15 seconds via cell TTL</span> | 
|  | <span class="source-line-no">6871</span><span id="line-6871">    region.put(new Put(row).add(new KeyValue(row, fam1, q3, now + 10000 - 1,</span> | 
|  | <span class="source-line-no">6872</span><span id="line-6872">      HConstants.EMPTY_BYTE_ARRAY, new ArrayBackedTag[] {</span> | 
|  | <span class="source-line-no">6873</span><span id="line-6873">        // TTL tags specify ts in milliseconds</span> | 
|  | <span class="source-line-no">6874</span><span id="line-6874">        new ArrayBackedTag(TagType.TTL_TAG_TYPE, Bytes.toBytes(5000L)) })));</span> | 
|  | <span class="source-line-no">6875</span><span id="line-6875">    // Add a cell that will expire in 20 seconds via family setting</span> | 
|  | <span class="source-line-no">6876</span><span id="line-6876">    region.put(new Put(row).addColumn(fam1, q4, now + 10000 - 1, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">6877</span><span id="line-6877"></span> | 
|  | <span class="source-line-no">6878</span><span id="line-6878">    // Flush so we are sure store scanning gets this right</span> | 
|  | <span class="source-line-no">6879</span><span id="line-6879">    region.flush(true);</span> | 
|  | <span class="source-line-no">6880</span><span id="line-6880"></span> | 
|  | <span class="source-line-no">6881</span><span id="line-6881">    // A query at time T+0 should return all cells</span> | 
|  | <span class="source-line-no">6882</span><span id="line-6882">    Result r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">6883</span><span id="line-6883">    assertNotNull(r.getValue(fam1, q1));</span> | 
|  | <span class="source-line-no">6884</span><span id="line-6884">    assertNotNull(r.getValue(fam1, q2));</span> | 
|  | <span class="source-line-no">6885</span><span id="line-6885">    assertNotNull(r.getValue(fam1, q3));</span> | 
|  | <span class="source-line-no">6886</span><span id="line-6886">    assertNotNull(r.getValue(fam1, q4));</span> | 
|  | <span class="source-line-no">6887</span><span id="line-6887"></span> | 
|  | <span class="source-line-no">6888</span><span id="line-6888">    // Increment time to T+5 seconds</span> | 
|  | <span class="source-line-no">6889</span><span id="line-6889">    edge.incrementTime(5000);</span> | 
|  | <span class="source-line-no">6890</span><span id="line-6890"></span> | 
|  | <span class="source-line-no">6891</span><span id="line-6891">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">6892</span><span id="line-6892">    assertNull(r.getValue(fam1, q1));</span> | 
|  | <span class="source-line-no">6893</span><span id="line-6893">    assertNotNull(r.getValue(fam1, q2));</span> | 
|  | <span class="source-line-no">6894</span><span id="line-6894">    assertNotNull(r.getValue(fam1, q3));</span> | 
|  | <span class="source-line-no">6895</span><span id="line-6895">    assertNotNull(r.getValue(fam1, q4));</span> | 
|  | <span class="source-line-no">6896</span><span id="line-6896"></span> | 
|  | <span class="source-line-no">6897</span><span id="line-6897">    // Increment time to T+10 seconds</span> | 
|  | <span class="source-line-no">6898</span><span id="line-6898">    edge.incrementTime(5000);</span> | 
|  | <span class="source-line-no">6899</span><span id="line-6899"></span> | 
|  | <span class="source-line-no">6900</span><span id="line-6900">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">6901</span><span id="line-6901">    assertNull(r.getValue(fam1, q1));</span> | 
|  | <span class="source-line-no">6902</span><span id="line-6902">    assertNull(r.getValue(fam1, q2));</span> | 
|  | <span class="source-line-no">6903</span><span id="line-6903">    assertNotNull(r.getValue(fam1, q3));</span> | 
|  | <span class="source-line-no">6904</span><span id="line-6904">    assertNotNull(r.getValue(fam1, q4));</span> | 
|  | <span class="source-line-no">6905</span><span id="line-6905"></span> | 
|  | <span class="source-line-no">6906</span><span id="line-6906">    // Increment time to T+15 seconds</span> | 
|  | <span class="source-line-no">6907</span><span id="line-6907">    edge.incrementTime(5000);</span> | 
|  | <span class="source-line-no">6908</span><span id="line-6908"></span> | 
|  | <span class="source-line-no">6909</span><span id="line-6909">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">6910</span><span id="line-6910">    assertNull(r.getValue(fam1, q1));</span> | 
|  | <span class="source-line-no">6911</span><span id="line-6911">    assertNull(r.getValue(fam1, q2));</span> | 
|  | <span class="source-line-no">6912</span><span id="line-6912">    assertNull(r.getValue(fam1, q3));</span> | 
|  | <span class="source-line-no">6913</span><span id="line-6913">    assertNotNull(r.getValue(fam1, q4));</span> | 
|  | <span class="source-line-no">6914</span><span id="line-6914"></span> | 
|  | <span class="source-line-no">6915</span><span id="line-6915">    // Increment time to T+20 seconds</span> | 
|  | <span class="source-line-no">6916</span><span id="line-6916">    edge.incrementTime(10000);</span> | 
|  | <span class="source-line-no">6917</span><span id="line-6917"></span> | 
|  | <span class="source-line-no">6918</span><span id="line-6918">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">6919</span><span id="line-6919">    assertNull(r.getValue(fam1, q1));</span> | 
|  | <span class="source-line-no">6920</span><span id="line-6920">    assertNull(r.getValue(fam1, q2));</span> | 
|  | <span class="source-line-no">6921</span><span id="line-6921">    assertNull(r.getValue(fam1, q3));</span> | 
|  | <span class="source-line-no">6922</span><span id="line-6922">    assertNull(r.getValue(fam1, q4));</span> | 
|  | <span class="source-line-no">6923</span><span id="line-6923"></span> | 
|  | <span class="source-line-no">6924</span><span id="line-6924">    // Fun with disappearing increments</span> | 
|  | <span class="source-line-no">6925</span><span id="line-6925"></span> | 
|  | <span class="source-line-no">6926</span><span id="line-6926">    // Start at 1</span> | 
|  | <span class="source-line-no">6927</span><span id="line-6927">    region.put(new Put(row).addColumn(fam1, q1, Bytes.toBytes(1L)));</span> | 
|  | <span class="source-line-no">6928</span><span id="line-6928">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">6929</span><span id="line-6929">    byte[] val = r.getValue(fam1, q1);</span> | 
|  | <span class="source-line-no">6930</span><span id="line-6930">    assertNotNull(val);</span> | 
|  | <span class="source-line-no">6931</span><span id="line-6931">    assertEquals(1L, Bytes.toLong(val));</span> | 
|  | <span class="source-line-no">6932</span><span id="line-6932"></span> | 
|  | <span class="source-line-no">6933</span><span id="line-6933">    // Increment with a TTL of 5 seconds</span> | 
|  | <span class="source-line-no">6934</span><span id="line-6934">    Increment incr = new Increment(row).addColumn(fam1, q1, 1L);</span> | 
|  | <span class="source-line-no">6935</span><span id="line-6935">    incr.setTTL(5000);</span> | 
|  | <span class="source-line-no">6936</span><span id="line-6936">    region.increment(incr); // 2</span> | 
|  | <span class="source-line-no">6937</span><span id="line-6937"></span> | 
|  | <span class="source-line-no">6938</span><span id="line-6938">    // New value should be 2</span> | 
|  | <span class="source-line-no">6939</span><span id="line-6939">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">6940</span><span id="line-6940">    val = r.getValue(fam1, q1);</span> | 
|  | <span class="source-line-no">6941</span><span id="line-6941">    assertNotNull(val);</span> | 
|  | <span class="source-line-no">6942</span><span id="line-6942">    assertEquals(2L, Bytes.toLong(val));</span> | 
|  | <span class="source-line-no">6943</span><span id="line-6943"></span> | 
|  | <span class="source-line-no">6944</span><span id="line-6944">    // Increment time to T+25 seconds</span> | 
|  | <span class="source-line-no">6945</span><span id="line-6945">    edge.incrementTime(5000);</span> | 
|  | <span class="source-line-no">6946</span><span id="line-6946"></span> | 
|  | <span class="source-line-no">6947</span><span id="line-6947">    // Value should be back to 1</span> | 
|  | <span class="source-line-no">6948</span><span id="line-6948">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">6949</span><span id="line-6949">    val = r.getValue(fam1, q1);</span> | 
|  | <span class="source-line-no">6950</span><span id="line-6950">    assertNotNull(val);</span> | 
|  | <span class="source-line-no">6951</span><span id="line-6951">    assertEquals(1L, Bytes.toLong(val));</span> | 
|  | <span class="source-line-no">6952</span><span id="line-6952"></span> | 
|  | <span class="source-line-no">6953</span><span id="line-6953">    // Increment time to T+30 seconds</span> | 
|  | <span class="source-line-no">6954</span><span id="line-6954">    edge.incrementTime(5000);</span> | 
|  | <span class="source-line-no">6955</span><span id="line-6955"></span> | 
|  | <span class="source-line-no">6956</span><span id="line-6956">    // Original value written at T+20 should be gone now via family TTL</span> | 
|  | <span class="source-line-no">6957</span><span id="line-6957">    r = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">6958</span><span id="line-6958">    assertNull(r.getValue(fam1, q1));</span> | 
|  | <span class="source-line-no">6959</span><span id="line-6959">  }</span> | 
|  | <span class="source-line-no">6960</span><span id="line-6960"></span> | 
|  | <span class="source-line-no">6961</span><span id="line-6961">  @Test</span> | 
|  | <span class="source-line-no">6962</span><span id="line-6962">  public void testTTLsUsingSmallHeartBeatCells() throws IOException {</span> | 
|  | <span class="source-line-no">6963</span><span id="line-6963">    IncrementingEnvironmentEdge edge = new IncrementingEnvironmentEdge();</span> | 
|  | <span class="source-line-no">6964</span><span id="line-6964">    EnvironmentEdgeManager.injectEdge(edge);</span> | 
|  | <span class="source-line-no">6965</span><span id="line-6965"></span> | 
|  | <span class="source-line-no">6966</span><span id="line-6966">    final byte[] row = Bytes.toBytes("testRow");</span> | 
|  | <span class="source-line-no">6967</span><span id="line-6967">    final byte[] q1 = Bytes.toBytes("q1");</span> | 
|  | <span class="source-line-no">6968</span><span id="line-6968">    final byte[] q2 = Bytes.toBytes("q2");</span> | 
|  | <span class="source-line-no">6969</span><span id="line-6969">    final byte[] q3 = Bytes.toBytes("q3");</span> | 
|  | <span class="source-line-no">6970</span><span id="line-6970">    final byte[] q4 = Bytes.toBytes("q4");</span> | 
|  | <span class="source-line-no">6971</span><span id="line-6971">    final byte[] q5 = Bytes.toBytes("q5");</span> | 
|  | <span class="source-line-no">6972</span><span id="line-6972">    final byte[] q6 = Bytes.toBytes("q6");</span> | 
|  | <span class="source-line-no">6973</span><span id="line-6973">    final byte[] q7 = Bytes.toBytes("q7");</span> | 
|  | <span class="source-line-no">6974</span><span id="line-6974">    final byte[] q8 = Bytes.toBytes("q8");</span> | 
|  | <span class="source-line-no">6975</span><span id="line-6975"></span> | 
|  | <span class="source-line-no">6976</span><span id="line-6976">    // 10 seconds</span> | 
|  | <span class="source-line-no">6977</span><span id="line-6977">    int ttlSecs = 10;</span> | 
|  | <span class="source-line-no">6978</span><span id="line-6978">    TableDescriptor tableDescriptor =</span> | 
|  | <span class="source-line-no">6979</span><span id="line-6979">      TableDescriptorBuilder.newBuilder(TableName.valueOf(name.getMethodName())).setColumnFamily(</span> | 
|  | <span class="source-line-no">6980</span><span id="line-6980">        ColumnFamilyDescriptorBuilder.newBuilder(fam1).setTimeToLive(ttlSecs).build()).build();</span> | 
|  | <span class="source-line-no">6981</span><span id="line-6981"></span> | 
|  | <span class="source-line-no">6982</span><span id="line-6982">    Configuration conf = new Configuration(TEST_UTIL.getConfiguration());</span> | 
|  | <span class="source-line-no">6983</span><span id="line-6983">    conf.setInt(HFile.FORMAT_VERSION_KEY, HFile.MIN_FORMAT_VERSION_WITH_TAGS);</span> | 
|  | <span class="source-line-no">6984</span><span id="line-6984">    // using small heart beat cells</span> | 
|  | <span class="source-line-no">6985</span><span id="line-6985">    conf.setLong(StoreScanner.HBASE_CELLS_SCANNED_PER_HEARTBEAT_CHECK, 2);</span> | 
|  | <span class="source-line-no">6986</span><span id="line-6986"></span> | 
|  | <span class="source-line-no">6987</span><span id="line-6987">    region = HBaseTestingUtil.createRegionAndWAL(</span> | 
|  | <span class="source-line-no">6988</span><span id="line-6988">      RegionInfoBuilder.newBuilder(tableDescriptor.getTableName()).build(),</span> | 
|  | <span class="source-line-no">6989</span><span id="line-6989">      TEST_UTIL.getDataTestDir(), conf, tableDescriptor);</span> | 
|  | <span class="source-line-no">6990</span><span id="line-6990">    assertNotNull(region);</span> | 
|  | <span class="source-line-no">6991</span><span id="line-6991">    long now = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">6992</span><span id="line-6992">    // Add a cell that will expire in 5 seconds via cell TTL</span> | 
|  | <span class="source-line-no">6993</span><span id="line-6993">    region.put(new Put(row).addColumn(fam1, q1, now, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">6994</span><span id="line-6994">    region.put(new Put(row).addColumn(fam1, q2, now, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">6995</span><span id="line-6995">    region.put(new Put(row).addColumn(fam1, q3, now, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">6996</span><span id="line-6996">    // Add a cell that will expire after 10 seconds via family setting</span> | 
|  | <span class="source-line-no">6997</span><span id="line-6997">    region</span> | 
|  | <span class="source-line-no">6998</span><span id="line-6998">      .put(new Put(row).addColumn(fam1, q4, now + ttlSecs * 1000 + 1, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">6999</span><span id="line-6999">    region</span> | 
|  | <span class="source-line-no">7000</span><span id="line-7000">      .put(new Put(row).addColumn(fam1, q5, now + ttlSecs * 1000 + 1, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">7001</span><span id="line-7001"></span> | 
|  | <span class="source-line-no">7002</span><span id="line-7002">    region.put(new Put(row).addColumn(fam1, q6, now, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">7003</span><span id="line-7003">    region.put(new Put(row).addColumn(fam1, q7, now, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">7004</span><span id="line-7004">    region</span> | 
|  | <span class="source-line-no">7005</span><span id="line-7005">      .put(new Put(row).addColumn(fam1, q8, now + ttlSecs * 1000 + 1, HConstants.EMPTY_BYTE_ARRAY));</span> | 
|  | <span class="source-line-no">7006</span><span id="line-7006"></span> | 
|  | <span class="source-line-no">7007</span><span id="line-7007">    // Flush so we are sure store scanning gets this right</span> | 
|  | <span class="source-line-no">7008</span><span id="line-7008">    region.flush(true);</span> | 
|  | <span class="source-line-no">7009</span><span id="line-7009"></span> | 
|  | <span class="source-line-no">7010</span><span id="line-7010">    // A query at time T+0 should return all cells</span> | 
|  | <span class="source-line-no">7011</span><span id="line-7011">    checkScan(8);</span> | 
|  | <span class="source-line-no">7012</span><span id="line-7012">    region.delete(new Delete(row).addColumn(fam1, q8));</span> | 
|  | <span class="source-line-no">7013</span><span id="line-7013"></span> | 
|  | <span class="source-line-no">7014</span><span id="line-7014">    // Increment time to T+ttlSecs seconds</span> | 
|  | <span class="source-line-no">7015</span><span id="line-7015">    edge.incrementTime(ttlSecs * 1000);</span> | 
|  | <span class="source-line-no">7016</span><span id="line-7016">    checkScan(2);</span> | 
|  | <span class="source-line-no">7017</span><span id="line-7017">  }</span> | 
|  | <span class="source-line-no">7018</span><span id="line-7018"></span> | 
|  | <span class="source-line-no">7019</span><span id="line-7019">  private void checkScan(int expectCellSize) throws IOException {</span> | 
|  | <span class="source-line-no">7020</span><span id="line-7020">    Scan s = new Scan().withStartRow(row);</span> | 
|  | <span class="source-line-no">7021</span><span id="line-7021">    ScannerContext.Builder contextBuilder = ScannerContext.newBuilder(true);</span> | 
|  | <span class="source-line-no">7022</span><span id="line-7022">    ScannerContext scannerContext = contextBuilder.build();</span> | 
|  | <span class="source-line-no">7023</span><span id="line-7023">    try (RegionScanner scanner = region.getScanner(s)) {</span> | 
|  | <span class="source-line-no">7024</span><span id="line-7024">      List<Cell> kvs = new ArrayList<>();</span> | 
|  | <span class="source-line-no">7025</span><span id="line-7025">      scanner.next(kvs, scannerContext);</span> | 
|  | <span class="source-line-no">7026</span><span id="line-7026">      assertEquals(expectCellSize, kvs.size());</span> | 
|  | <span class="source-line-no">7027</span><span id="line-7027">    }</span> | 
|  | <span class="source-line-no">7028</span><span id="line-7028">  }</span> | 
|  | <span class="source-line-no">7029</span><span id="line-7029"></span> | 
|  | <span class="source-line-no">7030</span><span id="line-7030">  @Test</span> | 
|  | <span class="source-line-no">7031</span><span id="line-7031">  public void testIncrementTimestampsAreMonotonic() throws IOException {</span> | 
|  | <span class="source-line-no">7032</span><span id="line-7032">    region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">7033</span><span id="line-7033">    ManualEnvironmentEdge edge = new ManualEnvironmentEdge();</span> | 
|  | <span class="source-line-no">7034</span><span id="line-7034">    EnvironmentEdgeManager.injectEdge(edge);</span> | 
|  | <span class="source-line-no">7035</span><span id="line-7035"></span> | 
|  | <span class="source-line-no">7036</span><span id="line-7036">    edge.setValue(10);</span> | 
|  | <span class="source-line-no">7037</span><span id="line-7037">    Increment inc = new Increment(row);</span> | 
|  | <span class="source-line-no">7038</span><span id="line-7038">    inc.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">7039</span><span id="line-7039">    inc.addColumn(fam1, qual1, 1L);</span> | 
|  | <span class="source-line-no">7040</span><span id="line-7040">    region.increment(inc);</span> | 
|  | <span class="source-line-no">7041</span><span id="line-7041"></span> | 
|  | <span class="source-line-no">7042</span><span id="line-7042">    Result result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7043</span><span id="line-7043">    Cell c = result.getColumnLatestCell(fam1, qual1);</span> | 
|  | <span class="source-line-no">7044</span><span id="line-7044">    assertNotNull(c);</span> | 
|  | <span class="source-line-no">7045</span><span id="line-7045">    assertEquals(10L, c.getTimestamp());</span> | 
|  | <span class="source-line-no">7046</span><span id="line-7046"></span> | 
|  | <span class="source-line-no">7047</span><span id="line-7047">    edge.setValue(1); // clock goes back</span> | 
|  | <span class="source-line-no">7048</span><span id="line-7048">    region.increment(inc);</span> | 
|  | <span class="source-line-no">7049</span><span id="line-7049">    result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7050</span><span id="line-7050">    c = result.getColumnLatestCell(fam1, qual1);</span> | 
|  | <span class="source-line-no">7051</span><span id="line-7051">    assertEquals(11L, c.getTimestamp());</span> | 
|  | <span class="source-line-no">7052</span><span id="line-7052">    assertEquals(2L, Bytes.toLong(c.getValueArray(), c.getValueOffset(), c.getValueLength()));</span> | 
|  | <span class="source-line-no">7053</span><span id="line-7053">  }</span> | 
|  | <span class="source-line-no">7054</span><span id="line-7054"></span> | 
|  | <span class="source-line-no">7055</span><span id="line-7055">  @Test</span> | 
|  | <span class="source-line-no">7056</span><span id="line-7056">  public void testAppendTimestampsAreMonotonic() throws IOException {</span> | 
|  | <span class="source-line-no">7057</span><span id="line-7057">    region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">7058</span><span id="line-7058">    ManualEnvironmentEdge edge = new ManualEnvironmentEdge();</span> | 
|  | <span class="source-line-no">7059</span><span id="line-7059">    EnvironmentEdgeManager.injectEdge(edge);</span> | 
|  | <span class="source-line-no">7060</span><span id="line-7060"></span> | 
|  | <span class="source-line-no">7061</span><span id="line-7061">    edge.setValue(10);</span> | 
|  | <span class="source-line-no">7062</span><span id="line-7062">    Append a = new Append(row);</span> | 
|  | <span class="source-line-no">7063</span><span id="line-7063">    a.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">7064</span><span id="line-7064">    a.addColumn(fam1, qual1, qual1);</span> | 
|  | <span class="source-line-no">7065</span><span id="line-7065">    region.append(a);</span> | 
|  | <span class="source-line-no">7066</span><span id="line-7066"></span> | 
|  | <span class="source-line-no">7067</span><span id="line-7067">    Result result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7068</span><span id="line-7068">    Cell c = result.getColumnLatestCell(fam1, qual1);</span> | 
|  | <span class="source-line-no">7069</span><span id="line-7069">    assertNotNull(c);</span> | 
|  | <span class="source-line-no">7070</span><span id="line-7070">    assertEquals(10L, c.getTimestamp());</span> | 
|  | <span class="source-line-no">7071</span><span id="line-7071"></span> | 
|  | <span class="source-line-no">7072</span><span id="line-7072">    edge.setValue(1); // clock goes back</span> | 
|  | <span class="source-line-no">7073</span><span id="line-7073">    region.append(a);</span> | 
|  | <span class="source-line-no">7074</span><span id="line-7074">    result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7075</span><span id="line-7075">    c = result.getColumnLatestCell(fam1, qual1);</span> | 
|  | <span class="source-line-no">7076</span><span id="line-7076">    assertEquals(11L, c.getTimestamp());</span> | 
|  | <span class="source-line-no">7077</span><span id="line-7077"></span> | 
|  | <span class="source-line-no">7078</span><span id="line-7078">    byte[] expected = new byte[qual1.length * 2];</span> | 
|  | <span class="source-line-no">7079</span><span id="line-7079">    System.arraycopy(qual1, 0, expected, 0, qual1.length);</span> | 
|  | <span class="source-line-no">7080</span><span id="line-7080">    System.arraycopy(qual1, 0, expected, qual1.length, qual1.length);</span> | 
|  | <span class="source-line-no">7081</span><span id="line-7081"></span> | 
|  | <span class="source-line-no">7082</span><span id="line-7082">    assertTrue(Bytes.equals(c.getValueArray(), c.getValueOffset(), c.getValueLength(), expected, 0,</span> | 
|  | <span class="source-line-no">7083</span><span id="line-7083">      expected.length));</span> | 
|  | <span class="source-line-no">7084</span><span id="line-7084">  }</span> | 
|  | <span class="source-line-no">7085</span><span id="line-7085"></span> | 
|  | <span class="source-line-no">7086</span><span id="line-7086">  @Test</span> | 
|  | <span class="source-line-no">7087</span><span id="line-7087">  public void testCheckAndMutateTimestampsAreMonotonic() throws IOException {</span> | 
|  | <span class="source-line-no">7088</span><span id="line-7088">    region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">7089</span><span id="line-7089">    ManualEnvironmentEdge edge = new ManualEnvironmentEdge();</span> | 
|  | <span class="source-line-no">7090</span><span id="line-7090">    EnvironmentEdgeManager.injectEdge(edge);</span> | 
|  | <span class="source-line-no">7091</span><span id="line-7091"></span> | 
|  | <span class="source-line-no">7092</span><span id="line-7092">    edge.setValue(10);</span> | 
|  | <span class="source-line-no">7093</span><span id="line-7093">    Put p = new Put(row);</span> | 
|  | <span class="source-line-no">7094</span><span id="line-7094">    p.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">7095</span><span id="line-7095">    p.addColumn(fam1, qual1, qual1);</span> | 
|  | <span class="source-line-no">7096</span><span id="line-7096">    region.put(p);</span> | 
|  | <span class="source-line-no">7097</span><span id="line-7097"></span> | 
|  | <span class="source-line-no">7098</span><span id="line-7098">    Result result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7099</span><span id="line-7099">    Cell c = result.getColumnLatestCell(fam1, qual1);</span> | 
|  | <span class="source-line-no">7100</span><span id="line-7100">    assertNotNull(c);</span> | 
|  | <span class="source-line-no">7101</span><span id="line-7101">    assertEquals(10L, c.getTimestamp());</span> | 
|  | <span class="source-line-no">7102</span><span id="line-7102"></span> | 
|  | <span class="source-line-no">7103</span><span id="line-7103">    edge.setValue(1); // clock goes back</span> | 
|  | <span class="source-line-no">7104</span><span id="line-7104">    p = new Put(row);</span> | 
|  | <span class="source-line-no">7105</span><span id="line-7105">    p.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">7106</span><span id="line-7106">    p.addColumn(fam1, qual1, qual2);</span> | 
|  | <span class="source-line-no">7107</span><span id="line-7107">    region.checkAndMutate(row, fam1, qual1, CompareOperator.EQUAL, new BinaryComparator(qual1), p);</span> | 
|  | <span class="source-line-no">7108</span><span id="line-7108">    result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7109</span><span id="line-7109">    c = result.getColumnLatestCell(fam1, qual1);</span> | 
|  | <span class="source-line-no">7110</span><span id="line-7110">    assertEquals(10L, c.getTimestamp());</span> | 
|  | <span class="source-line-no">7111</span><span id="line-7111"></span> | 
|  | <span class="source-line-no">7112</span><span id="line-7112">    assertTrue(Bytes.equals(c.getValueArray(), c.getValueOffset(), c.getValueLength(), qual2, 0,</span> | 
|  | <span class="source-line-no">7113</span><span id="line-7113">      qual2.length));</span> | 
|  | <span class="source-line-no">7114</span><span id="line-7114">  }</span> | 
|  | <span class="source-line-no">7115</span><span id="line-7115"></span> | 
|  | <span class="source-line-no">7116</span><span id="line-7116">  @Test</span> | 
|  | <span class="source-line-no">7117</span><span id="line-7117">  public void testBatchMutateWithWrongRegionException() throws Exception {</span> | 
|  | <span class="source-line-no">7118</span><span id="line-7118">    final byte[] a = Bytes.toBytes("a");</span> | 
|  | <span class="source-line-no">7119</span><span id="line-7119">    final byte[] b = Bytes.toBytes("b");</span> | 
|  | <span class="source-line-no">7120</span><span id="line-7120">    final byte[] c = Bytes.toBytes("c"); // exclusive</span> | 
|  | <span class="source-line-no">7121</span><span id="line-7121"></span> | 
|  | <span class="source-line-no">7122</span><span id="line-7122">    int prevLockTimeout = CONF.getInt("hbase.rowlock.wait.duration", 30000);</span> | 
|  | <span class="source-line-no">7123</span><span id="line-7123">    CONF.setInt("hbase.rowlock.wait.duration", 1000);</span> | 
|  | <span class="source-line-no">7124</span><span id="line-7124">    region = initHRegion(tableName, a, c, method, CONF, false, fam1);</span> | 
|  | <span class="source-line-no">7125</span><span id="line-7125"></span> | 
|  | <span class="source-line-no">7126</span><span id="line-7126">    Mutation[] mutations = new Mutation[] {</span> | 
|  | <span class="source-line-no">7127</span><span id="line-7127">      new Put(a).add(CellBuilderFactory.create(CellBuilderType.SHALLOW_COPY).setRow(a)</span> | 
|  | <span class="source-line-no">7128</span><span id="line-7128">        .setFamily(fam1).setTimestamp(HConstants.LATEST_TIMESTAMP).setType(Cell.Type.Put).build()),</span> | 
|  | <span class="source-line-no">7129</span><span id="line-7129">      // this is outside the region boundary</span> | 
|  | <span class="source-line-no">7130</span><span id="line-7130">      new Put(c).add(CellBuilderFactory.create(CellBuilderType.SHALLOW_COPY).setRow(c)</span> | 
|  | <span class="source-line-no">7131</span><span id="line-7131">        .setFamily(fam1).setTimestamp(HConstants.LATEST_TIMESTAMP).setType(Type.Put).build()),</span> | 
|  | <span class="source-line-no">7132</span><span id="line-7132">      new Put(b)</span> | 
|  | <span class="source-line-no">7133</span><span id="line-7133">        .add(CellBuilderFactory.create(CellBuilderType.SHALLOW_COPY).setRow(b).setFamily(fam1)</span> | 
|  | <span class="source-line-no">7134</span><span id="line-7134">          .setTimestamp(HConstants.LATEST_TIMESTAMP).setType(Cell.Type.Put).build()) };</span> | 
|  | <span class="source-line-no">7135</span><span id="line-7135"></span> | 
|  | <span class="source-line-no">7136</span><span id="line-7136">    OperationStatus[] status = region.batchMutate(mutations);</span> | 
|  | <span class="source-line-no">7137</span><span id="line-7137">    assertEquals(OperationStatusCode.SUCCESS, status[0].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">7138</span><span id="line-7138">    assertEquals(OperationStatusCode.SANITY_CHECK_FAILURE, status[1].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">7139</span><span id="line-7139">    assertEquals(OperationStatusCode.SUCCESS, status[2].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">7140</span><span id="line-7140"></span> | 
|  | <span class="source-line-no">7141</span><span id="line-7141">    // test with a row lock held for a long time</span> | 
|  | <span class="source-line-no">7142</span><span id="line-7142">    final CountDownLatch obtainedRowLock = new CountDownLatch(1);</span> | 
|  | <span class="source-line-no">7143</span><span id="line-7143">    ExecutorService exec = Executors.newFixedThreadPool(2);</span> | 
|  | <span class="source-line-no">7144</span><span id="line-7144">    Future<Void> f1 = exec.submit(new Callable<Void>() {</span> | 
|  | <span class="source-line-no">7145</span><span id="line-7145">      @Override</span> | 
|  | <span class="source-line-no">7146</span><span id="line-7146">      public Void call() throws Exception {</span> | 
|  | <span class="source-line-no">7147</span><span id="line-7147">        LOG.info("Acquiring row lock");</span> | 
|  | <span class="source-line-no">7148</span><span id="line-7148">        RowLock rl = region.getRowLock(b);</span> | 
|  | <span class="source-line-no">7149</span><span id="line-7149">        obtainedRowLock.countDown();</span> | 
|  | <span class="source-line-no">7150</span><span id="line-7150">        LOG.info("Waiting for 5 seconds before releasing lock");</span> | 
|  | <span class="source-line-no">7151</span><span id="line-7151">        Threads.sleep(5000);</span> | 
|  | <span class="source-line-no">7152</span><span id="line-7152">        LOG.info("Releasing row lock");</span> | 
|  | <span class="source-line-no">7153</span><span id="line-7153">        rl.release();</span> | 
|  | <span class="source-line-no">7154</span><span id="line-7154">        return null;</span> | 
|  | <span class="source-line-no">7155</span><span id="line-7155">      }</span> | 
|  | <span class="source-line-no">7156</span><span id="line-7156">    });</span> | 
|  | <span class="source-line-no">7157</span><span id="line-7157">    obtainedRowLock.await(30, TimeUnit.SECONDS);</span> | 
|  | <span class="source-line-no">7158</span><span id="line-7158"></span> | 
|  | <span class="source-line-no">7159</span><span id="line-7159">    Future<Void> f2 = exec.submit(new Callable<Void>() {</span> | 
|  | <span class="source-line-no">7160</span><span id="line-7160">      @Override</span> | 
|  | <span class="source-line-no">7161</span><span id="line-7161">      public Void call() throws Exception {</span> | 
|  | <span class="source-line-no">7162</span><span id="line-7162">        Mutation[] mutations = new Mutation[] {</span> | 
|  | <span class="source-line-no">7163</span><span id="line-7163">          new Put(a)</span> | 
|  | <span class="source-line-no">7164</span><span id="line-7164">            .add(CellBuilderFactory.create(CellBuilderType.SHALLOW_COPY).setRow(a).setFamily(fam1)</span> | 
|  | <span class="source-line-no">7165</span><span id="line-7165">              .setTimestamp(HConstants.LATEST_TIMESTAMP).setType(Cell.Type.Put).build()),</span> | 
|  | <span class="source-line-no">7166</span><span id="line-7166">          new Put(b)</span> | 
|  | <span class="source-line-no">7167</span><span id="line-7167">            .add(CellBuilderFactory.create(CellBuilderType.SHALLOW_COPY).setRow(b).setFamily(fam1)</span> | 
|  | <span class="source-line-no">7168</span><span id="line-7168">              .setTimestamp(HConstants.LATEST_TIMESTAMP).setType(Cell.Type.Put).build()), };</span> | 
|  | <span class="source-line-no">7169</span><span id="line-7169"></span> | 
|  | <span class="source-line-no">7170</span><span id="line-7170">        // this will wait for the row lock, and it will eventually succeed</span> | 
|  | <span class="source-line-no">7171</span><span id="line-7171">        OperationStatus[] status = region.batchMutate(mutations);</span> | 
|  | <span class="source-line-no">7172</span><span id="line-7172">        assertEquals(OperationStatusCode.SUCCESS, status[0].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">7173</span><span id="line-7173">        assertEquals(OperationStatusCode.SUCCESS, status[1].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">7174</span><span id="line-7174">        return null;</span> | 
|  | <span class="source-line-no">7175</span><span id="line-7175">      }</span> | 
|  | <span class="source-line-no">7176</span><span id="line-7176">    });</span> | 
|  | <span class="source-line-no">7177</span><span id="line-7177"></span> | 
|  | <span class="source-line-no">7178</span><span id="line-7178">    f1.get();</span> | 
|  | <span class="source-line-no">7179</span><span id="line-7179">    f2.get();</span> | 
|  | <span class="source-line-no">7180</span><span id="line-7180"></span> | 
|  | <span class="source-line-no">7181</span><span id="line-7181">    CONF.setInt("hbase.rowlock.wait.duration", prevLockTimeout);</span> | 
|  | <span class="source-line-no">7182</span><span id="line-7182">  }</span> | 
|  | <span class="source-line-no">7183</span><span id="line-7183"></span> | 
|  | <span class="source-line-no">7184</span><span id="line-7184">  @Test</span> | 
|  | <span class="source-line-no">7185</span><span id="line-7185">  public void testBatchMutateWithZeroRowLockWait() throws Exception {</span> | 
|  | <span class="source-line-no">7186</span><span id="line-7186">    final byte[] a = Bytes.toBytes("a");</span> | 
|  | <span class="source-line-no">7187</span><span id="line-7187">    final byte[] b = Bytes.toBytes("b");</span> | 
|  | <span class="source-line-no">7188</span><span id="line-7188">    final byte[] c = Bytes.toBytes("c"); // exclusive</span> | 
|  | <span class="source-line-no">7189</span><span id="line-7189"></span> | 
|  | <span class="source-line-no">7190</span><span id="line-7190">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">7191</span><span id="line-7191">    conf.setInt("hbase.rowlock.wait.duration", 0);</span> | 
|  | <span class="source-line-no">7192</span><span id="line-7192">    final RegionInfo hri =</span> | 
|  | <span class="source-line-no">7193</span><span id="line-7193">      RegionInfoBuilder.newBuilder(tableName).setStartKey(a).setEndKey(c).build();</span> | 
|  | <span class="source-line-no">7194</span><span id="line-7194">    final TableDescriptor htd = TableDescriptorBuilder.newBuilder(tableName)</span> | 
|  | <span class="source-line-no">7195</span><span id="line-7195">      .setColumnFamily(ColumnFamilyDescriptorBuilder.of(fam1)).build();</span> | 
|  | <span class="source-line-no">7196</span><span id="line-7196">    region = HRegion.createHRegion(hri, TEST_UTIL.getDataTestDir(), conf, htd,</span> | 
|  | <span class="source-line-no">7197</span><span id="line-7197">      HBaseTestingUtil.createWal(conf, TEST_UTIL.getDataTestDirOnTestFS(method + ".log"), hri));</span> | 
|  | <span class="source-line-no">7198</span><span id="line-7198"></span> | 
|  | <span class="source-line-no">7199</span><span id="line-7199">    Mutation[] mutations = new Mutation[] {</span> | 
|  | <span class="source-line-no">7200</span><span id="line-7200">      new Put(a).add(CellBuilderFactory.create(CellBuilderType.SHALLOW_COPY).setRow(a)</span> | 
|  | <span class="source-line-no">7201</span><span id="line-7201">        .setFamily(fam1).setTimestamp(HConstants.LATEST_TIMESTAMP).setType(Cell.Type.Put).build()),</span> | 
|  | <span class="source-line-no">7202</span><span id="line-7202">      new Put(b)</span> | 
|  | <span class="source-line-no">7203</span><span id="line-7203">        .add(CellBuilderFactory.create(CellBuilderType.SHALLOW_COPY).setRow(b).setFamily(fam1)</span> | 
|  | <span class="source-line-no">7204</span><span id="line-7204">          .setTimestamp(HConstants.LATEST_TIMESTAMP).setType(Cell.Type.Put).build()) };</span> | 
|  | <span class="source-line-no">7205</span><span id="line-7205"></span> | 
|  | <span class="source-line-no">7206</span><span id="line-7206">    OperationStatus[] status = region.batchMutate(mutations);</span> | 
|  | <span class="source-line-no">7207</span><span id="line-7207">    assertEquals(OperationStatusCode.SUCCESS, status[0].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">7208</span><span id="line-7208">    assertEquals(OperationStatusCode.SUCCESS, status[1].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">7209</span><span id="line-7209"></span> | 
|  | <span class="source-line-no">7210</span><span id="line-7210">    // test with a row lock held for a long time</span> | 
|  | <span class="source-line-no">7211</span><span id="line-7211">    final CountDownLatch obtainedRowLock = new CountDownLatch(1);</span> | 
|  | <span class="source-line-no">7212</span><span id="line-7212">    ExecutorService exec = Executors.newFixedThreadPool(2);</span> | 
|  | <span class="source-line-no">7213</span><span id="line-7213">    Future<Void> f1 = exec.submit(new Callable<Void>() {</span> | 
|  | <span class="source-line-no">7214</span><span id="line-7214">      @Override</span> | 
|  | <span class="source-line-no">7215</span><span id="line-7215">      public Void call() throws Exception {</span> | 
|  | <span class="source-line-no">7216</span><span id="line-7216">        LOG.info("Acquiring row lock");</span> | 
|  | <span class="source-line-no">7217</span><span id="line-7217">        RowLock rl = region.getRowLock(b);</span> | 
|  | <span class="source-line-no">7218</span><span id="line-7218">        obtainedRowLock.countDown();</span> | 
|  | <span class="source-line-no">7219</span><span id="line-7219">        LOG.info("Waiting for 5 seconds before releasing lock");</span> | 
|  | <span class="source-line-no">7220</span><span id="line-7220">        Threads.sleep(5000);</span> | 
|  | <span class="source-line-no">7221</span><span id="line-7221">        LOG.info("Releasing row lock");</span> | 
|  | <span class="source-line-no">7222</span><span id="line-7222">        rl.release();</span> | 
|  | <span class="source-line-no">7223</span><span id="line-7223">        return null;</span> | 
|  | <span class="source-line-no">7224</span><span id="line-7224">      }</span> | 
|  | <span class="source-line-no">7225</span><span id="line-7225">    });</span> | 
|  | <span class="source-line-no">7226</span><span id="line-7226">    obtainedRowLock.await(30, TimeUnit.SECONDS);</span> | 
|  | <span class="source-line-no">7227</span><span id="line-7227"></span> | 
|  | <span class="source-line-no">7228</span><span id="line-7228">    Future<Void> f2 = exec.submit(new Callable<Void>() {</span> | 
|  | <span class="source-line-no">7229</span><span id="line-7229">      @Override</span> | 
|  | <span class="source-line-no">7230</span><span id="line-7230">      public Void call() throws Exception {</span> | 
|  | <span class="source-line-no">7231</span><span id="line-7231">        Mutation[] mutations = new Mutation[] {</span> | 
|  | <span class="source-line-no">7232</span><span id="line-7232">          new Put(a)</span> | 
|  | <span class="source-line-no">7233</span><span id="line-7233">            .add(CellBuilderFactory.create(CellBuilderType.SHALLOW_COPY).setRow(a).setFamily(fam1)</span> | 
|  | <span class="source-line-no">7234</span><span id="line-7234">              .setTimestamp(HConstants.LATEST_TIMESTAMP).setType(Cell.Type.Put).build()),</span> | 
|  | <span class="source-line-no">7235</span><span id="line-7235">          new Put(b)</span> | 
|  | <span class="source-line-no">7236</span><span id="line-7236">            .add(CellBuilderFactory.create(CellBuilderType.SHALLOW_COPY).setRow(b).setFamily(fam1)</span> | 
|  | <span class="source-line-no">7237</span><span id="line-7237">              .setTimestamp(HConstants.LATEST_TIMESTAMP).setType(Cell.Type.Put).build()), };</span> | 
|  | <span class="source-line-no">7238</span><span id="line-7238">        // when handling row b we are going to spin on the failure to get the row lock</span> | 
|  | <span class="source-line-no">7239</span><span id="line-7239">        // until the lock above is released, but we will still succeed so long as that</span> | 
|  | <span class="source-line-no">7240</span><span id="line-7240">        // takes less time then the test time out.</span> | 
|  | <span class="source-line-no">7241</span><span id="line-7241">        OperationStatus[] status = region.batchMutate(mutations);</span> | 
|  | <span class="source-line-no">7242</span><span id="line-7242">        assertEquals(OperationStatusCode.SUCCESS, status[0].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">7243</span><span id="line-7243">        assertEquals(OperationStatusCode.SUCCESS, status[1].getOperationStatusCode());</span> | 
|  | <span class="source-line-no">7244</span><span id="line-7244">        return null;</span> | 
|  | <span class="source-line-no">7245</span><span id="line-7245">      }</span> | 
|  | <span class="source-line-no">7246</span><span id="line-7246">    });</span> | 
|  | <span class="source-line-no">7247</span><span id="line-7247"></span> | 
|  | <span class="source-line-no">7248</span><span id="line-7248">    f1.get();</span> | 
|  | <span class="source-line-no">7249</span><span id="line-7249">    f2.get();</span> | 
|  | <span class="source-line-no">7250</span><span id="line-7250">  }</span> | 
|  | <span class="source-line-no">7251</span><span id="line-7251"></span> | 
|  | <span class="source-line-no">7252</span><span id="line-7252">  @Test</span> | 
|  | <span class="source-line-no">7253</span><span id="line-7253">  public void testCheckAndRowMutateTimestampsAreMonotonic() throws IOException {</span> | 
|  | <span class="source-line-no">7254</span><span id="line-7254">    region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">7255</span><span id="line-7255">    ManualEnvironmentEdge edge = new ManualEnvironmentEdge();</span> | 
|  | <span class="source-line-no">7256</span><span id="line-7256">    EnvironmentEdgeManager.injectEdge(edge);</span> | 
|  | <span class="source-line-no">7257</span><span id="line-7257"></span> | 
|  | <span class="source-line-no">7258</span><span id="line-7258">    edge.setValue(10);</span> | 
|  | <span class="source-line-no">7259</span><span id="line-7259">    Put p = new Put(row);</span> | 
|  | <span class="source-line-no">7260</span><span id="line-7260">    p.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">7261</span><span id="line-7261">    p.addColumn(fam1, qual1, qual1);</span> | 
|  | <span class="source-line-no">7262</span><span id="line-7262">    region.put(p);</span> | 
|  | <span class="source-line-no">7263</span><span id="line-7263"></span> | 
|  | <span class="source-line-no">7264</span><span id="line-7264">    Result result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7265</span><span id="line-7265">    Cell c = result.getColumnLatestCell(fam1, qual1);</span> | 
|  | <span class="source-line-no">7266</span><span id="line-7266">    assertNotNull(c);</span> | 
|  | <span class="source-line-no">7267</span><span id="line-7267">    assertEquals(10L, c.getTimestamp());</span> | 
|  | <span class="source-line-no">7268</span><span id="line-7268"></span> | 
|  | <span class="source-line-no">7269</span><span id="line-7269">    edge.setValue(1); // clock goes back</span> | 
|  | <span class="source-line-no">7270</span><span id="line-7270">    p = new Put(row);</span> | 
|  | <span class="source-line-no">7271</span><span id="line-7271">    p.setDurability(Durability.SKIP_WAL);</span> | 
|  | <span class="source-line-no">7272</span><span id="line-7272">    p.addColumn(fam1, qual1, qual2);</span> | 
|  | <span class="source-line-no">7273</span><span id="line-7273">    RowMutations rm = new RowMutations(row);</span> | 
|  | <span class="source-line-no">7274</span><span id="line-7274">    rm.add(p);</span> | 
|  | <span class="source-line-no">7275</span><span id="line-7275">    assertTrue(region.checkAndRowMutate(row, fam1, qual1, CompareOperator.EQUAL,</span> | 
|  | <span class="source-line-no">7276</span><span id="line-7276">      new BinaryComparator(qual1), rm));</span> | 
|  | <span class="source-line-no">7277</span><span id="line-7277">    result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7278</span><span id="line-7278">    c = result.getColumnLatestCell(fam1, qual1);</span> | 
|  | <span class="source-line-no">7279</span><span id="line-7279">    assertEquals(10L, c.getTimestamp());</span> | 
|  | <span class="source-line-no">7280</span><span id="line-7280">    LOG.info(</span> | 
|  | <span class="source-line-no">7281</span><span id="line-7281">      "c value " + Bytes.toStringBinary(c.getValueArray(), c.getValueOffset(), c.getValueLength()));</span> | 
|  | <span class="source-line-no">7282</span><span id="line-7282"></span> | 
|  | <span class="source-line-no">7283</span><span id="line-7283">    assertTrue(Bytes.equals(c.getValueArray(), c.getValueOffset(), c.getValueLength(), qual2, 0,</span> | 
|  | <span class="source-line-no">7284</span><span id="line-7284">      qual2.length));</span> | 
|  | <span class="source-line-no">7285</span><span id="line-7285">  }</span> | 
|  | <span class="source-line-no">7286</span><span id="line-7286"></span> | 
|  | <span class="source-line-no">7287</span><span id="line-7287">  private HRegion initHRegion(TableName tableName, String callingMethod, byte[]... families)</span> | 
|  | <span class="source-line-no">7288</span><span id="line-7288">    throws IOException {</span> | 
|  | <span class="source-line-no">7289</span><span id="line-7289">    return initHRegion(tableName, callingMethod, HBaseConfiguration.create(), families);</span> | 
|  | <span class="source-line-no">7290</span><span id="line-7290">  }</span> | 
|  | <span class="source-line-no">7291</span><span id="line-7291"></span> | 
|  | <span class="source-line-no">7292</span><span id="line-7292">  /**</span> | 
|  | <span class="source-line-no">7293</span><span id="line-7293">   * HBASE-16429 Make sure no stuck if roll writer when ring buffer is filled with appends</span> | 
|  | <span class="source-line-no">7294</span><span id="line-7294">   * @throws IOException if IO error occurred during test</span> | 
|  | <span class="source-line-no">7295</span><span id="line-7295">   */</span> | 
|  | <span class="source-line-no">7296</span><span id="line-7296">  @Test</span> | 
|  | <span class="source-line-no">7297</span><span id="line-7297">  public void testWritesWhileRollWriter() throws IOException {</span> | 
|  | <span class="source-line-no">7298</span><span id="line-7298">    int testCount = 10;</span> | 
|  | <span class="source-line-no">7299</span><span id="line-7299">    int numRows = 1024;</span> | 
|  | <span class="source-line-no">7300</span><span id="line-7300">    int numFamilies = 2;</span> | 
|  | <span class="source-line-no">7301</span><span id="line-7301">    int numQualifiers = 2;</span> | 
|  | <span class="source-line-no">7302</span><span id="line-7302">    final byte[][] families = new byte[numFamilies][];</span> | 
|  | <span class="source-line-no">7303</span><span id="line-7303">    for (int i = 0; i < numFamilies; i++) {</span> | 
|  | <span class="source-line-no">7304</span><span id="line-7304">      families[i] = Bytes.toBytes("family" + i);</span> | 
|  | <span class="source-line-no">7305</span><span id="line-7305">    }</span> | 
|  | <span class="source-line-no">7306</span><span id="line-7306">    final byte[][] qualifiers = new byte[numQualifiers][];</span> | 
|  | <span class="source-line-no">7307</span><span id="line-7307">    for (int i = 0; i < numQualifiers; i++) {</span> | 
|  | <span class="source-line-no">7308</span><span id="line-7308">      qualifiers[i] = Bytes.toBytes("qual" + i);</span> | 
|  | <span class="source-line-no">7309</span><span id="line-7309">    }</span> | 
|  | <span class="source-line-no">7310</span><span id="line-7310"></span> | 
|  | <span class="source-line-no">7311</span><span id="line-7311">    CONF.setInt("hbase.regionserver.wal.disruptor.event.count", 2);</span> | 
|  | <span class="source-line-no">7312</span><span id="line-7312">    this.region = initHRegion(tableName, method, CONF, families);</span> | 
|  | <span class="source-line-no">7313</span><span id="line-7313">    try {</span> | 
|  | <span class="source-line-no">7314</span><span id="line-7314">      List<Thread> threads = new ArrayList<>();</span> | 
|  | <span class="source-line-no">7315</span><span id="line-7315">      for (int i = 0; i < numRows; i++) {</span> | 
|  | <span class="source-line-no">7316</span><span id="line-7316">        final int count = i;</span> | 
|  | <span class="source-line-no">7317</span><span id="line-7317">        Thread t = new Thread(new Runnable() {</span> | 
|  | <span class="source-line-no">7318</span><span id="line-7318"></span> | 
|  | <span class="source-line-no">7319</span><span id="line-7319">          @Override</span> | 
|  | <span class="source-line-no">7320</span><span id="line-7320">          public void run() {</span> | 
|  | <span class="source-line-no">7321</span><span id="line-7321">            byte[] row = Bytes.toBytes("row" + count);</span> | 
|  | <span class="source-line-no">7322</span><span id="line-7322">            Put put = new Put(row);</span> | 
|  | <span class="source-line-no">7323</span><span id="line-7323">            put.setDurability(Durability.SYNC_WAL);</span> | 
|  | <span class="source-line-no">7324</span><span id="line-7324">            byte[] value = Bytes.toBytes(String.valueOf(count));</span> | 
|  | <span class="source-line-no">7325</span><span id="line-7325">            for (byte[] family : families) {</span> | 
|  | <span class="source-line-no">7326</span><span id="line-7326">              for (byte[] qualifier : qualifiers) {</span> | 
|  | <span class="source-line-no">7327</span><span id="line-7327">                put.addColumn(family, qualifier, count, value);</span> | 
|  | <span class="source-line-no">7328</span><span id="line-7328">              }</span> | 
|  | <span class="source-line-no">7329</span><span id="line-7329">            }</span> | 
|  | <span class="source-line-no">7330</span><span id="line-7330">            try {</span> | 
|  | <span class="source-line-no">7331</span><span id="line-7331">              region.put(put);</span> | 
|  | <span class="source-line-no">7332</span><span id="line-7332">            } catch (IOException e) {</span> | 
|  | <span class="source-line-no">7333</span><span id="line-7333">              throw new RuntimeException(e);</span> | 
|  | <span class="source-line-no">7334</span><span id="line-7334">            }</span> | 
|  | <span class="source-line-no">7335</span><span id="line-7335">          }</span> | 
|  | <span class="source-line-no">7336</span><span id="line-7336">        });</span> | 
|  | <span class="source-line-no">7337</span><span id="line-7337">        threads.add(t);</span> | 
|  | <span class="source-line-no">7338</span><span id="line-7338">      }</span> | 
|  | <span class="source-line-no">7339</span><span id="line-7339">      for (Thread t : threads) {</span> | 
|  | <span class="source-line-no">7340</span><span id="line-7340">        t.start();</span> | 
|  | <span class="source-line-no">7341</span><span id="line-7341">      }</span> | 
|  | <span class="source-line-no">7342</span><span id="line-7342"></span> | 
|  | <span class="source-line-no">7343</span><span id="line-7343">      for (int i = 0; i < testCount; i++) {</span> | 
|  | <span class="source-line-no">7344</span><span id="line-7344">        region.getWAL().rollWriter();</span> | 
|  | <span class="source-line-no">7345</span><span id="line-7345">        Thread.yield();</span> | 
|  | <span class="source-line-no">7346</span><span id="line-7346">      }</span> | 
|  | <span class="source-line-no">7347</span><span id="line-7347">    } finally {</span> | 
|  | <span class="source-line-no">7348</span><span id="line-7348">      try {</span> | 
|  | <span class="source-line-no">7349</span><span id="line-7349">        HBaseTestingUtil.closeRegionAndWAL(this.region);</span> | 
|  | <span class="source-line-no">7350</span><span id="line-7350">        CONF.setInt("hbase.regionserver.wal.disruptor.event.count", 16 * 1024);</span> | 
|  | <span class="source-line-no">7351</span><span id="line-7351">      } catch (DroppedSnapshotException dse) {</span> | 
|  | <span class="source-line-no">7352</span><span id="line-7352">        // We could get this on way out because we interrupt the background flusher and it could</span> | 
|  | <span class="source-line-no">7353</span><span id="line-7353">        // fail anywhere causing a DSE over in the background flusher... only it is not properly</span> | 
|  | <span class="source-line-no">7354</span><span id="line-7354">        // dealt with so could still be memory hanging out when we get to here -- memory we can't</span> | 
|  | <span class="source-line-no">7355</span><span id="line-7355">        // flush because the accounting is 'off' since original DSE.</span> | 
|  | <span class="source-line-no">7356</span><span id="line-7356">      }</span> | 
|  | <span class="source-line-no">7357</span><span id="line-7357">      this.region = null;</span> | 
|  | <span class="source-line-no">7358</span><span id="line-7358">    }</span> | 
|  | <span class="source-line-no">7359</span><span id="line-7359">  }</span> | 
|  | <span class="source-line-no">7360</span><span id="line-7360"></span> | 
|  | <span class="source-line-no">7361</span><span id="line-7361">  @Test</span> | 
|  | <span class="source-line-no">7362</span><span id="line-7362">  public void testMutateRow() throws Exception {</span> | 
|  | <span class="source-line-no">7363</span><span id="line-7363">    final byte[] row = Bytes.toBytes("row");</span> | 
|  | <span class="source-line-no">7364</span><span id="line-7364">    final byte[] q1 = Bytes.toBytes("q1");</span> | 
|  | <span class="source-line-no">7365</span><span id="line-7365">    final byte[] q2 = Bytes.toBytes("q2");</span> | 
|  | <span class="source-line-no">7366</span><span id="line-7366">    final byte[] q3 = Bytes.toBytes("q3");</span> | 
|  | <span class="source-line-no">7367</span><span id="line-7367">    final byte[] q4 = Bytes.toBytes("q4");</span> | 
|  | <span class="source-line-no">7368</span><span id="line-7368">    final String v1 = "v1";</span> | 
|  | <span class="source-line-no">7369</span><span id="line-7369"></span> | 
|  | <span class="source-line-no">7370</span><span id="line-7370">    region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">7371</span><span id="line-7371"></span> | 
|  | <span class="source-line-no">7372</span><span id="line-7372">    // Initial values</span> | 
|  | <span class="source-line-no">7373</span><span id="line-7373">    region</span> | 
|  | <span class="source-line-no">7374</span><span id="line-7374">      .batchMutate(new Mutation[] { new Put(row).addColumn(fam1, q2, Bytes.toBytes("toBeDeleted")),</span> | 
|  | <span class="source-line-no">7375</span><span id="line-7375">        new Put(row).addColumn(fam1, q3, Bytes.toBytes(5L)),</span> | 
|  | <span class="source-line-no">7376</span><span id="line-7376">        new Put(row).addColumn(fam1, q4, Bytes.toBytes("a")), });</span> | 
|  | <span class="source-line-no">7377</span><span id="line-7377"></span> | 
|  | <span class="source-line-no">7378</span><span id="line-7378">    // Do mutateRow</span> | 
|  | <span class="source-line-no">7379</span><span id="line-7379">    Result result = region.mutateRow(</span> | 
|  | <span class="source-line-no">7380</span><span id="line-7380">      new RowMutations(row).add(Arrays.asList(new Put(row).addColumn(fam1, q1, Bytes.toBytes(v1)),</span> | 
|  | <span class="source-line-no">7381</span><span id="line-7381">        new Delete(row).addColumns(fam1, q2), new Increment(row).addColumn(fam1, q3, 1),</span> | 
|  | <span class="source-line-no">7382</span><span id="line-7382">        new Append(row).addColumn(fam1, q4, Bytes.toBytes("b")))));</span> | 
|  | <span class="source-line-no">7383</span><span id="line-7383"></span> | 
|  | <span class="source-line-no">7384</span><span id="line-7384">    assertNotNull(result);</span> | 
|  | <span class="source-line-no">7385</span><span id="line-7385">    assertEquals(6L, Bytes.toLong(result.getValue(fam1, q3)));</span> | 
|  | <span class="source-line-no">7386</span><span id="line-7386">    assertEquals("ab", Bytes.toString(result.getValue(fam1, q4)));</span> | 
|  | <span class="source-line-no">7387</span><span id="line-7387"></span> | 
|  | <span class="source-line-no">7388</span><span id="line-7388">    // Verify the value</span> | 
|  | <span class="source-line-no">7389</span><span id="line-7389">    result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7390</span><span id="line-7390">    assertEquals(v1, Bytes.toString(result.getValue(fam1, q1)));</span> | 
|  | <span class="source-line-no">7391</span><span id="line-7391">    assertNull(result.getValue(fam1, q2));</span> | 
|  | <span class="source-line-no">7392</span><span id="line-7392">    assertEquals(6L, Bytes.toLong(result.getValue(fam1, q3)));</span> | 
|  | <span class="source-line-no">7393</span><span id="line-7393">    assertEquals("ab", Bytes.toString(result.getValue(fam1, q4)));</span> | 
|  | <span class="source-line-no">7394</span><span id="line-7394">  }</span> | 
|  | <span class="source-line-no">7395</span><span id="line-7395"></span> | 
|  | <span class="source-line-no">7396</span><span id="line-7396">  @Test</span> | 
|  | <span class="source-line-no">7397</span><span id="line-7397">  public void testMutateRowInParallel() throws Exception {</span> | 
|  | <span class="source-line-no">7398</span><span id="line-7398">    final int numReaderThreads = 100;</span> | 
|  | <span class="source-line-no">7399</span><span id="line-7399">    final CountDownLatch latch = new CountDownLatch(numReaderThreads);</span> | 
|  | <span class="source-line-no">7400</span><span id="line-7400"></span> | 
|  | <span class="source-line-no">7401</span><span id="line-7401">    final byte[] row = Bytes.toBytes("row");</span> | 
|  | <span class="source-line-no">7402</span><span id="line-7402">    final byte[] q1 = Bytes.toBytes("q1");</span> | 
|  | <span class="source-line-no">7403</span><span id="line-7403">    final byte[] q2 = Bytes.toBytes("q2");</span> | 
|  | <span class="source-line-no">7404</span><span id="line-7404">    final byte[] q3 = Bytes.toBytes("q3");</span> | 
|  | <span class="source-line-no">7405</span><span id="line-7405">    final byte[] q4 = Bytes.toBytes("q4");</span> | 
|  | <span class="source-line-no">7406</span><span id="line-7406">    final String v1 = "v1";</span> | 
|  | <span class="source-line-no">7407</span><span id="line-7407">    final String v2 = "v2";</span> | 
|  | <span class="source-line-no">7408</span><span id="line-7408"></span> | 
|  | <span class="source-line-no">7409</span><span id="line-7409">    // We need to ensure the timestamp of the delete operation is more than the previous one</span> | 
|  | <span class="source-line-no">7410</span><span id="line-7410">    final AtomicLong deleteTimestamp = new AtomicLong();</span> | 
|  | <span class="source-line-no">7411</span><span id="line-7411"></span> | 
|  | <span class="source-line-no">7412</span><span id="line-7412">    region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">7413</span><span id="line-7413"></span> | 
|  | <span class="source-line-no">7414</span><span id="line-7414">    // Initial values</span> | 
|  | <span class="source-line-no">7415</span><span id="line-7415">    region.batchMutate(new Mutation[] { new Put(row).addColumn(fam1, q1, Bytes.toBytes(v1))</span> | 
|  | <span class="source-line-no">7416</span><span id="line-7416">      .addColumn(fam1, q2, deleteTimestamp.getAndIncrement(), Bytes.toBytes(v2))</span> | 
|  | <span class="source-line-no">7417</span><span id="line-7417">      .addColumn(fam1, q3, Bytes.toBytes(1L)).addColumn(fam1, q4, Bytes.toBytes("a")) });</span> | 
|  | <span class="source-line-no">7418</span><span id="line-7418"></span> | 
|  | <span class="source-line-no">7419</span><span id="line-7419">    final AtomicReference<AssertionError> assertionError = new AtomicReference<>();</span> | 
|  | <span class="source-line-no">7420</span><span id="line-7420"></span> | 
|  | <span class="source-line-no">7421</span><span id="line-7421">    // Writer thread</span> | 
|  | <span class="source-line-no">7422</span><span id="line-7422">    Thread writerThread = new Thread(() -> {</span> | 
|  | <span class="source-line-no">7423</span><span id="line-7423">      try {</span> | 
|  | <span class="source-line-no">7424</span><span id="line-7424">        while (true) {</span> | 
|  | <span class="source-line-no">7425</span><span id="line-7425">          // If all the reader threads finish, then stop the writer thread</span> | 
|  | <span class="source-line-no">7426</span><span id="line-7426">          if (latch.await(0, TimeUnit.MILLISECONDS)) {</span> | 
|  | <span class="source-line-no">7427</span><span id="line-7427">            return;</span> | 
|  | <span class="source-line-no">7428</span><span id="line-7428">          }</span> | 
|  | <span class="source-line-no">7429</span><span id="line-7429"></span> | 
|  | <span class="source-line-no">7430</span><span id="line-7430">          // Execute the mutations. This should be done atomically</span> | 
|  | <span class="source-line-no">7431</span><span id="line-7431">          region.mutateRow(new RowMutations(row)</span> | 
|  | <span class="source-line-no">7432</span><span id="line-7432">            .add(Arrays.asList(new Put(row).addColumn(fam1, q1, Bytes.toBytes(v2)),</span> | 
|  | <span class="source-line-no">7433</span><span id="line-7433">              new Delete(row).addColumns(fam1, q2, deleteTimestamp.getAndIncrement()),</span> | 
|  | <span class="source-line-no">7434</span><span id="line-7434">              new Increment(row).addColumn(fam1, q3, 1L),</span> | 
|  | <span class="source-line-no">7435</span><span id="line-7435">              new Append(row).addColumn(fam1, q4, Bytes.toBytes("b")))));</span> | 
|  | <span class="source-line-no">7436</span><span id="line-7436"></span> | 
|  | <span class="source-line-no">7437</span><span id="line-7437">          // We need to ensure the timestamps of the Increment/Append operations are more than the</span> | 
|  | <span class="source-line-no">7438</span><span id="line-7438">          // previous ones</span> | 
|  | <span class="source-line-no">7439</span><span id="line-7439">          Result result = region.get(new Get(row).addColumn(fam1, q3).addColumn(fam1, q4));</span> | 
|  | <span class="source-line-no">7440</span><span id="line-7440">          long tsIncrement = result.getColumnLatestCell(fam1, q3).getTimestamp();</span> | 
|  | <span class="source-line-no">7441</span><span id="line-7441">          long tsAppend = result.getColumnLatestCell(fam1, q4).getTimestamp();</span> | 
|  | <span class="source-line-no">7442</span><span id="line-7442"></span> | 
|  | <span class="source-line-no">7443</span><span id="line-7443">          // Put the initial values</span> | 
|  | <span class="source-line-no">7444</span><span id="line-7444">          region.batchMutate(new Mutation[] { new Put(row).addColumn(fam1, q1, Bytes.toBytes(v1))</span> | 
|  | <span class="source-line-no">7445</span><span id="line-7445">            .addColumn(fam1, q2, deleteTimestamp.getAndIncrement(), Bytes.toBytes(v2))</span> | 
|  | <span class="source-line-no">7446</span><span id="line-7446">            .addColumn(fam1, q3, tsIncrement + 1, Bytes.toBytes(1L))</span> | 
|  | <span class="source-line-no">7447</span><span id="line-7447">            .addColumn(fam1, q4, tsAppend + 1, Bytes.toBytes("a")) });</span> | 
|  | <span class="source-line-no">7448</span><span id="line-7448">        }</span> | 
|  | <span class="source-line-no">7449</span><span id="line-7449">      } catch (Exception e) {</span> | 
|  | <span class="source-line-no">7450</span><span id="line-7450">        assertionError.set(new AssertionError(e));</span> | 
|  | <span class="source-line-no">7451</span><span id="line-7451">      }</span> | 
|  | <span class="source-line-no">7452</span><span id="line-7452">    });</span> | 
|  | <span class="source-line-no">7453</span><span id="line-7453">    writerThread.start();</span> | 
|  | <span class="source-line-no">7454</span><span id="line-7454"></span> | 
|  | <span class="source-line-no">7455</span><span id="line-7455">    // Reader threads</span> | 
|  | <span class="source-line-no">7456</span><span id="line-7456">    for (int i = 0; i < numReaderThreads; i++) {</span> | 
|  | <span class="source-line-no">7457</span><span id="line-7457">      new Thread(() -> {</span> | 
|  | <span class="source-line-no">7458</span><span id="line-7458">        try {</span> | 
|  | <span class="source-line-no">7459</span><span id="line-7459">          for (int j = 0; j < 10000; j++) {</span> | 
|  | <span class="source-line-no">7460</span><span id="line-7460">            // Verify the values</span> | 
|  | <span class="source-line-no">7461</span><span id="line-7461">            Result result = region.get(new Get(row));</span> | 
|  | <span class="source-line-no">7462</span><span id="line-7462"></span> | 
|  | <span class="source-line-no">7463</span><span id="line-7463">            // The values should be equals to either the initial values or the values after</span> | 
|  | <span class="source-line-no">7464</span><span id="line-7464">            // executing the mutations</span> | 
|  | <span class="source-line-no">7465</span><span id="line-7465">            String q1Value = Bytes.toString(result.getValue(fam1, q1));</span> | 
|  | <span class="source-line-no">7466</span><span id="line-7466">            if (v1.equals(q1Value)) {</span> | 
|  | <span class="source-line-no">7467</span><span id="line-7467">              assertEquals(v2, Bytes.toString(result.getValue(fam1, q2)));</span> | 
|  | <span class="source-line-no">7468</span><span id="line-7468">              assertEquals(1L, Bytes.toLong(result.getValue(fam1, q3)));</span> | 
|  | <span class="source-line-no">7469</span><span id="line-7469">              assertEquals("a", Bytes.toString(result.getValue(fam1, q4)));</span> | 
|  | <span class="source-line-no">7470</span><span id="line-7470">            } else if (v2.equals(q1Value)) {</span> | 
|  | <span class="source-line-no">7471</span><span id="line-7471">              assertNull(Bytes.toString(result.getValue(fam1, q2)));</span> | 
|  | <span class="source-line-no">7472</span><span id="line-7472">              assertEquals(2L, Bytes.toLong(result.getValue(fam1, q3)));</span> | 
|  | <span class="source-line-no">7473</span><span id="line-7473">              assertEquals("ab", Bytes.toString(result.getValue(fam1, q4)));</span> | 
|  | <span class="source-line-no">7474</span><span id="line-7474">            } else {</span> | 
|  | <span class="source-line-no">7475</span><span id="line-7475">              fail("the qualifier " + Bytes.toString(q1) + " should be " + v1 + " or " + v2</span> | 
|  | <span class="source-line-no">7476</span><span id="line-7476">                + ", but " + q1Value);</span> | 
|  | <span class="source-line-no">7477</span><span id="line-7477">            }</span> | 
|  | <span class="source-line-no">7478</span><span id="line-7478">          }</span> | 
|  | <span class="source-line-no">7479</span><span id="line-7479">        } catch (Exception e) {</span> | 
|  | <span class="source-line-no">7480</span><span id="line-7480">          assertionError.set(new AssertionError(e));</span> | 
|  | <span class="source-line-no">7481</span><span id="line-7481">        } catch (AssertionError e) {</span> | 
|  | <span class="source-line-no">7482</span><span id="line-7482">          assertionError.set(e);</span> | 
|  | <span class="source-line-no">7483</span><span id="line-7483">        }</span> | 
|  | <span class="source-line-no">7484</span><span id="line-7484"></span> | 
|  | <span class="source-line-no">7485</span><span id="line-7485">        latch.countDown();</span> | 
|  | <span class="source-line-no">7486</span><span id="line-7486">      }).start();</span> | 
|  | <span class="source-line-no">7487</span><span id="line-7487">    }</span> | 
|  | <span class="source-line-no">7488</span><span id="line-7488"></span> | 
|  | <span class="source-line-no">7489</span><span id="line-7489">    writerThread.join();</span> | 
|  | <span class="source-line-no">7490</span><span id="line-7490"></span> | 
|  | <span class="source-line-no">7491</span><span id="line-7491">    if (assertionError.get() != null) {</span> | 
|  | <span class="source-line-no">7492</span><span id="line-7492">      throw assertionError.get();</span> | 
|  | <span class="source-line-no">7493</span><span id="line-7493">    }</span> | 
|  | <span class="source-line-no">7494</span><span id="line-7494">  }</span> | 
|  | <span class="source-line-no">7495</span><span id="line-7495"></span> | 
|  | <span class="source-line-no">7496</span><span id="line-7496">  @Test</span> | 
|  | <span class="source-line-no">7497</span><span id="line-7497">  public void testMutateRow_WriteRequestCount() throws Exception {</span> | 
|  | <span class="source-line-no">7498</span><span id="line-7498">    byte[] row1 = Bytes.toBytes("row1");</span> | 
|  | <span class="source-line-no">7499</span><span id="line-7499">    byte[] fam1 = Bytes.toBytes("fam1");</span> | 
|  | <span class="source-line-no">7500</span><span id="line-7500">    byte[] qf1 = Bytes.toBytes("qualifier");</span> | 
|  | <span class="source-line-no">7501</span><span id="line-7501">    byte[] val1 = Bytes.toBytes("value1");</span> | 
|  | <span class="source-line-no">7502</span><span id="line-7502"></span> | 
|  | <span class="source-line-no">7503</span><span id="line-7503">    RowMutations rm = new RowMutations(row1);</span> | 
|  | <span class="source-line-no">7504</span><span id="line-7504">    Put put = new Put(row1);</span> | 
|  | <span class="source-line-no">7505</span><span id="line-7505">    put.addColumn(fam1, qf1, val1);</span> | 
|  | <span class="source-line-no">7506</span><span id="line-7506">    rm.add(put);</span> | 
|  | <span class="source-line-no">7507</span><span id="line-7507"></span> | 
|  | <span class="source-line-no">7508</span><span id="line-7508">    this.region = initHRegion(tableName, method, CONF, fam1);</span> | 
|  | <span class="source-line-no">7509</span><span id="line-7509">    long wrcBeforeMutate = this.region.writeRequestsCount.longValue();</span> | 
|  | <span class="source-line-no">7510</span><span id="line-7510">    this.region.mutateRow(rm);</span> | 
|  | <span class="source-line-no">7511</span><span id="line-7511">    long wrcAfterMutate = this.region.writeRequestsCount.longValue();</span> | 
|  | <span class="source-line-no">7512</span><span id="line-7512">    Assert.assertEquals(wrcBeforeMutate + rm.getMutations().size(), wrcAfterMutate);</span> | 
|  | <span class="source-line-no">7513</span><span id="line-7513">  }</span> | 
|  | <span class="source-line-no">7514</span><span id="line-7514"></span> | 
|  | <span class="source-line-no">7515</span><span id="line-7515">  @Test</span> | 
|  | <span class="source-line-no">7516</span><span id="line-7516">  public void testBulkLoadReplicationEnabled() throws IOException {</span> | 
|  | <span class="source-line-no">7517</span><span id="line-7517">    TEST_UTIL.getConfiguration().setBoolean(HConstants.REPLICATION_BULKLOAD_ENABLE_KEY, true);</span> | 
|  | <span class="source-line-no">7518</span><span id="line-7518">    final ServerName serverName = ServerName.valueOf(name.getMethodName(), 100, 42);</span> | 
|  | <span class="source-line-no">7519</span><span id="line-7519">    final RegionServerServices rss = spy(TEST_UTIL.createMockRegionServerService(serverName));</span> | 
|  | <span class="source-line-no">7520</span><span id="line-7520"></span> | 
|  | <span class="source-line-no">7521</span><span id="line-7521">    TableDescriptor tableDescriptor =</span> | 
|  | <span class="source-line-no">7522</span><span id="line-7522">      TableDescriptorBuilder.newBuilder(TableName.valueOf(name.getMethodName()))</span> | 
|  | <span class="source-line-no">7523</span><span id="line-7523">        .setColumnFamily(ColumnFamilyDescriptorBuilder.of(fam1)).build();</span> | 
|  | <span class="source-line-no">7524</span><span id="line-7524">    RegionInfo hri = RegionInfoBuilder.newBuilder(tableDescriptor.getTableName()).build();</span> | 
|  | <span class="source-line-no">7525</span><span id="line-7525">    region = HRegion.openHRegion(hri, tableDescriptor, rss.getWAL(hri),</span> | 
|  | <span class="source-line-no">7526</span><span id="line-7526">      TEST_UTIL.getConfiguration(), rss, null);</span> | 
|  | <span class="source-line-no">7527</span><span id="line-7527"></span> | 
|  | <span class="source-line-no">7528</span><span id="line-7528">    assertTrue(region.conf.getBoolean(HConstants.REPLICATION_BULKLOAD_ENABLE_KEY, false));</span> | 
|  | <span class="source-line-no">7529</span><span id="line-7529">    String plugins = region.conf.get(CoprocessorHost.REGION_COPROCESSOR_CONF_KEY, "");</span> | 
|  | <span class="source-line-no">7530</span><span id="line-7530">    String replicationCoprocessorClass = ReplicationObserver.class.getCanonicalName();</span> | 
|  | <span class="source-line-no">7531</span><span id="line-7531">    assertTrue(plugins.contains(replicationCoprocessorClass));</span> | 
|  | <span class="source-line-no">7532</span><span id="line-7532">    assertTrue(region.getCoprocessorHost().getCoprocessors()</span> | 
|  | <span class="source-line-no">7533</span><span id="line-7533">      .contains(ReplicationObserver.class.getSimpleName()));</span> | 
|  | <span class="source-line-no">7534</span><span id="line-7534">  }</span> | 
|  | <span class="source-line-no">7535</span><span id="line-7535"></span> | 
|  | <span class="source-line-no">7536</span><span id="line-7536">  /**</span> | 
|  | <span class="source-line-no">7537</span><span id="line-7537">   * The same as HRegion class, the only difference is that instantiateHStore will create a</span> | 
|  | <span class="source-line-no">7538</span><span id="line-7538">   * different HStore - HStoreForTesting. [HBASE-8518]</span> | 
|  | <span class="source-line-no">7539</span><span id="line-7539">   */</span> | 
|  | <span class="source-line-no">7540</span><span id="line-7540">  public static class HRegionForTesting extends HRegion {</span> | 
|  | <span class="source-line-no">7541</span><span id="line-7541"></span> | 
|  | <span class="source-line-no">7542</span><span id="line-7542">    public HRegionForTesting(final Path tableDir, final WAL wal, final FileSystem fs,</span> | 
|  | <span class="source-line-no">7543</span><span id="line-7543">      final Configuration confParam, final RegionInfo regionInfo, final TableDescriptor htd,</span> | 
|  | <span class="source-line-no">7544</span><span id="line-7544">      final RegionServerServices rsServices) {</span> | 
|  | <span class="source-line-no">7545</span><span id="line-7545">      this(new HRegionFileSystem(confParam, fs, tableDir, regionInfo), wal, confParam, htd,</span> | 
|  | <span class="source-line-no">7546</span><span id="line-7546">        rsServices);</span> | 
|  | <span class="source-line-no">7547</span><span id="line-7547">    }</span> | 
|  | <span class="source-line-no">7548</span><span id="line-7548"></span> | 
|  | <span class="source-line-no">7549</span><span id="line-7549">    public HRegionForTesting(HRegionFileSystem fs, WAL wal, Configuration confParam,</span> | 
|  | <span class="source-line-no">7550</span><span id="line-7550">      TableDescriptor htd, RegionServerServices rsServices) {</span> | 
|  | <span class="source-line-no">7551</span><span id="line-7551">      super(fs, wal, confParam, htd, rsServices);</span> | 
|  | <span class="source-line-no">7552</span><span id="line-7552">    }</span> | 
|  | <span class="source-line-no">7553</span><span id="line-7553"></span> | 
|  | <span class="source-line-no">7554</span><span id="line-7554">    /**</span> | 
|  | <span class="source-line-no">7555</span><span id="line-7555">     * Create HStore instance.</span> | 
|  | <span class="source-line-no">7556</span><span id="line-7556">     * @return If Mob is enabled, return HMobStore, otherwise return HStoreForTesting.</span> | 
|  | <span class="source-line-no">7557</span><span id="line-7557">     */</span> | 
|  | <span class="source-line-no">7558</span><span id="line-7558">    @Override</span> | 
|  | <span class="source-line-no">7559</span><span id="line-7559">    protected HStore instantiateHStore(final ColumnFamilyDescriptor family, boolean warmup)</span> | 
|  | <span class="source-line-no">7560</span><span id="line-7560">      throws IOException {</span> | 
|  | <span class="source-line-no">7561</span><span id="line-7561">      if (family.isMobEnabled()) {</span> | 
|  | <span class="source-line-no">7562</span><span id="line-7562">        if (HFile.getFormatVersion(this.conf) < HFile.MIN_FORMAT_VERSION_WITH_TAGS) {</span> | 
|  | <span class="source-line-no">7563</span><span id="line-7563">          throw new IOException("A minimum HFile version of " + HFile.MIN_FORMAT_VERSION_WITH_TAGS</span> | 
|  | <span class="source-line-no">7564</span><span id="line-7564">            + " is required for MOB feature. Consider setting " + HFile.FORMAT_VERSION_KEY</span> | 
|  | <span class="source-line-no">7565</span><span id="line-7565">            + " accordingly.");</span> | 
|  | <span class="source-line-no">7566</span><span id="line-7566">        }</span> | 
|  | <span class="source-line-no">7567</span><span id="line-7567">        return new HMobStore(this, family, this.conf, warmup);</span> | 
|  | <span class="source-line-no">7568</span><span id="line-7568">      }</span> | 
|  | <span class="source-line-no">7569</span><span id="line-7569">      return new HStoreForTesting(this, family, this.conf, warmup);</span> | 
|  | <span class="source-line-no">7570</span><span id="line-7570">    }</span> | 
|  | <span class="source-line-no">7571</span><span id="line-7571">  }</span> | 
|  | <span class="source-line-no">7572</span><span id="line-7572"></span> | 
|  | <span class="source-line-no">7573</span><span id="line-7573">  /**</span> | 
|  | <span class="source-line-no">7574</span><span id="line-7574">   * HStoreForTesting is merely the same as HStore, the difference is in the doCompaction method of</span> | 
|  | <span class="source-line-no">7575</span><span id="line-7575">   * HStoreForTesting there is a checkpoint "hbase.hstore.compaction.complete" which doesn't let</span> | 
|  | <span class="source-line-no">7576</span><span id="line-7576">   * hstore compaction complete. In the former edition, this config is set in HStore class inside</span> | 
|  | <span class="source-line-no">7577</span><span id="line-7577">   * compact method, though this is just for testing, otherwise it doesn't do any help. In</span> | 
|  | <span class="source-line-no">7578</span><span id="line-7578">   * HBASE-8518, we try to get rid of all "hbase.hstore.compaction.complete" config (except for</span> | 
|  | <span class="source-line-no">7579</span><span id="line-7579">   * testing code).</span> | 
|  | <span class="source-line-no">7580</span><span id="line-7580">   */</span> | 
|  | <span class="source-line-no">7581</span><span id="line-7581">  public static class HStoreForTesting extends HStore {</span> | 
|  | <span class="source-line-no">7582</span><span id="line-7582"></span> | 
|  | <span class="source-line-no">7583</span><span id="line-7583">    protected HStoreForTesting(final HRegion region, final ColumnFamilyDescriptor family,</span> | 
|  | <span class="source-line-no">7584</span><span id="line-7584">      final Configuration confParam, boolean warmup) throws IOException {</span> | 
|  | <span class="source-line-no">7585</span><span id="line-7585">      super(region, family, confParam, warmup);</span> | 
|  | <span class="source-line-no">7586</span><span id="line-7586">    }</span> | 
|  | <span class="source-line-no">7587</span><span id="line-7587"></span> | 
|  | <span class="source-line-no">7588</span><span id="line-7588">    @Override</span> | 
|  | <span class="source-line-no">7589</span><span id="line-7589">    protected List<HStoreFile> doCompaction(CompactionRequestImpl cr,</span> | 
|  | <span class="source-line-no">7590</span><span id="line-7590">      Collection<HStoreFile> filesToCompact, User user, long compactionStartTime,</span> | 
|  | <span class="source-line-no">7591</span><span id="line-7591">      List<Path> newFiles) throws IOException {</span> | 
|  | <span class="source-line-no">7592</span><span id="line-7592">      // let compaction incomplete.</span> | 
|  | <span class="source-line-no">7593</span><span id="line-7593">      if (!this.conf.getBoolean("hbase.hstore.compaction.complete", true)) {</span> | 
|  | <span class="source-line-no">7594</span><span id="line-7594">        LOG.warn("hbase.hstore.compaction.complete is set to false");</span> | 
|  | <span class="source-line-no">7595</span><span id="line-7595">        List<HStoreFile> sfs = new ArrayList<>(newFiles.size());</span> | 
|  | <span class="source-line-no">7596</span><span id="line-7596">        final boolean evictOnClose =</span> | 
|  | <span class="source-line-no">7597</span><span id="line-7597">          getCacheConfig() != null ? getCacheConfig().shouldEvictOnClose() : true;</span> | 
|  | <span class="source-line-no">7598</span><span id="line-7598">        for (Path newFile : newFiles) {</span> | 
|  | <span class="source-line-no">7599</span><span id="line-7599">          // Create storefile around what we wrote with a reader on it.</span> | 
|  | <span class="source-line-no">7600</span><span id="line-7600">          HStoreFile sf = storeEngine.createStoreFileAndReader(newFile);</span> | 
|  | <span class="source-line-no">7601</span><span id="line-7601">          sf.closeStoreFile(evictOnClose);</span> | 
|  | <span class="source-line-no">7602</span><span id="line-7602">          sfs.add(sf);</span> | 
|  | <span class="source-line-no">7603</span><span id="line-7603">        }</span> | 
|  | <span class="source-line-no">7604</span><span id="line-7604">        return sfs;</span> | 
|  | <span class="source-line-no">7605</span><span id="line-7605">      }</span> | 
|  | <span class="source-line-no">7606</span><span id="line-7606">      return super.doCompaction(cr, filesToCompact, user, compactionStartTime, newFiles);</span> | 
|  | <span class="source-line-no">7607</span><span id="line-7607">    }</span> | 
|  | <span class="source-line-no">7608</span><span id="line-7608">  }</span> | 
|  | <span class="source-line-no">7609</span><span id="line-7609"></span> | 
|  | <span class="source-line-no">7610</span><span id="line-7610">  @Test</span> | 
|  | <span class="source-line-no">7611</span><span id="line-7611">  public void testCloseNoInterrupt() throws Exception {</span> | 
|  | <span class="source-line-no">7612</span><span id="line-7612">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">7613</span><span id="line-7613">    byte[][] families = { cf1 };</span> | 
|  | <span class="source-line-no">7614</span><span id="line-7614">    final int SLEEP_TIME = 10 * 1000;</span> | 
|  | <span class="source-line-no">7615</span><span id="line-7615"></span> | 
|  | <span class="source-line-no">7616</span><span id="line-7616">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">7617</span><span id="line-7617">    // Disable close thread interrupt and server abort behavior</span> | 
|  | <span class="source-line-no">7618</span><span id="line-7618">    conf.setBoolean(HRegion.CLOSE_WAIT_ABORT, false);</span> | 
|  | <span class="source-line-no">7619</span><span id="line-7619">    conf.setInt(HRegion.CLOSE_WAIT_INTERVAL, 1000);</span> | 
|  | <span class="source-line-no">7620</span><span id="line-7620">    region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">7621</span><span id="line-7621"></span> | 
|  | <span class="source-line-no">7622</span><span id="line-7622">    final CountDownLatch latch = new CountDownLatch(1);</span> | 
|  | <span class="source-line-no">7623</span><span id="line-7623">    final AtomicBoolean holderInterrupted = new AtomicBoolean();</span> | 
|  | <span class="source-line-no">7624</span><span id="line-7624">    Thread holder = new Thread(new Runnable() {</span> | 
|  | <span class="source-line-no">7625</span><span id="line-7625">      @Override</span> | 
|  | <span class="source-line-no">7626</span><span id="line-7626">      public void run() {</span> | 
|  | <span class="source-line-no">7627</span><span id="line-7627">        try {</span> | 
|  | <span class="source-line-no">7628</span><span id="line-7628">          LOG.info("Starting region operation holder");</span> | 
|  | <span class="source-line-no">7629</span><span id="line-7629">          region.startRegionOperation(Operation.SCAN);</span> | 
|  | <span class="source-line-no">7630</span><span id="line-7630">          latch.countDown();</span> | 
|  | <span class="source-line-no">7631</span><span id="line-7631">          try {</span> | 
|  | <span class="source-line-no">7632</span><span id="line-7632">            Thread.sleep(SLEEP_TIME);</span> | 
|  | <span class="source-line-no">7633</span><span id="line-7633">          } catch (InterruptedException e) {</span> | 
|  | <span class="source-line-no">7634</span><span id="line-7634">            LOG.info("Interrupted");</span> | 
|  | <span class="source-line-no">7635</span><span id="line-7635">            holderInterrupted.set(true);</span> | 
|  | <span class="source-line-no">7636</span><span id="line-7636">          }</span> | 
|  | <span class="source-line-no">7637</span><span id="line-7637">        } catch (Exception e) {</span> | 
|  | <span class="source-line-no">7638</span><span id="line-7638">          throw new RuntimeException(e);</span> | 
|  | <span class="source-line-no">7639</span><span id="line-7639">        } finally {</span> | 
|  | <span class="source-line-no">7640</span><span id="line-7640">          try {</span> | 
|  | <span class="source-line-no">7641</span><span id="line-7641">            region.closeRegionOperation();</span> | 
|  | <span class="source-line-no">7642</span><span id="line-7642">          } catch (IOException e) {</span> | 
|  | <span class="source-line-no">7643</span><span id="line-7643">          }</span> | 
|  | <span class="source-line-no">7644</span><span id="line-7644">          LOG.info("Stopped region operation holder");</span> | 
|  | <span class="source-line-no">7645</span><span id="line-7645">        }</span> | 
|  | <span class="source-line-no">7646</span><span id="line-7646">      }</span> | 
|  | <span class="source-line-no">7647</span><span id="line-7647">    });</span> | 
|  | <span class="source-line-no">7648</span><span id="line-7648"></span> | 
|  | <span class="source-line-no">7649</span><span id="line-7649">    holder.start();</span> | 
|  | <span class="source-line-no">7650</span><span id="line-7650">    latch.await();</span> | 
|  | <span class="source-line-no">7651</span><span id="line-7651">    HBaseTestingUtil.closeRegionAndWAL(region);</span> | 
|  | <span class="source-line-no">7652</span><span id="line-7652">    region = null;</span> | 
|  | <span class="source-line-no">7653</span><span id="line-7653">    holder.join();</span> | 
|  | <span class="source-line-no">7654</span><span id="line-7654"></span> | 
|  | <span class="source-line-no">7655</span><span id="line-7655">    assertFalse("Region lock holder should not have been interrupted", holderInterrupted.get());</span> | 
|  | <span class="source-line-no">7656</span><span id="line-7656">  }</span> | 
|  | <span class="source-line-no">7657</span><span id="line-7657"></span> | 
|  | <span class="source-line-no">7658</span><span id="line-7658">  @Test</span> | 
|  | <span class="source-line-no">7659</span><span id="line-7659">  public void testCloseInterrupt() throws Exception {</span> | 
|  | <span class="source-line-no">7660</span><span id="line-7660">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">7661</span><span id="line-7661">    byte[][] families = { cf1 };</span> | 
|  | <span class="source-line-no">7662</span><span id="line-7662">    final int SLEEP_TIME = 10 * 1000;</span> | 
|  | <span class="source-line-no">7663</span><span id="line-7663"></span> | 
|  | <span class="source-line-no">7664</span><span id="line-7664">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">7665</span><span id="line-7665">    // Enable close thread interrupt and server abort behavior</span> | 
|  | <span class="source-line-no">7666</span><span id="line-7666">    conf.setBoolean(HRegion.CLOSE_WAIT_ABORT, true);</span> | 
|  | <span class="source-line-no">7667</span><span id="line-7667">    // Speed up the unit test, no need to wait default 10 seconds.</span> | 
|  | <span class="source-line-no">7668</span><span id="line-7668">    conf.setInt(HRegion.CLOSE_WAIT_INTERVAL, 1000);</span> | 
|  | <span class="source-line-no">7669</span><span id="line-7669">    region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">7670</span><span id="line-7670"></span> | 
|  | <span class="source-line-no">7671</span><span id="line-7671">    final CountDownLatch latch = new CountDownLatch(1);</span> | 
|  | <span class="source-line-no">7672</span><span id="line-7672">    final AtomicBoolean holderInterrupted = new AtomicBoolean();</span> | 
|  | <span class="source-line-no">7673</span><span id="line-7673">    Thread holder = new Thread(new Runnable() {</span> | 
|  | <span class="source-line-no">7674</span><span id="line-7674">      @Override</span> | 
|  | <span class="source-line-no">7675</span><span id="line-7675">      public void run() {</span> | 
|  | <span class="source-line-no">7676</span><span id="line-7676">        try {</span> | 
|  | <span class="source-line-no">7677</span><span id="line-7677">          LOG.info("Starting region operation holder");</span> | 
|  | <span class="source-line-no">7678</span><span id="line-7678">          region.startRegionOperation(Operation.SCAN);</span> | 
|  | <span class="source-line-no">7679</span><span id="line-7679">          latch.countDown();</span> | 
|  | <span class="source-line-no">7680</span><span id="line-7680">          try {</span> | 
|  | <span class="source-line-no">7681</span><span id="line-7681">            Thread.sleep(SLEEP_TIME);</span> | 
|  | <span class="source-line-no">7682</span><span id="line-7682">          } catch (InterruptedException e) {</span> | 
|  | <span class="source-line-no">7683</span><span id="line-7683">            LOG.info("Interrupted");</span> | 
|  | <span class="source-line-no">7684</span><span id="line-7684">            holderInterrupted.set(true);</span> | 
|  | <span class="source-line-no">7685</span><span id="line-7685">          }</span> | 
|  | <span class="source-line-no">7686</span><span id="line-7686">        } catch (Exception e) {</span> | 
|  | <span class="source-line-no">7687</span><span id="line-7687">          throw new RuntimeException(e);</span> | 
|  | <span class="source-line-no">7688</span><span id="line-7688">        } finally {</span> | 
|  | <span class="source-line-no">7689</span><span id="line-7689">          try {</span> | 
|  | <span class="source-line-no">7690</span><span id="line-7690">            region.closeRegionOperation();</span> | 
|  | <span class="source-line-no">7691</span><span id="line-7691">          } catch (IOException e) {</span> | 
|  | <span class="source-line-no">7692</span><span id="line-7692">          }</span> | 
|  | <span class="source-line-no">7693</span><span id="line-7693">          LOG.info("Stopped region operation holder");</span> | 
|  | <span class="source-line-no">7694</span><span id="line-7694">        }</span> | 
|  | <span class="source-line-no">7695</span><span id="line-7695">      }</span> | 
|  | <span class="source-line-no">7696</span><span id="line-7696">    });</span> | 
|  | <span class="source-line-no">7697</span><span id="line-7697"></span> | 
|  | <span class="source-line-no">7698</span><span id="line-7698">    holder.start();</span> | 
|  | <span class="source-line-no">7699</span><span id="line-7699">    latch.await();</span> | 
|  | <span class="source-line-no">7700</span><span id="line-7700">    region.close();</span> | 
|  | <span class="source-line-no">7701</span><span id="line-7701">    region = null;</span> | 
|  | <span class="source-line-no">7702</span><span id="line-7702">    holder.join();</span> | 
|  | <span class="source-line-no">7703</span><span id="line-7703"></span> | 
|  | <span class="source-line-no">7704</span><span id="line-7704">    assertTrue("Region lock holder was not interrupted", holderInterrupted.get());</span> | 
|  | <span class="source-line-no">7705</span><span id="line-7705">  }</span> | 
|  | <span class="source-line-no">7706</span><span id="line-7706"></span> | 
|  | <span class="source-line-no">7707</span><span id="line-7707">  @Test</span> | 
|  | <span class="source-line-no">7708</span><span id="line-7708">  public void testCloseAbort() throws Exception {</span> | 
|  | <span class="source-line-no">7709</span><span id="line-7709">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">7710</span><span id="line-7710">    byte[][] families = { cf1 };</span> | 
|  | <span class="source-line-no">7711</span><span id="line-7711">    final int SLEEP_TIME = 10 * 1000;</span> | 
|  | <span class="source-line-no">7712</span><span id="line-7712"></span> | 
|  | <span class="source-line-no">7713</span><span id="line-7713">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">7714</span><span id="line-7714">    // Enable close thread interrupt and server abort behavior.</span> | 
|  | <span class="source-line-no">7715</span><span id="line-7715">    conf.setBoolean(HRegion.CLOSE_WAIT_ABORT, true);</span> | 
|  | <span class="source-line-no">7716</span><span id="line-7716">    // Set the abort interval to a fraction of sleep time so we are guaranteed to be aborted.</span> | 
|  | <span class="source-line-no">7717</span><span id="line-7717">    conf.setInt(HRegion.CLOSE_WAIT_TIME, SLEEP_TIME / 2);</span> | 
|  | <span class="source-line-no">7718</span><span id="line-7718">    // Set the wait interval to a fraction of sleep time so we are guaranteed to be interrupted.</span> | 
|  | <span class="source-line-no">7719</span><span id="line-7719">    conf.setInt(HRegion.CLOSE_WAIT_INTERVAL, SLEEP_TIME / 4);</span> | 
|  | <span class="source-line-no">7720</span><span id="line-7720">    region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">7721</span><span id="line-7721">    RegionServerServices rsServices = mock(RegionServerServices.class);</span> | 
|  | <span class="source-line-no">7722</span><span id="line-7722">    when(rsServices.getServerName()).thenReturn(ServerName.valueOf("localhost", 1000, 1000));</span> | 
|  | <span class="source-line-no">7723</span><span id="line-7723">    region.rsServices = rsServices;</span> | 
|  | <span class="source-line-no">7724</span><span id="line-7724"></span> | 
|  | <span class="source-line-no">7725</span><span id="line-7725">    final CountDownLatch latch = new CountDownLatch(1);</span> | 
|  | <span class="source-line-no">7726</span><span id="line-7726">    Thread holder = new Thread(new Runnable() {</span> | 
|  | <span class="source-line-no">7727</span><span id="line-7727">      @Override</span> | 
|  | <span class="source-line-no">7728</span><span id="line-7728">      public void run() {</span> | 
|  | <span class="source-line-no">7729</span><span id="line-7729">        try {</span> | 
|  | <span class="source-line-no">7730</span><span id="line-7730">          LOG.info("Starting region operation holder");</span> | 
|  | <span class="source-line-no">7731</span><span id="line-7731">          region.startRegionOperation(Operation.SCAN);</span> | 
|  | <span class="source-line-no">7732</span><span id="line-7732">          latch.countDown();</span> | 
|  | <span class="source-line-no">7733</span><span id="line-7733">          // Hold the lock for SLEEP_TIME seconds no matter how many times we are interrupted.</span> | 
|  | <span class="source-line-no">7734</span><span id="line-7734">          int timeRemaining = SLEEP_TIME;</span> | 
|  | <span class="source-line-no">7735</span><span id="line-7735">          while (timeRemaining > 0) {</span> | 
|  | <span class="source-line-no">7736</span><span id="line-7736">            long start = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">7737</span><span id="line-7737">            try {</span> | 
|  | <span class="source-line-no">7738</span><span id="line-7738">              Thread.sleep(timeRemaining);</span> | 
|  | <span class="source-line-no">7739</span><span id="line-7739">            } catch (InterruptedException e) {</span> | 
|  | <span class="source-line-no">7740</span><span id="line-7740">              LOG.info("Interrupted");</span> | 
|  | <span class="source-line-no">7741</span><span id="line-7741">            }</span> | 
|  | <span class="source-line-no">7742</span><span id="line-7742">            long end = EnvironmentEdgeManager.currentTime();</span> | 
|  | <span class="source-line-no">7743</span><span id="line-7743">            timeRemaining -= end - start;</span> | 
|  | <span class="source-line-no">7744</span><span id="line-7744">            if (timeRemaining < 0) {</span> | 
|  | <span class="source-line-no">7745</span><span id="line-7745">              timeRemaining = 0;</span> | 
|  | <span class="source-line-no">7746</span><span id="line-7746">            }</span> | 
|  | <span class="source-line-no">7747</span><span id="line-7747">            if (timeRemaining > 0) {</span> | 
|  | <span class="source-line-no">7748</span><span id="line-7748">              LOG.info("Sleeping again, remaining time " + timeRemaining + " ms");</span> | 
|  | <span class="source-line-no">7749</span><span id="line-7749">            }</span> | 
|  | <span class="source-line-no">7750</span><span id="line-7750">          }</span> | 
|  | <span class="source-line-no">7751</span><span id="line-7751">        } catch (Exception e) {</span> | 
|  | <span class="source-line-no">7752</span><span id="line-7752">          throw new RuntimeException(e);</span> | 
|  | <span class="source-line-no">7753</span><span id="line-7753">        } finally {</span> | 
|  | <span class="source-line-no">7754</span><span id="line-7754">          try {</span> | 
|  | <span class="source-line-no">7755</span><span id="line-7755">            region.closeRegionOperation();</span> | 
|  | <span class="source-line-no">7756</span><span id="line-7756">          } catch (IOException e) {</span> | 
|  | <span class="source-line-no">7757</span><span id="line-7757">          }</span> | 
|  | <span class="source-line-no">7758</span><span id="line-7758">          LOG.info("Stopped region operation holder");</span> | 
|  | <span class="source-line-no">7759</span><span id="line-7759">        }</span> | 
|  | <span class="source-line-no">7760</span><span id="line-7760">      }</span> | 
|  | <span class="source-line-no">7761</span><span id="line-7761">    });</span> | 
|  | <span class="source-line-no">7762</span><span id="line-7762"></span> | 
|  | <span class="source-line-no">7763</span><span id="line-7763">    holder.start();</span> | 
|  | <span class="source-line-no">7764</span><span id="line-7764">    latch.await();</span> | 
|  | <span class="source-line-no">7765</span><span id="line-7765">    assertThrows(IOException.class, () -> region.close());</span> | 
|  | <span class="source-line-no">7766</span><span id="line-7766">    holder.join();</span> | 
|  | <span class="source-line-no">7767</span><span id="line-7767"></span> | 
|  | <span class="source-line-no">7768</span><span id="line-7768">    // Verify the region tried to abort the server</span> | 
|  | <span class="source-line-no">7769</span><span id="line-7769">    verify(rsServices, atLeast(1)).abort(anyString(), any());</span> | 
|  | <span class="source-line-no">7770</span><span id="line-7770">  }</span> | 
|  | <span class="source-line-no">7771</span><span id="line-7771"></span> | 
|  | <span class="source-line-no">7772</span><span id="line-7772">  @Test</span> | 
|  | <span class="source-line-no">7773</span><span id="line-7773">  public void testInterruptProtection() throws Exception {</span> | 
|  | <span class="source-line-no">7774</span><span id="line-7774">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">7775</span><span id="line-7775">    byte[][] families = { cf1 };</span> | 
|  | <span class="source-line-no">7776</span><span id="line-7776">    final int SLEEP_TIME = 10 * 1000;</span> | 
|  | <span class="source-line-no">7777</span><span id="line-7777"></span> | 
|  | <span class="source-line-no">7778</span><span id="line-7778">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">7779</span><span id="line-7779">    // Enable close thread interrupt and server abort behavior.</span> | 
|  | <span class="source-line-no">7780</span><span id="line-7780">    conf.setBoolean(HRegion.CLOSE_WAIT_ABORT, true);</span> | 
|  | <span class="source-line-no">7781</span><span id="line-7781">    conf.setInt(HRegion.CLOSE_WAIT_INTERVAL, 1000);</span> | 
|  | <span class="source-line-no">7782</span><span id="line-7782">    region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">7783</span><span id="line-7783"></span> | 
|  | <span class="source-line-no">7784</span><span id="line-7784">    final CountDownLatch latch = new CountDownLatch(1);</span> | 
|  | <span class="source-line-no">7785</span><span id="line-7785">    final AtomicBoolean holderInterrupted = new AtomicBoolean();</span> | 
|  | <span class="source-line-no">7786</span><span id="line-7786">    Thread holder = new Thread(new Runnable() {</span> | 
|  | <span class="source-line-no">7787</span><span id="line-7787">      @Override</span> | 
|  | <span class="source-line-no">7788</span><span id="line-7788">      public void run() {</span> | 
|  | <span class="source-line-no">7789</span><span id="line-7789">        try {</span> | 
|  | <span class="source-line-no">7790</span><span id="line-7790">          LOG.info("Starting region operation holder");</span> | 
|  | <span class="source-line-no">7791</span><span id="line-7791">          region.startRegionOperation(Operation.SCAN);</span> | 
|  | <span class="source-line-no">7792</span><span id="line-7792">          LOG.info("Protecting against interrupts");</span> | 
|  | <span class="source-line-no">7793</span><span id="line-7793">          region.disableInterrupts();</span> | 
|  | <span class="source-line-no">7794</span><span id="line-7794">          try {</span> | 
|  | <span class="source-line-no">7795</span><span id="line-7795">            latch.countDown();</span> | 
|  | <span class="source-line-no">7796</span><span id="line-7796">            try {</span> | 
|  | <span class="source-line-no">7797</span><span id="line-7797">              Thread.sleep(SLEEP_TIME);</span> | 
|  | <span class="source-line-no">7798</span><span id="line-7798">            } catch (InterruptedException e) {</span> | 
|  | <span class="source-line-no">7799</span><span id="line-7799">              LOG.info("Interrupted");</span> | 
|  | <span class="source-line-no">7800</span><span id="line-7800">              holderInterrupted.set(true);</span> | 
|  | <span class="source-line-no">7801</span><span id="line-7801">            }</span> | 
|  | <span class="source-line-no">7802</span><span id="line-7802">          } finally {</span> | 
|  | <span class="source-line-no">7803</span><span id="line-7803">            region.enableInterrupts();</span> | 
|  | <span class="source-line-no">7804</span><span id="line-7804">          }</span> | 
|  | <span class="source-line-no">7805</span><span id="line-7805">        } catch (Exception e) {</span> | 
|  | <span class="source-line-no">7806</span><span id="line-7806">          throw new RuntimeException(e);</span> | 
|  | <span class="source-line-no">7807</span><span id="line-7807">        } finally {</span> | 
|  | <span class="source-line-no">7808</span><span id="line-7808">          try {</span> | 
|  | <span class="source-line-no">7809</span><span id="line-7809">            region.closeRegionOperation();</span> | 
|  | <span class="source-line-no">7810</span><span id="line-7810">          } catch (IOException e) {</span> | 
|  | <span class="source-line-no">7811</span><span id="line-7811">          }</span> | 
|  | <span class="source-line-no">7812</span><span id="line-7812">          LOG.info("Stopped region operation holder");</span> | 
|  | <span class="source-line-no">7813</span><span id="line-7813">        }</span> | 
|  | <span class="source-line-no">7814</span><span id="line-7814">      }</span> | 
|  | <span class="source-line-no">7815</span><span id="line-7815">    });</span> | 
|  | <span class="source-line-no">7816</span><span id="line-7816"></span> | 
|  | <span class="source-line-no">7817</span><span id="line-7817">    holder.start();</span> | 
|  | <span class="source-line-no">7818</span><span id="line-7818">    latch.await();</span> | 
|  | <span class="source-line-no">7819</span><span id="line-7819">    region.close();</span> | 
|  | <span class="source-line-no">7820</span><span id="line-7820">    region = null;</span> | 
|  | <span class="source-line-no">7821</span><span id="line-7821">    holder.join();</span> | 
|  | <span class="source-line-no">7822</span><span id="line-7822"></span> | 
|  | <span class="source-line-no">7823</span><span id="line-7823">    assertFalse("Region lock holder should not have been interrupted", holderInterrupted.get());</span> | 
|  | <span class="source-line-no">7824</span><span id="line-7824">  }</span> | 
|  | <span class="source-line-no">7825</span><span id="line-7825"></span> | 
|  | <span class="source-line-no">7826</span><span id="line-7826">  @Test</span> | 
|  | <span class="source-line-no">7827</span><span id="line-7827">  public void testRegionOnCoprocessorsChange() throws IOException {</span> | 
|  | <span class="source-line-no">7828</span><span id="line-7828">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">7829</span><span id="line-7829">    byte[][] families = { cf1 };</span> | 
|  | <span class="source-line-no">7830</span><span id="line-7830"></span> | 
|  | <span class="source-line-no">7831</span><span id="line-7831">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">7832</span><span id="line-7832">    region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">7833</span><span id="line-7833">    assertNull(region.getCoprocessorHost());</span> | 
|  | <span class="source-line-no">7834</span><span id="line-7834"></span> | 
|  | <span class="source-line-no">7835</span><span id="line-7835">    // set and verify the system coprocessors for region and user region</span> | 
|  | <span class="source-line-no">7836</span><span id="line-7836">    Configuration newConf = new Configuration(conf);</span> | 
|  | <span class="source-line-no">7837</span><span id="line-7837">    newConf.set(CoprocessorHost.REGION_COPROCESSOR_CONF_KEY, MetaTableMetrics.class.getName());</span> | 
|  | <span class="source-line-no">7838</span><span id="line-7838">    newConf.set(CoprocessorHost.USER_REGION_COPROCESSOR_CONF_KEY,</span> | 
|  | <span class="source-line-no">7839</span><span id="line-7839">      NoOpRegionCoprocessor.class.getName());</span> | 
|  | <span class="source-line-no">7840</span><span id="line-7840">    // trigger configuration change</span> | 
|  | <span class="source-line-no">7841</span><span id="line-7841">    region.onConfigurationChange(newConf);</span> | 
|  | <span class="source-line-no">7842</span><span id="line-7842">    assertTrue(region.getCoprocessorHost() != null);</span> | 
|  | <span class="source-line-no">7843</span><span id="line-7843">    Set<String> coprocessors = region.getCoprocessorHost().getCoprocessors();</span> | 
|  | <span class="source-line-no">7844</span><span id="line-7844">    assertTrue(coprocessors.size() == 2);</span> | 
|  | <span class="source-line-no">7845</span><span id="line-7845">    assertTrue(region.getCoprocessorHost().getCoprocessors()</span> | 
|  | <span class="source-line-no">7846</span><span id="line-7846">      .contains(MetaTableMetrics.class.getSimpleName()));</span> | 
|  | <span class="source-line-no">7847</span><span id="line-7847">    assertTrue(region.getCoprocessorHost().getCoprocessors()</span> | 
|  | <span class="source-line-no">7848</span><span id="line-7848">      .contains(NoOpRegionCoprocessor.class.getSimpleName()));</span> | 
|  | <span class="source-line-no">7849</span><span id="line-7849"></span> | 
|  | <span class="source-line-no">7850</span><span id="line-7850">    // remove region coprocessor and keep only user region coprocessor</span> | 
|  | <span class="source-line-no">7851</span><span id="line-7851">    newConf.unset(CoprocessorHost.REGION_COPROCESSOR_CONF_KEY);</span> | 
|  | <span class="source-line-no">7852</span><span id="line-7852">    region.onConfigurationChange(newConf);</span> | 
|  | <span class="source-line-no">7853</span><span id="line-7853">    assertTrue(region.getCoprocessorHost() != null);</span> | 
|  | <span class="source-line-no">7854</span><span id="line-7854">    coprocessors = region.getCoprocessorHost().getCoprocessors();</span> | 
|  | <span class="source-line-no">7855</span><span id="line-7855">    assertTrue(coprocessors.size() == 1);</span> | 
|  | <span class="source-line-no">7856</span><span id="line-7856">    assertTrue(region.getCoprocessorHost().getCoprocessors()</span> | 
|  | <span class="source-line-no">7857</span><span id="line-7857">      .contains(NoOpRegionCoprocessor.class.getSimpleName()));</span> | 
|  | <span class="source-line-no">7858</span><span id="line-7858">  }</span> | 
|  | <span class="source-line-no">7859</span><span id="line-7859"></span> | 
|  | <span class="source-line-no">7860</span><span id="line-7860">  @Test</span> | 
|  | <span class="source-line-no">7861</span><span id="line-7861">  public void testRegionOnCoprocessorsWithoutChange() throws IOException {</span> | 
|  | <span class="source-line-no">7862</span><span id="line-7862">    byte[] cf1 = Bytes.toBytes("CF1");</span> | 
|  | <span class="source-line-no">7863</span><span id="line-7863">    byte[][] families = { cf1 };</span> | 
|  | <span class="source-line-no">7864</span><span id="line-7864"></span> | 
|  | <span class="source-line-no">7865</span><span id="line-7865">    Configuration conf = new Configuration(CONF);</span> | 
|  | <span class="source-line-no">7866</span><span id="line-7866">    conf.set(CoprocessorHost.REGION_COPROCESSOR_CONF_KEY,</span> | 
|  | <span class="source-line-no">7867</span><span id="line-7867">      MetaTableMetrics.class.getCanonicalName());</span> | 
|  | <span class="source-line-no">7868</span><span id="line-7868">    region = initHRegion(tableName, method, conf, families);</span> | 
|  | <span class="source-line-no">7869</span><span id="line-7869">    // region service is null in unit test, we need to load the coprocessor once</span> | 
|  | <span class="source-line-no">7870</span><span id="line-7870">    region.setCoprocessorHost(new RegionCoprocessorHost(region, null, conf));</span> | 
|  | <span class="source-line-no">7871</span><span id="line-7871">    RegionCoprocessor regionCoprocessor =</span> | 
|  | <span class="source-line-no">7872</span><span id="line-7872">      region.getCoprocessorHost().findCoprocessor(MetaTableMetrics.class.getName());</span> | 
|  | <span class="source-line-no">7873</span><span id="line-7873"></span> | 
|  | <span class="source-line-no">7874</span><span id="line-7874">    // simulate when other configuration may have changed and onConfigurationChange execute once</span> | 
|  | <span class="source-line-no">7875</span><span id="line-7875">    region.onConfigurationChange(conf);</span> | 
|  | <span class="source-line-no">7876</span><span id="line-7876">    RegionCoprocessor regionCoprocessorAfterOnConfigurationChange =</span> | 
|  | <span class="source-line-no">7877</span><span id="line-7877">      region.getCoprocessorHost().findCoprocessor(MetaTableMetrics.class.getName());</span> | 
|  | <span class="source-line-no">7878</span><span id="line-7878">    assertEquals(regionCoprocessor, regionCoprocessorAfterOnConfigurationChange);</span> | 
|  | <span class="source-line-no">7879</span><span id="line-7879">  }</span> | 
|  | <span class="source-line-no">7880</span><span id="line-7880"></span> | 
|  | <span class="source-line-no">7881</span><span id="line-7881">  public static class NoOpRegionCoprocessor implements RegionCoprocessor, RegionObserver {</span> | 
|  | <span class="source-line-no">7882</span><span id="line-7882">    // a empty region coprocessor class</span> | 
|  | <span class="source-line-no">7883</span><span id="line-7883">  }</span> | 
|  | <span class="source-line-no">7884</span><span id="line-7884">}</span> | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  | </pre> | 
|  | </div> | 
|  | </main> | 
|  | </body> | 
|  | </html> |