mirror of
https://code.briarproject.org/briar/briar.git
synced 2026-02-17 05:09:53 +01:00
DatabaseComponent.generateBatch() now returns a boolean.
This allows a connection to know whether to try writing another batch immediately, or to wait for an event from the DB.
This commit is contained in:
@@ -73,17 +73,21 @@ public interface DatabaseComponent {
|
|||||||
void generateAck(ContactId c, AckWriter a) throws DbException,
|
void generateAck(ContactId c, AckWriter a) throws DbException,
|
||||||
IOException;
|
IOException;
|
||||||
|
|
||||||
/** Generates a batch of messages for the given contact. */
|
/**
|
||||||
void generateBatch(ContactId c, BatchWriter b) throws DbException,
|
* Generates a batch of messages for the given contact.
|
||||||
|
* @return True if any messages were added to tbe batch.
|
||||||
|
*/
|
||||||
|
boolean generateBatch(ContactId c, BatchWriter b) throws DbException,
|
||||||
IOException;
|
IOException;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Generates a batch of messages for the given contact from the given
|
* Generates a batch of messages for the given contact from the given
|
||||||
* collection of requested messages, and returns the IDs of any messages
|
* collection of requested messages. Any messages that were either added to
|
||||||
* that were either added to the batch, or were considered for inclusion
|
* the batch, or were considered but are no longer sendable to the contact,
|
||||||
* but are no longer sendable to the contact.
|
* are removed from the collection of requested messages before returning.
|
||||||
|
* @return True if any messages were added to the batch.
|
||||||
*/
|
*/
|
||||||
Collection<MessageId> generateBatch(ContactId c, BatchWriter b,
|
boolean generateBatch(ContactId c, BatchWriter b,
|
||||||
Collection<MessageId> requested) throws DbException, IOException;
|
Collection<MessageId> requested) throws DbException, IOException;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -408,29 +408,26 @@ DatabaseCleaner.Callback {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void generateBatch(ContactId c, BatchWriter b) throws DbException,
|
public boolean generateBatch(ContactId c, BatchWriter b) throws DbException,
|
||||||
IOException {
|
IOException {
|
||||||
contactLock.readLock().lock();
|
contactLock.readLock().lock();
|
||||||
try {
|
try {
|
||||||
if(!containsContact(c)) throw new NoSuchContactException();
|
if(!containsContact(c)) throw new NoSuchContactException();
|
||||||
messageLock.readLock().lock();
|
messageLock.readLock().lock();
|
||||||
try {
|
try {
|
||||||
Collection<MessageId> sent;
|
Collection<MessageId> sent = new ArrayList<MessageId>();
|
||||||
int bytesSent = 0;
|
|
||||||
messageStatusLock.readLock().lock();
|
messageStatusLock.readLock().lock();
|
||||||
try {
|
try {
|
||||||
subscriptionLock.readLock().lock();
|
subscriptionLock.readLock().lock();
|
||||||
try {
|
try {
|
||||||
T txn = db.startTransaction();
|
T txn = db.startTransaction();
|
||||||
try {
|
try {
|
||||||
sent = new ArrayList<MessageId>();
|
|
||||||
int capacity = b.getCapacity();
|
int capacity = b.getCapacity();
|
||||||
Collection<MessageId> sendable =
|
Collection<MessageId> sendable =
|
||||||
db.getSendableMessages(txn, c, capacity);
|
db.getSendableMessages(txn, c, capacity);
|
||||||
for(MessageId m : sendable) {
|
for(MessageId m : sendable) {
|
||||||
byte[] raw = db.getMessage(txn, m);
|
byte[] raw = db.getMessage(txn, m);
|
||||||
if(!b.writeMessage(raw)) break;
|
if(!b.writeMessage(raw)) break;
|
||||||
bytesSent += raw.length;
|
|
||||||
sent.add(m);
|
sent.add(m);
|
||||||
}
|
}
|
||||||
db.commitTransaction(txn);
|
db.commitTransaction(txn);
|
||||||
@@ -448,7 +445,7 @@ DatabaseCleaner.Callback {
|
|||||||
messageStatusLock.readLock().unlock();
|
messageStatusLock.readLock().unlock();
|
||||||
}
|
}
|
||||||
// Record the contents of the batch, unless it's empty
|
// Record the contents of the batch, unless it's empty
|
||||||
if(sent.isEmpty()) return;
|
if(sent.isEmpty()) return false;
|
||||||
BatchId id = b.finish();
|
BatchId id = b.finish();
|
||||||
messageStatusLock.writeLock().lock();
|
messageStatusLock.writeLock().lock();
|
||||||
try {
|
try {
|
||||||
@@ -456,6 +453,7 @@ DatabaseCleaner.Callback {
|
|||||||
try {
|
try {
|
||||||
db.addOutstandingBatch(txn, c, id, sent);
|
db.addOutstandingBatch(txn, c, id, sent);
|
||||||
db.commitTransaction(txn);
|
db.commitTransaction(txn);
|
||||||
|
return true;
|
||||||
} catch(DbException e) {
|
} catch(DbException e) {
|
||||||
db.abortTransaction(txn);
|
db.abortTransaction(txn);
|
||||||
throw e;
|
throw e;
|
||||||
@@ -471,24 +469,23 @@ DatabaseCleaner.Callback {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public Collection<MessageId> generateBatch(ContactId c, BatchWriter b,
|
public boolean generateBatch(ContactId c, BatchWriter b,
|
||||||
Collection<MessageId> requested) throws DbException, IOException {
|
Collection<MessageId> requested) throws DbException, IOException {
|
||||||
contactLock.readLock().lock();
|
contactLock.readLock().lock();
|
||||||
try {
|
try {
|
||||||
if(!containsContact(c)) throw new NoSuchContactException();
|
if(!containsContact(c)) throw new NoSuchContactException();
|
||||||
messageLock.readLock().lock();
|
messageLock.readLock().lock();
|
||||||
try {
|
try {
|
||||||
Collection<MessageId> sent, considered;
|
Collection<MessageId> sent = new ArrayList<MessageId>();
|
||||||
messageStatusLock.readLock().lock();
|
messageStatusLock.readLock().lock();
|
||||||
try{
|
try{
|
||||||
subscriptionLock.readLock().lock();
|
subscriptionLock.readLock().lock();
|
||||||
try {
|
try {
|
||||||
T txn = db.startTransaction();
|
T txn = db.startTransaction();
|
||||||
try {
|
try {
|
||||||
sent = new ArrayList<MessageId>();
|
Iterator<MessageId> it = requested.iterator();
|
||||||
considered = new ArrayList<MessageId>();
|
while(it.hasNext()) {
|
||||||
int bytesSent = 0;
|
MessageId m = it.next();
|
||||||
for(MessageId m : requested) {
|
|
||||||
byte[] raw = db.getMessageIfSendable(txn, c, m);
|
byte[] raw = db.getMessageIfSendable(txn, c, m);
|
||||||
// If the message is still sendable, try to add
|
// If the message is still sendable, try to add
|
||||||
// it to the batch. If the batch is full, don't
|
// it to the batch. If the batch is full, don't
|
||||||
@@ -496,10 +493,9 @@ DatabaseCleaner.Callback {
|
|||||||
// try to add any further messages.
|
// try to add any further messages.
|
||||||
if(raw != null) {
|
if(raw != null) {
|
||||||
if(!b.writeMessage(raw)) break;
|
if(!b.writeMessage(raw)) break;
|
||||||
bytesSent += raw.length;
|
|
||||||
sent.add(m);
|
sent.add(m);
|
||||||
}
|
}
|
||||||
considered.add(m);
|
it.remove();
|
||||||
}
|
}
|
||||||
db.commitTransaction(txn);
|
db.commitTransaction(txn);
|
||||||
} catch(DbException e) {
|
} catch(DbException e) {
|
||||||
@@ -516,7 +512,7 @@ DatabaseCleaner.Callback {
|
|||||||
messageStatusLock.readLock().unlock();
|
messageStatusLock.readLock().unlock();
|
||||||
}
|
}
|
||||||
// Record the contents of the batch, unless it's empty
|
// Record the contents of the batch, unless it's empty
|
||||||
if(sent.isEmpty()) return considered;
|
if(sent.isEmpty()) return false;
|
||||||
BatchId id = b.finish();
|
BatchId id = b.finish();
|
||||||
messageStatusLock.writeLock().lock();
|
messageStatusLock.writeLock().lock();
|
||||||
try {
|
try {
|
||||||
@@ -524,7 +520,7 @@ DatabaseCleaner.Callback {
|
|||||||
try {
|
try {
|
||||||
db.addOutstandingBatch(txn, c, id, sent);
|
db.addOutstandingBatch(txn, c, id, sent);
|
||||||
db.commitTransaction(txn);
|
db.commitTransaction(txn);
|
||||||
return considered;
|
return true;
|
||||||
} catch(DbException e) {
|
} catch(DbException e) {
|
||||||
db.abortTransaction(txn);
|
db.abortTransaction(txn);
|
||||||
throw e;
|
throw e;
|
||||||
|
|||||||
@@ -41,8 +41,8 @@ class BatchWriterImpl implements BatchWriter {
|
|||||||
started = true;
|
started = true;
|
||||||
}
|
}
|
||||||
// Allow one byte for the list end tag
|
// Allow one byte for the list end tag
|
||||||
int capacity = ProtocolConstants.MAX_PACKET_LENGTH
|
int capacity =
|
||||||
- (int) w.getBytesWritten() - 1;
|
ProtocolConstants.MAX_PACKET_LENGTH - (int) w.getBytesWritten() - 1;
|
||||||
if(capacity < message.length) return false;
|
if(capacity < message.length) return false;
|
||||||
// Bypass the writer and write each raw message directly
|
// Bypass the writer and write each raw message directly
|
||||||
out.write(message);
|
out.write(message);
|
||||||
|
|||||||
Reference in New Issue
Block a user