|
||||||||||
PREV CLASS NEXT CLASS | FRAMES NO FRAMES | |||||||||
SUMMARY: NESTED | FIELD | CONSTR | METHOD | DETAIL: FIELD | CONSTR | METHOD |
java.lang.Object ccs.beetree.BeeTree
public final class BeeTree
A BeeTree provides storage, access and indexing to a collection of Binary
Large OBjects (blobs) gathered together in a single disk file (which may
have any name or extension). These blobs are indexed by a single,
arbitrary-length key String. Everything in the file, excluding a small
amount of blob-length information which must be stored in a more weakly
obscured form, and 32 bytes of serial-ID information at the start of the
file used for locking, is encrypted. A "password" (an arbitrary-length
byte string) is supplied for this purpose. If the password is zero-length
then a null cipher is used, otherwise a real cipher is used: currently
AES-CBC-HMAC-SHA1 with 128- to 256-bit keys. Alternatively, each
blob may supply its own Cipher
object to handle its own
encryption.
This is a multi-user / multithread-safe persister. The locking system is robust but can be defeated: in particular, access from a remote host (e.g. via mapped network drives under windows) will hose it, and your data as well. Many BeeTree objects in many threads in many VM's can share a disk file.
The file managed using a BeeTree consists of a set of
BeeObject
s. The BeeObject
provides some basic
services required to serialise the object, and some data fields which the
BeeTree uses to keep track of things. Objects which you wish to store in the
BeeTree must extend BeeObject
.
A BeeTree which has lots of deletes on it will become fragmented. This will
reduce performance and will make the file excessively large. When the app
has time (time enough to read and write every blob in the store - could
be a while!) it should compact it. This is achieved using a
BeeTreeCompactor
.
Keys must be valid UTF strings. However, this format covers a multitude of sins, so this restriction should not be problematic.
The BeeTree maintains a "current object" pointer, which is set by find and used by prev, next and match. Some other operations affect the pointer, as described in the per-method documentation. If an operation throws an exception, the current-pointer status becomes undefined.
The locking system requires a unique file ID for every BeeTree disk file. However, it can happen that two files end up with the same "unique" file ID, by chance. If this happens, the two lock each other, reducing efficiency but not risking data corruption.
Most applications will prefer to use CDBeeTree
instead, which
provides richer functionality. CDBeeTree
uses BeeTree internally.
BeeObject
,
CDBeeTree
Field Summary | |
---|---|
static int |
CIPHERAES
Cipher version constant. |
static int |
CIPHERBLOWFISH
Cipher version constant. |
static int |
CIPHERFISHY
Cipher version constant. |
static int |
CIPHERSTILLFISHY
Cipher version constant. |
static long |
LIMIT
The maximum size of a BeeObject; (2^62 - epsilon) bytes. |
Constructor Summary | |
---|---|
BeeTree(java.io.File f,
byte[] password,
boolean create)
Create a new BeeTree indexing the supplied File. |
|
BeeTree(java.io.File f,
byte[] password,
boolean check,
boolean create)
Deprecated. The extra consistency checks are now implemented as assertions. To enable these checks, enable assertions with the -ea VM
parameter. |
Method Summary | |
---|---|
void |
backup(java.io.File tgt)
Backs up the beetree to the supplied file, in an safe way. |
static void |
changeFileID(java.io.File btf)
Change the file ID of a BeeTree. |
void |
changeKey(BeeObject bo,
java.lang.String newkey)
Changes the key of the supplied object without changing its data. |
void |
delete(BeeObject bo)
Deletes the supplied object from the BeeTree. |
void |
eviscerate(boolean isWipe)
Remove every single object from the BeeTree in one fell swoop. |
boolean |
findExact(BeeObject bo)
Finds an object from an exact key. |
boolean |
findExactKey(BeeObject bo)
As findExact , except that the object is not unmarshalled. |
boolean |
findFirst(BeeObject bo)
Finds an object from a partial key. |
boolean |
findFirstKey(BeeObject bo)
As findFirst , except that the object is not unmarshalled. |
Cipher |
getCipherFor(byte[] password)
Returns a configured Cipher corresponding to the current cipher version and the supplied password. |
Cipher |
getCipherInstance()
Returns a new, uninitialised instance of the Cipher corresponding to the current Cipher version. |
int |
getCipherVersion()
Returns the current cipher version. |
java.io.File |
getContainingFile()
Returns the File containing the beetree. |
long |
getFileID()
Returns the file ID of the beetree. |
Cipher |
getNullCipherInstance()
Returns a new, uninitialised instance of the Cipher the tree uses when it's not actually encrypted. |
byte[] |
getPassword()
returns a copy of the current password, if any. |
long |
getTotalFree()
Returns the total amount of free space inside the BeeTree. |
int |
getTotalSpaces()
Returns the number of free spaces inside the BeeTree. |
void |
insert(BeeObject bo)
Inserts an object into the BeeTree. |
void |
lock()
Acquires a hold on the BeeTree's nestable (re-entrant) mutex. |
boolean |
next(BeeObject bo)
Find the next object. |
boolean |
nextKey(BeeObject bo)
As next , except the BeeObject is not unmarshalled. |
boolean |
nextMatch(BeeObject bo)
Find the next object which matches the partial key from the most recent findFirst . |
boolean |
nextMatchKey(BeeObject bo)
As nextMatch , except that the object is not unmarshalled. |
boolean |
prev(BeeObject bo)
Find the previous object, as next . |
boolean |
prevKey(BeeObject bo)
Find the previous object but don't unmarshal, as nextKey . |
void |
restore(java.io.File src)
Deprecated. Considered dodgy! This has not been used in anger and so has not accrued the same level of confidence as everything else. Most applications won't need to do this except during disaster recovery; under these circumstances it's much safer to stop the application, restore manually and then restart the application. |
static void |
setDeadlockTimeoutMillis(long millis)
Sets a deadlock timeout, in milliseconds. |
void |
setNodeCacheSize(int size)
Changes the size of the node cache. |
void |
setThreshold(int threshold)
Changes the swapping threshold for temporary space when marshalling. |
void |
threadLock()
Lock the beetree file so that only this thread in this VM can use it; all other threads in all other VMs are locked out. |
void |
threadLockRO()
As threadLock , but only acquires an RO lock. |
void |
threadUnlock()
Release the beetree from your previously-applied thread lock. |
void |
threadUnlockIfHolder()
Release the beetree from a previously-applied thread lock, iff the current thread has one to release. |
void |
threadUnlockRO()
Release the beetree from your previously-applied RO thread lock. |
void |
threadUnlockROIfHolder()
Release the beetree from a previously-applied thread lock, iff the current thread has one to release. |
void |
unlock()
Releases a hold obtained by lock . |
void |
update(BeeObject bo)
Updates the object, which is already in the BeeTree. |
Methods inherited from class java.lang.Object |
---|
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait |
Field Detail |
---|
public static final int CIPHERFISHY
public static final int CIPHERSTILLFISHY
public static final int CIPHERBLOWFISH
public static final int CIPHERAES
public static final long LIMIT
Constructor Detail |
---|
public BeeTree(java.io.File f, byte[] password, boolean check, boolean create) throws java.io.IOException
-ea
VM
parameter.
check
is true, extra consistency checks will be made, and ConsistencyException thrown if
they fail (this would probably indicate a BeeTree internal fault or
disk-file corruption).
f
- The disk file to contain the BeeTree.password
- The password for the BeeTree, supplied as a set of bytes. If
your app is using a string, think about character encoding carefully. Supply
null to not use encryption.check
- Ignored.create
- If true, create a new db file. If the file exists, it will be
truncated to length zero (thus preserving any file permissions).
If false, read in details from an existing db file, throwing
an exception if the file isn't valid.
java.io.IOException
public BeeTree(java.io.File f, byte[] password, boolean create) throws java.io.IOException
-ea
parameter to the VM.
f
- The disk file to contain the BeeTree.password
- The password for the BeeTree, supplied as a set of bytes. If
your app is using a string, think about character encoding carefully. Supply
null to not use encryption.create
- If true, create a new db file. If the file exists, it will be
truncated to length zero (thus preserving any file permissions).
If false, read in details from an existing db file, throwing
an exception if the file isn't valid.
java.io.IOException
Method Detail |
---|
public void insert(BeeObject bo) throws ConsistencyException, java.io.IOException, BeeException
bo
- The object to insert
ConsistencyException
java.io.IOException
BeeException
public void update(BeeObject bo) throws java.io.IOException
bo
- The object to update.
java.io.IOException
public void changeKey(BeeObject bo, java.lang.String newkey) throws java.io.IOException
update
, which changes the data
without changing the key. Before invoking the method, set the BeeObject to
return its old (current) key. The method will invoke setKey
on
the BeeObject to change the key during the method. Since the object is not
marshalled or unmarshalled during the process, niether preMarshal
or preUnmarshal
will be invoked on it by this method.
bo
- The BeeObject whose key is to be changed. On entry, its key should
be set to the old (current) value.newkey
- The key to change to.
java.io.IOException
public void delete(BeeObject bo) throws ConsistencyException, BeeException, java.io.IOException
bo
- the object to delete.
ConsistencyException
BeeException
java.io.IOException
public boolean findFirst(BeeObject bo) throws java.io.IOException
bo.getKey
.
The full object corresponding to the first key matching the partial key
is returned, together with the full key. After a findFirst
,
next
and prev
will find the next and previous records
(and can be applied iteratively).
If the method returns false, the key will not have changed. (bo.setKey
will not have been called.)
bo
- a BeeObject
containing the partial key.
java.io.IOException
public boolean findFirstKey(BeeObject bo) throws java.io.IOException
findFirst
, except that the object is not unmarshalled.
For finding keys, when not concerned with the objects.
bo
- a BeeObject
containing the partial key.
java.io.IOException
public boolean findExact(BeeObject bo) throws java.io.IOException
bo.getKey
.
This saves you from having to check that the key you get is not a
superset of the key you wanted. It is also fractionally quicker than
findFirst
.
After a findExact
, next
and prev
will
find the next and previous records. (and can be applied iteratively).
If the method returns false, the key will not have changed.
(bo.setKey
will not have been called.)
bo
- a BeeObject
containing the key.
java.io.IOException
public boolean findExactKey(BeeObject bo) throws java.io.IOException
findExact
, except that the object is not unmarshalled.
For finding keys, when not concerned with the objects.
bo
- a BeeObject
containing the key.
java.io.IOException
public boolean next(BeeObject bo) throws java.io.IOException
find
. If the search fails
(as in 'returns false', not as in 'throws an exception') the current-record
pointer remains unchanged.
bo
- a blank BeeObject.
java.io.IOException
public boolean nextKey(BeeObject bo) throws java.io.IOException
next
, except the BeeObject is not unmarshalled. For finding
keys, when not concerned with the objects they index.
bo
- a blank BeeObject.
java.io.IOException
public boolean nextMatch(BeeObject bo) throws java.io.IOException
findFirst
. Returns as next. If the operation returns false, the
current-record pointer remains unchanged. There is no prevMatch because the
process is asymmetrical - prevMatch would be twinned with findLast, and that
is not implemented either. (It could be, were there enough demand).
bo
- a blank BeeObject.
java.io.IOException
public boolean nextMatchKey(BeeObject bo) throws java.io.IOException
nextMatch
, except that the object is not unmarshalled.
bo
- a blank BeeObject.
java.io.IOException
public boolean prev(BeeObject bo) throws java.io.IOException
next
.
bo
- a blank BeeObject.
java.io.IOException
public boolean prevKey(BeeObject bo) throws java.io.IOException
nextKey
.
bo
- a blank BeeObject.
java.io.IOException
public void threadLock() throws java.io.IOException
Lock the beetree file so that only this thread in this VM can use it; all other threads in all other VMs are locked out. This guarantees that a set of operations on the beetree are atomic; this is necessary (but not sufficient, although it'll do if you don't need rollback) to comprise a transaction. For the sake of efficiency, apps should try to complete such atomicised operations quickly. The disk file is open while the lock holds, increasing its vulnerability in the event of a system failure.
Apps must ensure that the lock is released; generally this is best done using a try...finally block.
As well as operations that must be atomic, it also improves efficiency to thread-lock the beetree where several operations will be carried out on the same beetree in quick succession.
This call will block until such a lock can be obtained.
Calls can safely be nested - one unlock for every lock.
java.io.IOException
public void threadUnlock() throws java.io.IOException
java.io.IOException
public void threadLockRO() throws java.io.IOException
threadLock
, but only acquires an RO lock. Improves
multithread concurrency, but you do need to make sure that your transaction
doesn't do any write operations. Don't nest RO and RW thread locks.
java.io.IOException
public void threadUnlockRO() throws java.io.IOException
java.io.IOException
public void threadUnlockIfHolder() throws java.io.IOException
java.io.IOException
public void threadUnlockROIfHolder() throws java.io.IOException
java.io.IOException
public void eviscerate(boolean isWipe) throws java.io.IOException
isWipe
- Whether to attempt to wipe the underlying file.
The wipe is a rather limited single-pass wipe; for greater security you should
use BeeTreeCompactor
with a multipass FileKiller mode, instead of this
method.
java.io.IOException
public long getTotalFree() throws ConsistencyException
Note:This is only indicative, and may be inaccurate in the presence
of concurrent access and immediately after compaction. If you need to ensure
an accurate result, thread-lock the beetree and do any operation on it
(e.g. findExact
) immediately before calling this method.
ConsistencyException
public int getTotalSpaces() throws ConsistencyException
Note:This is only indicative, and may be inaccurate in the presence
of concurrent access and immediately after compaction. If you need to ensure
an accurate result, thread-lock the beetree and do any operation on it
(e.g. findExact
) immediately before calling this method.
ConsistencyException
- If the BeeTree is invalid.public void setThreshold(int threshold)
threshold
- The threshold.public java.io.File getContainingFile()
public byte[] getPassword()
public int getCipherVersion()
public Cipher getCipherInstance()
public Cipher getNullCipherInstance()
public Cipher getCipherFor(byte[] password) throws java.io.IOException
java.io.IOException
public void setNodeCacheSize(int size)
size
- The node cache size.public long getFileID()
public void backup(java.io.File tgt) throws java.io.IOException
tgt
- The file to backup to.
java.io.IOException
- if there was a problem during the process. The source
file (i.e. the "live" database) will not be affected. The state of the
target file following an exception is undefined.public void restore(java.io.File src) throws java.io.IOException
backup
, in a safe way. NOTE:
it is unsafe to attempt this manually even in a single-threaded application.
Such an attempt will cause data corruption. Use the tool!
NOTE: mayh not be safe with CDBeeTrees, especially if the
set structure of the version to be restored is different from that being
overwritten.
src
- The source to restore from.
java.io.IOException
- If the restore failed. If this happens, then the backup
will be OK, but the beetree will be corrupt. Close all applications that might
be using the beetree and then copy the backup over the "live" beetree file using
the operating system facility.public static void changeFileID(java.io.File btf) throws java.io.IOException
btf
- The file containing a beetree, associated with no BeeTree object,
whose file ID is to be changed.
java.io.IOException
- if the operation fails.public static void setDeadlockTimeoutMillis(long millis)
BeeLine
s to detect potential deadlocks at the
initial test stage: BeeLine provides fault-evidence which allows you to
prevent the fault getting into production code, whereas this only provides
fault recovery. A gram of prevention is better than a kilo of cure!
DeadlockException
is thrown.
public void lock() throws DeadlockException
threadLock
instead. Don't call this unless you know what you're
doing.
DeadlockException
public void unlock()
lock
. Same comments apply as for
lock
.
|
||||||||||
PREV CLASS NEXT CLASS | FRAMES NO FRAMES | |||||||||
SUMMARY: NESTED | FIELD | CONSTR | METHOD | DETAIL: FIELD | CONSTR | METHOD |