mirror of
https://code.briarproject.org/briar/briar.git
synced 2026-02-14 19:59:05 +01:00
Nudge the database API in the direction of sanity.
This commit is contained in:
@@ -170,6 +170,13 @@ interface Database<T> {
|
||||
*/
|
||||
Collection<BatchId> getBatchesToAck(T txn, ContactId c) throws DbException;
|
||||
|
||||
/**
|
||||
* Returns the configuration for the given transport.
|
||||
* <p>
|
||||
* Locking: transports read.
|
||||
*/
|
||||
TransportConfig getConfig(T txn, TransportId t) throws DbException;
|
||||
|
||||
/**
|
||||
* Allocates and returns a connection number for the given contact and
|
||||
* transport.
|
||||
@@ -280,12 +287,12 @@ interface Database<T> {
|
||||
Rating getRating(T txn, AuthorId a) throws DbException;
|
||||
|
||||
/**
|
||||
* Returns all remote transport properties.
|
||||
* Returns all remote properties for the given transport.
|
||||
* <p>
|
||||
* Locking: contacts read, transports read.
|
||||
*/
|
||||
Map<TransportId, Map<ContactId, TransportProperties>>
|
||||
getRemoteTransports(T txn) throws DbException;
|
||||
Map<ContactId, TransportProperties> getRemoteProperties(T txn,
|
||||
TransportId t) throws DbException;
|
||||
|
||||
/**
|
||||
* Returns the sendability score of the given group message.
|
||||
@@ -335,13 +342,6 @@ interface Database<T> {
|
||||
*/
|
||||
Collection<Group> getSubscriptions(T txn, ContactId c) throws DbException;
|
||||
|
||||
/**
|
||||
* Returns the configuration for the given transport.
|
||||
* <p>
|
||||
* Locking: transports read.
|
||||
*/
|
||||
TransportConfig getTransportConfig(T txn, TransportId t) throws DbException;
|
||||
|
||||
/**
|
||||
* Returns the contacts to which the given group is visible.
|
||||
* <p>
|
||||
@@ -414,6 +414,15 @@ interface Database<T> {
|
||||
*/
|
||||
void removeSubscription(T txn, GroupId g) throws DbException;
|
||||
|
||||
/**
|
||||
* Sets the configuration for the given transport, replacing any existing
|
||||
* configuration for that transport.
|
||||
* <p>
|
||||
* Locking: transports write.
|
||||
*/
|
||||
void setConfig(T txn, TransportId t, TransportConfig config)
|
||||
throws DbException;
|
||||
|
||||
/**
|
||||
* Sets the connection reordering window for the given contact and
|
||||
* transport.
|
||||
@@ -423,6 +432,15 @@ interface Database<T> {
|
||||
void setConnectionWindow(T txn, ContactId c, TransportId t,
|
||||
ConnectionWindow w) throws DbException;
|
||||
|
||||
/**
|
||||
* Sets the local transport properties for the given transport, replacing
|
||||
* any existing properties for that transport.
|
||||
* <p>
|
||||
* Locking: transports write.
|
||||
*/
|
||||
void setLocalProperties(T txn, TransportId t, TransportProperties p)
|
||||
throws DbException;
|
||||
|
||||
/**
|
||||
* Sets the user's rating for the given author.
|
||||
* <p>
|
||||
@@ -475,24 +493,6 @@ interface Database<T> {
|
||||
void setSubscriptionTimestamp(T txn, ContactId c, long timestamp)
|
||||
throws DbException;
|
||||
|
||||
/**
|
||||
* Sets the configuration for the given transport, replacing any existing
|
||||
* configuration for that transport.
|
||||
* <p>
|
||||
* Locking: transports write.
|
||||
*/
|
||||
void setTransportConfig(T txn, TransportId t, TransportConfig config)
|
||||
throws DbException;
|
||||
|
||||
/**
|
||||
* Sets the transport properties for the given transport, replacing any
|
||||
* existing properties for that transport.
|
||||
* <p>
|
||||
* Locking: transports write.
|
||||
*/
|
||||
void setTransportProperties(T txn, TransportId t,
|
||||
TransportProperties properties) throws DbException;
|
||||
|
||||
/**
|
||||
* Sets the transport properties for the given contact, replacing any
|
||||
* existing properties unless the existing properties have a newer
|
||||
|
||||
@@ -636,6 +636,23 @@ DatabaseCleaner.Callback {
|
||||
LOG.fine("Added " + transports.size() + " transports to update");
|
||||
}
|
||||
|
||||
public TransportConfig getConfig(TransportId t) throws DbException {
|
||||
transportLock.readLock().lock();
|
||||
try {
|
||||
T txn = db.startTransaction();
|
||||
try {
|
||||
TransportConfig config = db.getConfig(txn, t);
|
||||
db.commitTransaction(txn);
|
||||
return config;
|
||||
} catch(DbException e) {
|
||||
db.abortTransaction(txn);
|
||||
throw e;
|
||||
}
|
||||
} finally {
|
||||
transportLock.readLock().unlock();
|
||||
}
|
||||
}
|
||||
|
||||
public long getConnectionNumber(ContactId c, TransportId t)
|
||||
throws DbException {
|
||||
contactLock.readLock().lock();
|
||||
@@ -737,18 +754,18 @@ DatabaseCleaner.Callback {
|
||||
}
|
||||
}
|
||||
|
||||
public Map<TransportId, Map<ContactId, TransportProperties>>
|
||||
getRemoteTransports() throws DbException {
|
||||
public Map<ContactId, TransportProperties> getRemoteProperties(
|
||||
TransportId t) throws DbException {
|
||||
contactLock.readLock().lock();
|
||||
try {
|
||||
transportLock.readLock().lock();
|
||||
try {
|
||||
T txn = db.startTransaction();
|
||||
try {
|
||||
Map<TransportId, Map<ContactId, TransportProperties>>
|
||||
transports = db.getRemoteTransports(txn);
|
||||
Map<ContactId, TransportProperties> properties =
|
||||
db.getRemoteProperties(txn, t);
|
||||
db.commitTransaction(txn);
|
||||
return transports;
|
||||
return properties;
|
||||
} catch(DbException e) {
|
||||
db.abortTransaction(txn);
|
||||
throw e;
|
||||
@@ -796,24 +813,6 @@ DatabaseCleaner.Callback {
|
||||
}
|
||||
}
|
||||
|
||||
public TransportConfig getTransportConfig(TransportId t)
|
||||
throws DbException {
|
||||
transportLock.readLock().lock();
|
||||
try {
|
||||
T txn = db.startTransaction();
|
||||
try {
|
||||
TransportConfig config = db.getTransportConfig(txn, t);
|
||||
db.commitTransaction(txn);
|
||||
return config;
|
||||
} catch(DbException e) {
|
||||
db.abortTransaction(txn);
|
||||
throw e;
|
||||
}
|
||||
} finally {
|
||||
transportLock.readLock().unlock();
|
||||
}
|
||||
}
|
||||
|
||||
public Collection<ContactId> getVisibility(GroupId g) throws DbException {
|
||||
contactLock.readLock().lock();
|
||||
try {
|
||||
@@ -1105,6 +1104,30 @@ DatabaseCleaner.Callback {
|
||||
callListeners(Event.CONTACTS_UPDATED);
|
||||
}
|
||||
|
||||
public void setConfig(TransportId t, TransportConfig config)
|
||||
throws DbException {
|
||||
boolean changed = false;
|
||||
transportLock.writeLock().lock();
|
||||
try {
|
||||
T txn = db.startTransaction();
|
||||
try {
|
||||
TransportConfig old = db.getConfig(txn, t);
|
||||
if(!config.equals(old)) {
|
||||
db.setConfig(txn, t, config);
|
||||
changed = true;
|
||||
}
|
||||
db.commitTransaction(txn);
|
||||
} catch(DbException e) {
|
||||
db.abortTransaction(txn);
|
||||
throw e;
|
||||
}
|
||||
} finally {
|
||||
transportLock.writeLock().unlock();
|
||||
}
|
||||
// Call the listeners outside the lock
|
||||
if(changed) callListeners(Event.TRANSPORTS_UPDATED);
|
||||
}
|
||||
|
||||
public void setConnectionWindow(ContactId c, TransportId t,
|
||||
ConnectionWindow w) throws DbException {
|
||||
contactLock.readLock().lock();
|
||||
@@ -1127,6 +1150,30 @@ DatabaseCleaner.Callback {
|
||||
}
|
||||
}
|
||||
|
||||
public void setLocalProperties(TransportId t,
|
||||
TransportProperties properties) throws DbException {
|
||||
boolean changed = false;
|
||||
transportLock.writeLock().lock();
|
||||
try {
|
||||
T txn = db.startTransaction();
|
||||
try {
|
||||
TransportProperties old = db.getLocalTransports(txn).get(t);
|
||||
if(!properties.equals(old)) {
|
||||
db.setLocalProperties(txn, t, properties);
|
||||
changed = true;
|
||||
}
|
||||
db.commitTransaction(txn);
|
||||
} catch(DbException e) {
|
||||
db.abortTransaction(txn);
|
||||
throw e;
|
||||
}
|
||||
} finally {
|
||||
transportLock.writeLock().unlock();
|
||||
}
|
||||
// Call the listeners outside the lock
|
||||
if(changed) callListeners(Event.TRANSPORTS_UPDATED);
|
||||
}
|
||||
|
||||
public void setRating(AuthorId a, Rating r) throws DbException {
|
||||
messageLock.writeLock().lock();
|
||||
try {
|
||||
@@ -1221,56 +1268,6 @@ DatabaseCleaner.Callback {
|
||||
+ indirect + " indirectly");
|
||||
}
|
||||
|
||||
public void setTransportConfig(TransportId t, TransportConfig config)
|
||||
throws DbException {
|
||||
boolean changed = false;
|
||||
transportLock.writeLock().lock();
|
||||
try {
|
||||
T txn = db.startTransaction();
|
||||
try {
|
||||
TransportConfig old = db.getTransportConfig(txn, t);
|
||||
if(!config.equals(old)) {
|
||||
db.setTransportConfig(txn, t, config);
|
||||
changed = true;
|
||||
}
|
||||
db.commitTransaction(txn);
|
||||
} catch(DbException e) {
|
||||
db.abortTransaction(txn);
|
||||
throw e;
|
||||
}
|
||||
} finally {
|
||||
transportLock.writeLock().unlock();
|
||||
}
|
||||
// Call the listeners outside the lock
|
||||
if(changed) callListeners(Event.TRANSPORTS_UPDATED);
|
||||
}
|
||||
|
||||
public void setTransportProperties(TransportId t,
|
||||
TransportProperties properties) throws DbException {
|
||||
boolean changed = false;
|
||||
transportLock.writeLock().lock();
|
||||
try {
|
||||
T txn = db.startTransaction();
|
||||
try {
|
||||
Map<TransportId, TransportProperties> transports =
|
||||
db.getLocalTransports(txn);
|
||||
TransportProperties old = transports.get(t);
|
||||
if(!properties.equals(old)) {
|
||||
db.setTransportProperties(txn, t, properties);
|
||||
changed = true;
|
||||
}
|
||||
db.commitTransaction(txn);
|
||||
} catch(DbException e) {
|
||||
db.abortTransaction(txn);
|
||||
throw e;
|
||||
}
|
||||
} finally {
|
||||
transportLock.writeLock().unlock();
|
||||
}
|
||||
// Call the listeners outside the lock
|
||||
if(changed) callListeners(Event.TRANSPORTS_UPDATED);
|
||||
}
|
||||
|
||||
public void setVisibility(GroupId g, Collection<ContactId> visible)
|
||||
throws DbException {
|
||||
contactLock.readLock().lock();
|
||||
|
||||
@@ -16,7 +16,6 @@ import java.util.HashMap;
|
||||
import java.util.LinkedList;
|
||||
import java.util.Map;
|
||||
import java.util.Map.Entry;
|
||||
import java.util.TreeMap;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
@@ -811,6 +810,28 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
}
|
||||
}
|
||||
|
||||
public TransportConfig getConfig(Connection txn, TransportId t)
|
||||
throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
String sql = "SELECT key, value FROM transportConfig"
|
||||
+ " WHERE transportId = ?";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setInt(1, t.getInt());
|
||||
rs = ps.executeQuery();
|
||||
TransportConfig config = new TransportConfig();
|
||||
while(rs.next()) config.put(rs.getString(1), rs.getString(2));
|
||||
rs.close();
|
||||
ps.close();
|
||||
return config;
|
||||
} catch(SQLException e) {
|
||||
tryToClose(rs);
|
||||
tryToClose(ps);
|
||||
throw new DbException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public long getConnectionNumber(Connection txn, ContactId c,
|
||||
TransportId t) throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
@@ -918,6 +939,34 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
} else return f.length();
|
||||
}
|
||||
|
||||
public MessageId getGroupMessageParent(Connection txn, MessageId m)
|
||||
throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
String sql = "SELECT m1.parentId FROM messages AS m1"
|
||||
+ " JOIN messages AS m2"
|
||||
+ " ON m1.parentId = m2.messageId"
|
||||
+ " AND m1.groupId = m2.groupId"
|
||||
+ " WHERE m1.messageId = ?";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setBytes(1, m.getBytes());
|
||||
rs = ps.executeQuery();
|
||||
MessageId parent = null;
|
||||
if(rs.next()) {
|
||||
parent = new MessageId(rs.getBytes(1));
|
||||
if(rs.next()) throw new DbStateException();
|
||||
}
|
||||
rs.close();
|
||||
ps.close();
|
||||
return parent;
|
||||
} catch(SQLException e) {
|
||||
tryToClose(rs);
|
||||
tryToClose(ps);
|
||||
throw new DbException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public Map<TransportId, TransportProperties> getLocalTransports(
|
||||
Connection txn) throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
@@ -928,7 +977,7 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
ps = txn.prepareStatement(sql);
|
||||
rs = ps.executeQuery();
|
||||
Map<TransportId, TransportProperties> transports =
|
||||
new TreeMap<TransportId, TransportProperties>();
|
||||
new HashMap<TransportId, TransportProperties>();
|
||||
TransportProperties properties = null;
|
||||
TransportId lastId = null;
|
||||
while(rs.next()) {
|
||||
@@ -1164,34 +1213,6 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
}
|
||||
}
|
||||
|
||||
public MessageId getGroupMessageParent(Connection txn, MessageId m)
|
||||
throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
String sql = "SELECT m1.parentId FROM messages AS m1"
|
||||
+ " JOIN messages AS m2"
|
||||
+ " ON m1.parentId = m2.messageId"
|
||||
+ " AND m1.groupId = m2.groupId"
|
||||
+ " WHERE m1.messageId = ?";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setBytes(1, m.getBytes());
|
||||
rs = ps.executeQuery();
|
||||
MessageId parent = null;
|
||||
if(rs.next()) {
|
||||
parent = new MessageId(rs.getBytes(1));
|
||||
if(rs.next()) throw new DbStateException();
|
||||
}
|
||||
rs.close();
|
||||
ps.close();
|
||||
return parent;
|
||||
} catch(SQLException e) {
|
||||
tryToClose(rs);
|
||||
tryToClose(ps);
|
||||
throw new DbException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public Rating getRating(Connection txn, AuthorId a) throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
ResultSet rs = null;
|
||||
@@ -1214,61 +1235,32 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
}
|
||||
}
|
||||
|
||||
public Map<TransportId, Map<ContactId, TransportProperties>>
|
||||
getRemoteTransports(Connection txn) throws DbException {
|
||||
public Map<ContactId, TransportProperties> getRemoteProperties(
|
||||
Connection txn, TransportId t) throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
String sql = "SELECT transportId, contactId, key, value"
|
||||
+ " FROM contactTransports"
|
||||
+ " ORDER BY transportId";
|
||||
String sql = "SELECT contactId, key, value FROM contactTransports"
|
||||
+ " WHERE transportId = ?"
|
||||
+ " ORDER BY contactId";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setInt(1, t.getInt());
|
||||
rs = ps.executeQuery();
|
||||
Map<TransportId, Map<ContactId, TransportProperties>> transports =
|
||||
new TreeMap<TransportId, Map<ContactId, TransportProperties>>();
|
||||
Map<ContactId, TransportProperties> contacts = null;
|
||||
TransportProperties properties = null;
|
||||
TransportId lastTransportId = null;
|
||||
Map<ContactId, TransportProperties> properties =
|
||||
new HashMap<ContactId, TransportProperties>();
|
||||
TransportProperties p = null;
|
||||
ContactId lastContactId = null;
|
||||
while(rs.next()) {
|
||||
TransportId transportId = new TransportId(rs.getInt(1));
|
||||
if(!transportId.equals(lastTransportId)) {
|
||||
contacts = new HashMap<ContactId, TransportProperties>();
|
||||
transports.put(transportId, contacts);
|
||||
lastContactId = null;
|
||||
}
|
||||
ContactId contactId = new ContactId(rs.getInt(2));
|
||||
ContactId contactId = new ContactId(rs.getInt(1));
|
||||
if(!contactId.equals(lastContactId)) {
|
||||
properties = new TransportProperties();
|
||||
contacts.put(contactId, properties);
|
||||
p = new TransportProperties();
|
||||
properties.put(contactId, p);
|
||||
}
|
||||
properties.put(rs.getString(3), rs.getString(4));
|
||||
p.put(rs.getString(2), rs.getString(3));
|
||||
}
|
||||
rs.close();
|
||||
ps.close();
|
||||
return transports;
|
||||
} catch(SQLException e) {
|
||||
tryToClose(rs);
|
||||
tryToClose(ps);
|
||||
throw new DbException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public byte[] getSharedSecret(Connection txn, ContactId c)
|
||||
throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
String sql = "SELECT secret FROM contacts WHERE contactId = ?";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setInt(1, c.getInt());
|
||||
rs = ps.executeQuery();
|
||||
if(!rs.next()) throw new DbStateException();
|
||||
byte[] secret = rs.getBytes(1);
|
||||
if(rs.next()) throw new DbStateException();
|
||||
rs.close();
|
||||
ps.close();
|
||||
return secret;
|
||||
return properties;
|
||||
} catch(SQLException e) {
|
||||
tryToClose(rs);
|
||||
tryToClose(ps);
|
||||
@@ -1415,6 +1407,28 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
}
|
||||
}
|
||||
|
||||
public byte[] getSharedSecret(Connection txn, ContactId c)
|
||||
throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
String sql = "SELECT secret FROM contacts WHERE contactId = ?";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setInt(1, c.getInt());
|
||||
rs = ps.executeQuery();
|
||||
if(!rs.next()) throw new DbStateException();
|
||||
byte[] secret = rs.getBytes(1);
|
||||
if(rs.next()) throw new DbStateException();
|
||||
rs.close();
|
||||
ps.close();
|
||||
return secret;
|
||||
} catch(SQLException e) {
|
||||
tryToClose(rs);
|
||||
tryToClose(ps);
|
||||
throw new DbException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public Collection<Group> getSubscriptions(Connection txn)
|
||||
throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
@@ -1469,28 +1483,6 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
}
|
||||
}
|
||||
|
||||
public TransportConfig getTransportConfig(Connection txn,
|
||||
TransportId t) throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
ResultSet rs = null;
|
||||
try {
|
||||
String sql = "SELECT key, value FROM transportConfig"
|
||||
+ " WHERE transportId = ?";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setInt(1, t.getInt());
|
||||
rs = ps.executeQuery();
|
||||
TransportConfig config = new TransportConfig();
|
||||
while(rs.next()) config.put(rs.getString(1), rs.getString(2));
|
||||
rs.close();
|
||||
ps.close();
|
||||
return config;
|
||||
} catch(SQLException e) {
|
||||
tryToClose(rs);
|
||||
tryToClose(ps);
|
||||
throw new DbException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public Collection<ContactId> getVisibility(Connection txn, GroupId g)
|
||||
throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
@@ -1778,6 +1770,44 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
}
|
||||
}
|
||||
|
||||
public void setConfig(Connection txn, TransportId t, TransportConfig config)
|
||||
throws DbException {
|
||||
setTransportDetails(txn, t, config, "transportConfig");
|
||||
}
|
||||
|
||||
private void setTransportDetails(Connection txn, TransportId t,
|
||||
Map<String, String> details, String table) throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
try {
|
||||
// Delete any existing details for the given transport
|
||||
String sql = "DELETE FROM " + table + " WHERE transportId = ?";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setInt(1, t.getInt());
|
||||
ps.executeUpdate();
|
||||
ps.close();
|
||||
// Store the new details
|
||||
sql = "INSERT INTO " + table + " (transportId, key, value)"
|
||||
+ " VALUES (?, ?, ?)";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setInt(1, t.getInt());
|
||||
for(Entry<String, String> e : details.entrySet()) {
|
||||
ps.setString(2, e.getKey());
|
||||
ps.setString(3, e.getValue());
|
||||
ps.addBatch();
|
||||
}
|
||||
int[] batchAffected = ps.executeBatch();
|
||||
if(batchAffected.length != details.size())
|
||||
throw new DbStateException();
|
||||
for(int i = 0; i < batchAffected.length; i++) {
|
||||
if(batchAffected[i] != 1) throw new DbStateException();
|
||||
}
|
||||
ps.close();
|
||||
} catch(SQLException e) {
|
||||
tryToClose(ps);
|
||||
throw new DbException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public void setConnectionWindow(Connection txn, ContactId c,
|
||||
TransportId t, ConnectionWindow w) throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
@@ -1826,6 +1856,11 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
}
|
||||
}
|
||||
|
||||
public void setLocalProperties(Connection txn, TransportId t,
|
||||
TransportProperties properties) throws DbException {
|
||||
setTransportDetails(txn, t, properties, "transports");
|
||||
}
|
||||
|
||||
public Rating setRating(Connection txn, AuthorId a, Rating r)
|
||||
throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
@@ -2051,49 +2086,6 @@ abstract class JdbcDatabase implements Database<Connection> {
|
||||
}
|
||||
}
|
||||
|
||||
public void setTransportConfig(Connection txn, TransportId t,
|
||||
TransportConfig config) throws DbException {
|
||||
setTransportDetails(txn, t, config, "transportConfig");
|
||||
}
|
||||
|
||||
private void setTransportDetails(Connection txn, TransportId t,
|
||||
Map<String, String> details, String table) throws DbException {
|
||||
PreparedStatement ps = null;
|
||||
try {
|
||||
// Delete any existing details for the given transport
|
||||
String sql = "DELETE FROM " + table + " WHERE transportId = ?";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setInt(1, t.getInt());
|
||||
ps.executeUpdate();
|
||||
ps.close();
|
||||
// Store the new details
|
||||
sql = "INSERT INTO " + table + " (transportId, key, value)"
|
||||
+ " VALUES (?, ?, ?)";
|
||||
ps = txn.prepareStatement(sql);
|
||||
ps.setInt(1, t.getInt());
|
||||
for(Entry<String, String> e : details.entrySet()) {
|
||||
ps.setString(2, e.getKey());
|
||||
ps.setString(3, e.getValue());
|
||||
ps.addBatch();
|
||||
}
|
||||
int[] batchAffected = ps.executeBatch();
|
||||
if(batchAffected.length != details.size())
|
||||
throw new DbStateException();
|
||||
for(int i = 0; i < batchAffected.length; i++) {
|
||||
if(batchAffected[i] != 1) throw new DbStateException();
|
||||
}
|
||||
ps.close();
|
||||
} catch(SQLException e) {
|
||||
tryToClose(ps);
|
||||
throw new DbException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public void setTransportProperties(Connection txn, TransportId t,
|
||||
TransportProperties properties) throws DbException {
|
||||
setTransportDetails(txn, t, properties, "transports");
|
||||
}
|
||||
|
||||
public void setTransports(Connection txn, ContactId c,
|
||||
Map<TransportId, TransportProperties> transports, long timestamp)
|
||||
throws DbException {
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
package net.sf.briar.protocol;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.TreeMap;
|
||||
|
||||
import net.sf.briar.api.FormatException;
|
||||
import net.sf.briar.api.TransportId;
|
||||
@@ -40,7 +40,7 @@ class TransportReader implements ObjectReader<TransportUpdate> {
|
||||
if(l.size() > TransportUpdate.MAX_PLUGINS_PER_UPDATE)
|
||||
throw new FormatException();
|
||||
Map<TransportId, TransportProperties> transports =
|
||||
new TreeMap<TransportId, TransportProperties>();
|
||||
new HashMap<TransportId, TransportProperties>();
|
||||
for(Transport t : l) {
|
||||
if(transports.put(t.id, t.properties) != null)
|
||||
throw new FormatException(); // Duplicate transport ID
|
||||
|
||||
Reference in New Issue
Block a user