View Javadoc

1   /*
2    *
3    * Licensed to the Apache Software Foundation (ASF) under one
4    * or more contributor license agreements.  See the NOTICE file
5    * distributed with this work for additional information
6    * regarding copyright ownership.  The ASF licenses this file
7    * to you under the Apache License, Version 2.0 (the
8    * "License"); you may not use this file except in compliance
9    * with the License.  You may obtain a copy of the License at
10   *
11   *     http://www.apache.org/licenses/LICENSE-2.0
12   *
13   * Unless required by applicable law or agreed to in writing, software
14   * distributed under the License is distributed on an "AS IS" BASIS,
15   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16   * See the License for the specific language governing permissions and
17   * limitations under the License.
18   */
19  
20  package org.apache.hadoop.hbase.filter;
21  
22  import java.io.IOException;
23  import java.util.ArrayList;
24  import java.util.List;
25  
26  import org.apache.hadoop.classification.InterfaceAudience;
27  import org.apache.hadoop.classification.InterfaceStability;
28  import org.apache.hadoop.hbase.Cell;
29  import org.apache.hadoop.hbase.KeyValue;
30  import org.apache.hadoop.hbase.KeyValueUtil;
31  
32  /**
33   * Abstract base class to help you implement new Filters.  Common "ignore" or NOOP type
34   * methods can go here, helping to reduce boiler plate in an ever-expanding filter
35   * library.
36   *
37   * If you could instantiate FilterBase, it would end up being a "null" filter -
38   * that is one that never filters anything.
39   */
40  @InterfaceAudience.Private // TODO add filter limited private level
41  public abstract class FilterBase extends Filter {
42  
43    /**
44     * Filters that are purely stateless and do nothing in their reset() methods can inherit
45     * this null/empty implementation.
46     *
47     * @inheritDoc
48     */
49    @Override
50    public void reset() throws IOException {
51    }
52  
53    /**
54     * Filters that do not filter by row key can inherit this implementation that
55     * never filters anything. (ie: returns false).
56     *
57     * @inheritDoc
58     */
59    @Override
60    public boolean filterRowKey(byte[] buffer, int offset, int length) throws IOException {
61      return false;
62    }
63  
64    /**
65     * Filters that never filter all remaining can inherit this implementation that
66     * never stops the filter early.
67     *
68     * @inheritDoc
69     */
70    @Override
71    public boolean filterAllRemaining() throws IOException {
72      return false;
73    }
74  
75    /**
76     * By default no transformation takes place
77     *
78     * @inheritDoc
79     */
80    @Override
81    public Cell transformCell(Cell v) throws IOException {
82      // Old filters based off of this class will override KeyValue transform(KeyValue).
83      // Thus to maintain compatibility we need to call the old version.
84      return transform(KeyValueUtil.ensureKeyValue(v));
85    }
86  
87    /**
88     * WARNING: please to not override this method.  Instead override {@link #transformCell(Cell)}.
89     *
90     * This is for transition from 0.94 -> 0.96
91     */
92    @Override
93    @Deprecated
94    public KeyValue transform(KeyValue currentKV) throws IOException {
95      return currentKV;
96    }
97  
98    /**
99     * Filters that never filter by modifying the returned List of Cells can
100    * inherit this implementation that does nothing.
101    *
102    * @inheritDoc
103    */
104   @Override
105   public void filterRowCells(List<Cell> ignored) throws IOException {
106     // Old filters based off of this class will override KeyValue transform(KeyValue).
107     // Thus to maintain compatibility we need to call the old version.
108     List<KeyValue> kvs = new ArrayList<KeyValue>(ignored.size());
109     for (Cell c : ignored) {
110       kvs.add(KeyValueUtil.ensureKeyValue(c));
111     }
112     filterRow(kvs);
113     ignored.clear();
114     ignored.addAll(kvs);
115   }
116 
117   /**
118    * WARNING: please to not override this method.  Instead override {@link #transformCell(Cell)}.
119    *
120    * This is for transition from 0.94 -> 0.96
121    */
122   @Override
123   @Deprecated
124   public void filterRow(List<KeyValue> kvs) throws IOException {
125   }
126 
127   /**
128    * Fitlers that never filter by modifying the returned List of Cells can
129    * inherit this implementation that does nothing.
130    *
131    * @inheritDoc
132    */
133   @Override
134   public boolean hasFilterRow() {
135     return false;
136   }
137 
138   /**
139    * Filters that never filter by rows based on previously gathered state from
140    * {@link #filterKeyValue(Cell)} can inherit this implementation that
141    * never filters a row.
142    *
143    * @inheritDoc
144    */
145   @Override
146   public boolean filterRow() throws IOException {
147     return false;
148   }
149 
150   /**
151    * This method is deprecated and you should override Cell getNextKeyHint(Cell) instead.
152    */
153   @Override
154   @Deprecated
155   public KeyValue getNextKeyHint(KeyValue currentKV) throws IOException {
156     return null;
157   }
158   
159   /**
160    * Filters that are not sure which key must be next seeked to, can inherit
161    * this implementation that, by default, returns a null Cell.
162    *
163    * @inheritDoc
164    */
165   public Cell getNextCellHint(Cell currentKV) throws IOException {
166     // Old filters based off of this class will override KeyValue getNextKeyHint(KeyValue).
167     // Thus to maintain compatibility we need to call the old version.
168     return getNextKeyHint(KeyValueUtil.ensureKeyValue(currentKV));
169   }
170 
171   /**
172    * By default, we require all scan's column families to be present. Our
173    * subclasses may be more precise.
174    *
175    * @inheritDoc
176    */
177   public boolean isFamilyEssential(byte[] name) throws IOException {
178     return true;
179   }
180 
181   /**
182    * Given the filter's arguments it constructs the filter
183    * <p>
184    * @param filterArguments the filter's arguments
185    * @return constructed filter object
186    */
187   public static Filter createFilterFromArguments(ArrayList<byte []> filterArguments) {
188     throw new IllegalArgumentException("This method has not been implemented");
189   }
190 
191   /**
192    * Return filter's info for debugging and logging purpose.
193    */
194   public String toString() {
195     return this.getClass().getSimpleName();
196   }
197 
198   /**
199    * Return length 0 byte array for Filters that don't require special serialization
200    */
201   public byte[] toByteArray() throws IOException {
202     return new byte[0];
203   }
204 
205   /**
206    * Default implementation so that writers of custom filters aren't forced to implement.
207    *
208    * @param other
209    * @return true if and only if the fields of the filter that are serialized
210    * are equal to the corresponding fields in other.  Used for testing.
211    */
212   boolean areSerializedFieldsEqual(Filter other) {
213     return true;
214   }
215 }