View Javadoc
1   /*
2    *  Licensed to the Apache Software Foundation (ASF) under one
3    *  or more contributor license agreements.  See the NOTICE file
4    *  distributed with this work for additional information
5    *  regarding copyright ownership.  The ASF licenses this file
6    *  to you under the Apache License, Version 2.0 (the
7    *  "License"); you may not use this file except in compliance
8    *  with the License.  You may obtain a copy of the License at
9    *  
10   *    http://www.apache.org/licenses/LICENSE-2.0
11   *  
12   *  Unless required by applicable law or agreed to in writing,
13   *  software distributed under the License is distributed on an
14   *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   *  KIND, either express or implied.  See the License for the
16   *  specific language governing permissions and limitations
17   *  under the License. 
18   *  
19   */
20  package org.apache.directory.server.xdbm;
21  
22  
23  import java.util.Comparator;
24  
25  import org.apache.directory.api.ldap.model.cursor.Cursor;
26  import org.apache.directory.api.ldap.model.cursor.Tuple;
27  import org.apache.directory.api.ldap.model.exception.LdapException;
28  import org.apache.directory.server.core.api.partition.PartitionTxn;
29  
30  
31  /**
32   * A wrapper interface around BTree implementations used to abstract away
33   * implementation details.
34   * 
35   * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
36   */
37  public interface Table<K, V>
38  {
39      /**
40       * Gets the key comparator used by this Table: may be null if this Table
41       * was not initialized with one.
42       *
43       * @return the key comparator or null if this Table was not created with
44       * one.
45       */
46      Comparator<K> getKeyComparator();
47  
48  
49      /**
50       * Gets the value comparator used by this Table: may be null if this Table
51       * was not initialized with one.
52       *
53       * @return the value comparator or null if this Table was not created with
54       * one.
55       */
56      Comparator<V> getValueComparator();
57  
58  
59      /**
60       * Gets the name of this Table.
61       *
62       * @return the name
63       */
64      String getName();
65  
66  
67      /**
68       * Checks to see if this Table has allows for duplicate keys (a.k.a.
69       * multiple values for the same key).
70       *
71       * @return true if duplicate keys are enabled, false otherwise
72       */
73      boolean isDupsEnabled();
74  
75  
76      // ------------------------------------------------------------------------
77      // Simple Table Key/Value Assertions 
78      // ------------------------------------------------------------------------
79  
80      /**
81       * Checks to see if this table has one or more tuples with a specific key:
82       * this is exactly the same as a get call with a check to see if the
83       * returned value is null or not.
84       *
85       * @param transaction The transaction we are running in
86       * @param key the Object of the key to check for
87       * @return true if the key exists, false otherwise
88       * @throws LdapException if there is a failure to read the underlying Db
89       */
90      boolean has( PartitionTxn transaction, K key ) throws LdapException;
91  
92  
93      /**
94       * Checks to see if this table has a key with a specific value.
95       *
96       * @param transaction The transaction we are running in
97       * @param key the key to check for
98       * @param value the value to check for
99       * @return true if a record with the key and value exists, false otherwise
100      * @throws LdapException if there is a failure to read the underlying Db
101      */
102     boolean has( PartitionTxn transaction, K key, V value ) throws LdapException;
103 
104 
105     /**
106      * Checks to see if this table has a record with a key greater than or
107      * equal to the key argument.  The key argument need not exist for this
108      * call to return true.  The underlying database must sort keys based on a
109      * key comparator because this method depends on key ordering.
110      *
111      * @param transaction The transaction we are running in
112      * @param key the key to compare keys to
113      * @return true if a Tuple with a key greater than or equal to the key
114      * argument exists, false otherwise
115      * @throws LdapException if there is a failure to read the underlying Db
116      */
117     boolean hasGreaterOrEqual( PartitionTxn transaction, K key ) throws LdapException;
118 
119 
120     /**
121      * Checks to see if this table has a record with a key less than or
122      * equal to the key argument.  The key argument need not exist for this
123      * call to return true.  The underlying database must sort keys based on a
124      * key comparator because this method depends on key ordering.
125      *
126      * @param transaction The transaction we are running in
127      * @param key the key to compare keys to
128      * @return true if a Tuple with a key less than or equal to the key
129      * argument exists, false otherwise
130      * @throws LdapException if there is a failure to read the underlying Db
131      */
132     boolean hasLessOrEqual( PartitionTxn transaction, K key ) throws LdapException;
133 
134 
135     /**
136      * Checks to see if this table has a Tuple with a key equal to the key
137      * argument, yet with a value greater than or equal to the value argument
138      * provided.  The key argument <strong>MUST</strong> exist for this call
139      * to return true and the underlying Db must allow for values of duplicate
140      * keys to be sorted.  The entire basis to this method depends on the fact
141      * that tuples of the same key have values sorted according to a valid
142      * value comparator.
143      *
144      * If the table does not support duplicates then an
145      * UnsupportedOperationException is thrown.
146      *
147      * @param transaction The transaction we are running in
148      * @param key the key
149      * @param val the value to compare values to
150      * @return true if a Tuple with a key equal to the key argument and a
151      * value greater than the value argument exists, false otherwise
152      * @throws LdapException if there is a failure to read the underlying Db
153      * or if the underlying Db is not of the Btree type that allows sorted
154      * duplicate values.
155      */
156     boolean hasGreaterOrEqual( PartitionTxn transaction, K key, V val ) throws LdapException;
157 
158 
159     /**
160      * Checks to see if this table has a Tuple with a key equal to the key
161      * argument, yet with a value less than or equal to the value argument
162      * provided.  The key argument <strong>MUST</strong> exist for this call
163      * to return true and the underlying Db must allow for values of duplicate
164      * keys to be sorted.  The entire basis to this method depends on the fact
165      * that tuples of the same key have values sorted according to a valid
166      * value comparator.
167      *
168      * If the table does not support duplicates then an
169      * UnsupportedOperationException is thrown.
170      *
171      * @param transaction The transaction we are running in
172      * @param key the key
173      * @param val the value to compare values to
174      * @return true if a Tuple with a key equal to the key argument and a
175      * value less than the value argument exists, false otherwise
176      * @throws LdapException if there is a failure to read the underlying Db
177      * or if the underlying Db is not of the Btree type that allows sorted
178      * duplicate values.
179      */
180     boolean hasLessOrEqual( PartitionTxn transaction, K key, V val ) throws LdapException;
181 
182 
183     // ------------------------------------------------------------------------
184     // Table Value Accessors/Mutators
185     // ------------------------------------------------------------------------
186 
187     /**
188      * Gets the value of a record by key if the key exists.  If this Table
189      * allows duplicate keys then the first key will be returned.  If this
190      * Table sorts keys then the key will be the smallest key in the Table as
191      * specified by this Table's comparator or the default byte-wise lexical
192      * comparator.
193      *
194      * @param transaction The transaction we are running in
195      * @param key the key of the record
196      * @return the value of the record with the specified key if key exists or
197      * null if no such key exists.
198      * @throws LdapException if there is a failure to read the underlying Db
199      */
200     V get( PartitionTxn transaction, K key ) throws LdapException;
201 
202 
203     /**
204      * Puts a record into this Table.  Null is not allowed for keys or values
205      * and should result in an IllegalArgumentException.
206      *
207      * @param writeTransaction The transaction we are running in
208      * @param key the key of the record
209      * @param value the value of the record.
210      * @throws LdapException if there is a failure to read or write to the
211      * underlying Db
212      * @throws IllegalArgumentException if a null key or value is used
213      */
214     void put( PartitionTxn writeTransaction, K key, V value ) throws LdapException;
215 
216 
217     /**
218      * Removes all records with a specified key from this Table.
219      *
220      * @param writeTransaction The transaction we are running in
221      * @param key the key of the records to remove
222      * @throws LdapException if there is a failure to read or write to
223      * the underlying Db
224      */
225     void remove( PartitionTxn writeTransaction, K key ) throws LdapException;
226 
227 
228     /**
229      * Removes a single key value pair with a specified key and value from
230      * this Table.
231      *
232      * @param writeTransaction The transaction we are running in
233      * @param key the key of the record to remove
234      * @param value the value of the record to remove
235      * @throws LdapException if there is a failure to read or write to
236      * the underlying Db
237      */
238     void remove( PartitionTxn writeTransaction, K key, V value ) throws LdapException;
239 
240 
241     /**
242      * Creates a Cursor that traverses Tuples in a Table.
243      *
244      * @return a Cursor over Tuples containing the key value pairs
245      */
246     Cursor<Tuple<K, V>> cursor();
247 
248 
249     /**
250      * Creates a Cursor that traverses Table Tuples for the same key. Only
251      * Tuples with the provided key will be returned if the key exists at
252      * all.  If the key does not exist an empty Cursor is returned.  The
253      * motivation behind this method is to minimize the need for callers to
254      * actively constrain Cursor operations based on the Tuples they return
255      * to a specific key.  This Cursor is naturally limited to return only
256      * the tuples for the same key.
257      *
258      * @param partitionTxn The transaction we are running in
259      * @param key the duplicate key to return the Tuples of
260      * @return a Cursor over Tuples containing the same key
261      * @throws LdapException if there are failures accessing underlying stores
262      */
263     Cursor<Tuple<K, V>> cursor( PartitionTxn partitionTxn, K key ) throws LdapException;
264 
265 
266     /**
267      * Creates a Cursor that traverses Table values for the same key. Only
268      * Tuples with the provided key will have their values returned if the key
269      * exists at all.  If the key does not exist an empty Cursor is returned.
270      * The motivation behind this method is to minimize the need for callers
271      * to actively constrain Cursor operations to a specific key while
272      * removing overheads in creating new Tuples or population one that is
273      * reused to return key value pairs.  This Cursor is naturally limited to
274      * return only the values for the same key.
275      *
276      * @param transaction The transaction we are running in
277      * @param key the duplicate key to return the values of
278      * @return a Cursor over values of a key
279      * @throws LdapException if there are failures accessing underlying stores
280      */
281     Cursor<V> valueCursor( PartitionTxn transaction, K key ) throws LdapException;
282 
283 
284     // ------------------------------------------------------------------------
285     // Table Record Count Methods
286     // ------------------------------------------------------------------------
287 
288     /**
289      * Gets the count of the number of Tuples in this Table.
290      *
291      * @param transaction The transaction we are running in
292      * @return the number of records
293      * @throws LdapException if there is a failure to read the underlying Db
294      */
295     long count( PartitionTxn transaction ) throws LdapException;
296 
297 
298     /**
299      * Gets the count of the number of records in this Table with a specific
300      * key: returns the number of duplicates for a key.
301      *
302      * @param transaction The transaction we are running in
303      * @param key the Object key to count.
304      * @return the number of duplicate records for a key.
305      * @throws LdapException if there is a failure to read the underlying Db
306      */
307     long count( PartitionTxn transaction, K key ) throws LdapException;
308 
309 
310     /**
311      * Gets the number of records greater than or equal to a key value.  The 
312      * specific key argument provided need not exist for this call to return 
313      * a non-zero value.
314      *
315      * @param transaction The transaction we are running in
316      * @param key the key to use in comparisons
317      * @return the number of keys greater than or equal to the key
318      * @throws LdapException if there is a failure to read the underlying db
319      */
320     long greaterThanCount( PartitionTxn transaction, K key ) throws LdapException;
321 
322 
323     /**
324      * Gets the number of records less than or equal to a key value.  The 
325      * specific key argument provided need not exist for this call to return 
326      * a non-zero value.
327      *
328      * @param transaction The transaction we are running in
329      * @param key the key to use in comparisons
330      * @return the number of keys less than or equal to the key
331      * @throws LdapException if there is a failure to read the underlying db
332      */
333     long lessThanCount( PartitionTxn transaction, K key ) throws LdapException;
334 
335 
336     /**
337      * Closes the underlying Db of this Table.
338      *
339      * @param transaction The transaction we are running in
340      * @throws LdapException on any failures
341      */
342     void close( PartitionTxn transaction ) throws LdapException;
343 }