001/* 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018package org.apache.hadoop.hbase.client; 019 020import java.io.Closeable; 021import java.io.IOException; 022import java.util.Collections; 023import java.util.List; 024import java.util.Map; 025import org.apache.hadoop.conf.Configuration; 026import org.apache.hadoop.hbase.TableName; 027import org.apache.yetus.audience.InterfaceAudience; 028 029/** 030 * <p> 031 * Used to communicate with a single HBase table similar to {@link Table} but meant for batched, 032 * asynchronous puts. Obtain an instance from a {@link Connection} and call {@link #close()} 033 * afterwards. Customizations can be applied to the {@code BufferedMutator} via the 034 * {@link BufferedMutatorParams}. 035 * </p> 036 * <p> 037 * Exception handling with asynchronously via the {@link BufferedMutator.ExceptionListener}. The 038 * default implementation is to throw the exception upon receipt. This behavior can be overridden 039 * with a custom implementation, provided as a parameter with 040 * {@link BufferedMutatorParams#listener(BufferedMutator.ExceptionListener)}. 041 * </p> 042 * <p> 043 * Map/Reduce jobs are good use cases for using {@code BufferedMutator}. Map/reduce jobs benefit 044 * from batching, but have no natural flush point. {@code BufferedMutator} receives the puts from 045 * the M/R job and will batch puts based on some heuristic, such as the accumulated size of the 046 * puts, and submit batches of puts asynchronously so that the M/R logic can continue without 047 * interruption. 048 * </p> 049 * <p> 050 * {@code BufferedMutator} can also be used on more exotic circumstances. Map/Reduce batch jobs will 051 * have a single {@code BufferedMutator} per thread. A single {@code BufferedMutator} can also be 052 * effectively used in high volume online systems to batch puts, with the caveat that extreme 053 * circumstances, such as JVM or machine failure, may cause some data loss. 054 * </p> 055 * <p> 056 * NOTE: This class replaces the functionality that used to be available via 057 * HTable#setAutoFlush(boolean) set to {@code false}. 058 * </p> 059 * <p> 060 * See also the {@code BufferedMutatorExample} in the hbase-examples module. 061 * </p> 062 * @see ConnectionFactory 063 * @see Connection 064 * @since 1.0.0 065 */ 066@InterfaceAudience.Public 067public interface BufferedMutator extends Closeable { 068 /** 069 * Key to use setting non-default BufferedMutator implementation in Configuration. 070 */ 071 String CLASSNAME_KEY = "hbase.client.bufferedmutator.classname"; 072 073 /** 074 * Having the timer tick run more often that once every 100ms is needless and will probably cause 075 * too many timer events firing having a negative impact on performance. 076 */ 077 long MIN_WRITE_BUFFER_PERIODIC_FLUSH_TIMERTICK_MS = 100; 078 079 /** 080 * Gets the fully qualified table name instance of the table that this BufferedMutator writes to. 081 */ 082 TableName getName(); 083 084 /** 085 * Returns the {@link org.apache.hadoop.conf.Configuration} object used by this instance. 086 * <p> 087 * The reference returned is not a copy, so any change made to it will affect this instance. 088 */ 089 Configuration getConfiguration(); 090 091 /** 092 * Sends a {@link Mutation} to the table. The mutations will be buffered and sent over the wire as 093 * part of a batch. Currently only supports {@link Put} and {@link Delete} mutations. 094 * @param mutation The data to send. 095 * @throws IOException if a remote or network exception occurs. 096 */ 097 void mutate(Mutation mutation) throws IOException; 098 099 /** 100 * Send some {@link Mutation}s to the table. The mutations will be buffered and sent over the wire 101 * as part of a batch. There is no guarantee of sending entire content of {@code mutations} in a 102 * single batch; it will be broken up according to the write buffer capacity. 103 * @param mutations The data to send. 104 * @throws IOException if a remote or network exception occurs. 105 */ 106 void mutate(List<? extends Mutation> mutations) throws IOException; 107 108 /** 109 * Performs a {@link #flush()} and releases any resources held. 110 * @throws IOException if a remote or network exception occurs. 111 */ 112 @Override 113 void close() throws IOException; 114 115 /** 116 * Executes all the buffered, asynchronous {@link Mutation} operations and waits until they are 117 * done. 118 * @throws IOException if a remote or network exception occurs. 119 */ 120 void flush() throws IOException; 121 122 /** 123 * Sets the maximum time before the buffer is automatically flushed checking once per second. 124 * @param timeoutMs The maximum number of milliseconds how long records may be buffered before 125 * they are flushed. Set to 0 to disable. 126 */ 127 default void setWriteBufferPeriodicFlush(long timeoutMs) { 128 setWriteBufferPeriodicFlush(timeoutMs, 1000L); 129 } 130 131 /** 132 * Sets the maximum time before the buffer is automatically flushed. 133 * @param timeoutMs The maximum number of milliseconds how long records may be buffered before 134 * they are flushed. Set to 0 to disable. 135 * @param timerTickMs The number of milliseconds between each check if the timeout has been 136 * exceeded. Must be 100ms (as defined in 137 * {@link #MIN_WRITE_BUFFER_PERIODIC_FLUSH_TIMERTICK_MS}) or larger to avoid 138 * performance problems. 139 */ 140 default void setWriteBufferPeriodicFlush(long timeoutMs, long timerTickMs) { 141 throw new UnsupportedOperationException( 142 "The BufferedMutator::setWriteBufferPeriodicFlush has not been implemented"); 143 } 144 145 /** 146 * Disable periodic flushing of the write buffer. 147 */ 148 default void disableWriteBufferPeriodicFlush() { 149 setWriteBufferPeriodicFlush(0, MIN_WRITE_BUFFER_PERIODIC_FLUSH_TIMERTICK_MS); 150 } 151 152 /** 153 * Returns the current periodic flush timeout value in milliseconds. 154 * @return The maximum number of milliseconds how long records may be buffered before they are 155 * flushed. The value 0 means this is disabled. 156 */ 157 default long getWriteBufferPeriodicFlushTimeoutMs() { 158 throw new UnsupportedOperationException( 159 "The BufferedMutator::getWriteBufferPeriodicFlushTimeoutMs has not been implemented"); 160 } 161 162 /** 163 * Returns the current periodic flush timertick interval in milliseconds. 164 * @return The number of milliseconds between each check if the timeout has been exceeded. This 165 * value only has a real meaning if the timeout has been set to > 0 166 */ 167 default long getWriteBufferPeriodicFlushTimerTickMs() { 168 throw new UnsupportedOperationException( 169 "The BufferedMutator::getWriteBufferPeriodicFlushTimerTickMs has not been implemented"); 170 } 171 172 /** 173 * Returns the maximum size in bytes of the write buffer for this HTable. 174 * <p> 175 * The default value comes from the configuration parameter {@code hbase.client.write.buffer}. 176 * @return The size of the write buffer in bytes. 177 */ 178 default long getWriteBufferSize() { 179 throw new UnsupportedOperationException( 180 "The BufferedMutator::getWriteBufferSize has not been implemented"); 181 } 182 183 /** 184 * Set rpc timeout for this mutator instance 185 */ 186 default void setRpcTimeout(int timeout) { 187 throw new UnsupportedOperationException( 188 "The BufferedMutator::setRpcTimeout has not been implemented"); 189 } 190 191 /** 192 * Set operation timeout for this mutator instance 193 */ 194 default void setOperationTimeout(int timeout) { 195 throw new UnsupportedOperationException( 196 "The BufferedMutator::setOperationTimeout has not been implemented"); 197 } 198 199 /** 200 * Returns the rpc request attributes. 201 */ 202 default Map<String, byte[]> getRequestAttributes() { 203 return Collections.emptyMap(); 204 } 205 206 /** 207 * The maximum number of mutations that this buffered mutator will buffer before flushing them 208 */ 209 default int getMaxMutations() { 210 throw new UnsupportedOperationException( 211 "The BufferedMutator::getMaxMutations has not been implemented"); 212 } 213 214 /** 215 * Listens for asynchronous exceptions on a {@link BufferedMutator}. 216 */ 217 @InterfaceAudience.Public 218 interface ExceptionListener { 219 public void onException(RetriesExhaustedWithDetailsException exception, BufferedMutator mutator) 220 throws RetriesExhaustedWithDetailsException; 221 } 222}