diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/TransportId.java b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/TransportId.java
index 352e946a0aa51e48ae1712f0aa3aa1c1f719c9a7..5ad3762dfe31c2db510f65d41bf188afcb572d0d 100644
--- a/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/TransportId.java
+++ b/bramble-api/src/main/java/org/briarproject/bramble/api/plugin/TransportId.java
@@ -1,22 +1,23 @@
 package org.briarproject.bramble.api.plugin;
 
-import java.nio.charset.Charset;
+import org.briarproject.bramble.util.StringUtils;
 
 /**
- * Type-safe wrapper for a string that uniquely identifies a transport plugin.
+ * Type-safe wrapper for a namespaced string that uniquely identifies a
+ * transport plugin.
  */
 public class TransportId {
 
 	/**
-	 * The maximum length of transport identifier in UTF-8 bytes.
+	 * The maximum length of a transport identifier in UTF-8 bytes.
 	 */
-	public static int MAX_TRANSPORT_ID_LENGTH = 64;
+	public static int MAX_TRANSPORT_ID_LENGTH = 100;
 
 	private final String id;
 
 	public TransportId(String id) {
-		byte[] b = id.getBytes(Charset.forName("UTF-8"));
-		if (b.length == 0 || b.length > MAX_TRANSPORT_ID_LENGTH)
+		int length = StringUtils.toUtf8(id).length;
+		if (length == 0 || length > MAX_TRANSPORT_ID_LENGTH)
 			throw new IllegalArgumentException();
 		this.id = id;
 	}
diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/sync/ClientId.java b/bramble-api/src/main/java/org/briarproject/bramble/api/sync/ClientId.java
index 9f873b8e9602d2c67b9fd773f1eed7ae790ec5dc..a0f4e66754eb3da34864619e12145e7f49f1df6c 100644
--- a/bramble-api/src/main/java/org/briarproject/bramble/api/sync/ClientId.java
+++ b/bramble-api/src/main/java/org/briarproject/bramble/api/sync/ClientId.java
@@ -1,19 +1,29 @@
 package org.briarproject.bramble.api.sync;
 
 import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
+import org.briarproject.bramble.util.StringUtils;
 
 import javax.annotation.concurrent.Immutable;
 
 /**
- * Wrapper for a name-spaced string that uniquely identifies a sync client.
+ * Type-safe wrapper for a namespaced string that uniquely identifies a sync
+ * client.
  */
 @Immutable
 @NotNullByDefault
 public class ClientId implements Comparable<ClientId> {
 
+	/**
+	 * The maximum length of a client identifier in UTF-8 bytes.
+	 */
+	public static int MAX_CLIENT_ID_LENGTH = 100;
+
 	private final String id;
 
 	public ClientId(String id) {
+		int length = StringUtils.toUtf8(id).length;
+		if (length == 0 || length > MAX_CLIENT_ID_LENGTH)
+			throw new IllegalArgumentException();
 		this.id = id;
 	}
 
diff --git a/bramble-api/src/test/java/org/briarproject/bramble/test/TestUtils.java b/bramble-api/src/test/java/org/briarproject/bramble/test/TestUtils.java
index a0fcb5e4ebdacd3dabb3ebe6b2937f506b2d05f2..9da2a829ce775fa650ecf7ea8c1915516ff2e857 100644
--- a/bramble-api/src/test/java/org/briarproject/bramble/test/TestUtils.java
+++ b/bramble-api/src/test/java/org/briarproject/bramble/test/TestUtils.java
@@ -5,6 +5,7 @@ import org.briarproject.bramble.api.crypto.SecretKey;
 import org.briarproject.bramble.api.identity.Author;
 import org.briarproject.bramble.api.identity.AuthorId;
 import org.briarproject.bramble.api.identity.LocalAuthor;
+import org.briarproject.bramble.api.plugin.TransportId;
 import org.briarproject.bramble.api.sync.ClientId;
 import org.briarproject.bramble.api.sync.Group;
 import org.briarproject.bramble.api.sync.GroupId;
@@ -23,6 +24,8 @@ import java.util.concurrent.atomic.AtomicInteger;
 import static org.briarproject.bramble.api.identity.Author.FORMAT_VERSION;
 import static org.briarproject.bramble.api.identity.AuthorConstants.MAX_AUTHOR_NAME_LENGTH;
 import static org.briarproject.bramble.api.identity.AuthorConstants.MAX_PUBLIC_KEY_LENGTH;
+import static org.briarproject.bramble.api.plugin.TransportId.MAX_TRANSPORT_ID_LENGTH;
+import static org.briarproject.bramble.api.sync.ClientId.MAX_CLIENT_ID_LENGTH;
 import static org.briarproject.bramble.api.sync.SyncConstants.MAX_GROUP_DESCRIPTOR_LENGTH;
 import static org.briarproject.bramble.api.sync.SyncConstants.MAX_MESSAGE_BODY_LENGTH;
 import static org.briarproject.bramble.api.sync.SyncConstants.MESSAGE_HEADER_LENGTH;
@@ -54,6 +57,14 @@ public class TestUtils {
 		return getRandomBytes(UniqueId.LENGTH);
 	}
 
+	public static ClientId getClientId() {
+		return new ClientId(getRandomString(MAX_CLIENT_ID_LENGTH));
+	}
+
+	public static TransportId getTransportId() {
+		return new TransportId(getRandomString(MAX_TRANSPORT_ID_LENGTH));
+	}
+
 	public static SecretKey getSecretKey() {
 		return new SecretKey(getRandomBytes(SecretKey.LENGTH));
 	}
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/crypto/KeyDerivationTest.java b/bramble-core/src/test/java/org/briarproject/bramble/crypto/KeyDerivationTest.java
index dc51966ffb3e1c15acc1fa66b0657b057cbe9624..969d62588cbbae880918799859012f566150e716 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/crypto/KeyDerivationTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/crypto/KeyDerivationTest.java
@@ -17,6 +17,7 @@ import java.util.List;
 import java.util.Set;
 
 import static org.briarproject.bramble.test.TestUtils.getSecretKey;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.junit.Assert.assertArrayEquals;
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertTrue;
@@ -27,7 +28,7 @@ public class KeyDerivationTest extends BrambleTestCase {
 			new CryptoComponentImpl(new TestSecureRandomProvider(), null);
 	private final TransportCrypto transportCrypto =
 			new TransportCryptoImpl(crypto);
-	private final TransportId transportId = new TransportId("id");
+	private final TransportId transportId = getTransportId();
 	private final SecretKey master = getSecretKey();
 
 	@Test
@@ -135,7 +136,7 @@ public class KeyDerivationTest extends BrambleTestCase {
 
 	@Test
 	public void testTransportIdAffectsOutput() {
-		TransportId transportId1 = new TransportId("id1");
+		TransportId transportId1 = getTransportId();
 		assertFalse(transportId.getString().equals(transportId1.getString()));
 		TransportKeys k = transportCrypto.deriveTransportKeys(transportId,
 				master, 123, true, true);
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseComponentImplTest.java b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseComponentImplTest.java
index f0149bb248948d6bb51d7bd1693a741407d464cc..06552073c223bc6447a1a6a37fec213355629348 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseComponentImplTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseComponentImplTest.java
@@ -70,9 +70,10 @@ import static org.briarproject.bramble.api.sync.ValidationManager.State.UNKNOWN;
 import static org.briarproject.bramble.api.transport.TransportConstants.REORDERING_WINDOW_SIZE;
 import static org.briarproject.bramble.db.DatabaseConstants.MAX_OFFERED_MESSAGES;
 import static org.briarproject.bramble.test.TestUtils.getAuthor;
+import static org.briarproject.bramble.test.TestUtils.getClientId;
 import static org.briarproject.bramble.test.TestUtils.getLocalAuthor;
 import static org.briarproject.bramble.test.TestUtils.getSecretKey;
-import static org.briarproject.bramble.util.StringUtils.getRandomString;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertNotNull;
@@ -104,7 +105,7 @@ public class DatabaseComponentImplTest extends BrambleMockTestCase {
 	private final KeySetId keySetId;
 
 	public DatabaseComponentImplTest() {
-		clientId = new ClientId(getRandomString(123));
+		clientId = getClientId();
 		groupId = new GroupId(TestUtils.getRandomId());
 		byte[] descriptor = new byte[MAX_GROUP_DESCRIPTOR_LENGTH];
 		group = new Group(groupId, clientId, descriptor);
@@ -118,7 +119,7 @@ public class DatabaseComponentImplTest extends BrambleMockTestCase {
 		message = new Message(messageId, groupId, timestamp, raw);
 		metadata = new Metadata();
 		metadata.put("foo", new byte[] {'b', 'a', 'r'});
-		transportId = new TransportId("id");
+		transportId = getTransportId();
 		maxLatency = Integer.MAX_VALUE;
 		contactId = new ContactId(234);
 		contact = new Contact(contactId, author, localAuthor.getId(),
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/db/JdbcDatabaseTest.java b/bramble-core/src/test/java/org/briarproject/bramble/db/JdbcDatabaseTest.java
index 157b6902be00063bd0215b5b8a7dd011f9cc2837..d1b898efe8b0cb247fc8f86303f1ed83472b318f 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/db/JdbcDatabaseTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/db/JdbcDatabaseTest.java
@@ -59,11 +59,12 @@ import static org.briarproject.bramble.api.sync.ValidationManager.State.INVALID;
 import static org.briarproject.bramble.api.sync.ValidationManager.State.PENDING;
 import static org.briarproject.bramble.api.sync.ValidationManager.State.UNKNOWN;
 import static org.briarproject.bramble.test.TestUtils.getAuthor;
+import static org.briarproject.bramble.test.TestUtils.getClientId;
 import static org.briarproject.bramble.test.TestUtils.getLocalAuthor;
 import static org.briarproject.bramble.test.TestUtils.getRandomBytes;
 import static org.briarproject.bramble.test.TestUtils.getRandomId;
 import static org.briarproject.bramble.test.TestUtils.getSecretKey;
-import static org.briarproject.bramble.util.StringUtils.getRandomString;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.junit.Assert.assertArrayEquals;
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertFalse;
@@ -95,7 +96,7 @@ public abstract class JdbcDatabaseTest extends BrambleTestCase {
 
 	JdbcDatabaseTest() throws Exception {
 		groupId = new GroupId(getRandomId());
-		clientId = new ClientId(getRandomString(123));
+		clientId = getClientId();
 		byte[] descriptor = new byte[MAX_GROUP_DESCRIPTOR_LENGTH];
 		group = new Group(groupId, clientId, descriptor);
 		author = getAuthor();
@@ -105,7 +106,7 @@ public abstract class JdbcDatabaseTest extends BrambleTestCase {
 		size = 1234;
 		raw = getRandomBytes(size);
 		message = new Message(messageId, groupId, timestamp, raw);
-		transportId = new TransportId("id");
+		transportId = getTransportId();
 		contactId = new ContactId(1);
 		keySetId = new KeySetId(1);
 		keySetId1 = new KeySetId(2);
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/keyagreement/KeyAgreementTransportTest.java b/bramble-core/src/test/java/org/briarproject/bramble/keyagreement/KeyAgreementTransportTest.java
index 5030f6931e3592618ed5abc7d73bae3550d45deb..b42fbbd25442572cecb1bbcf3cacff9ba16dd64f 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/keyagreement/KeyAgreementTransportTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/keyagreement/KeyAgreementTransportTest.java
@@ -19,6 +19,7 @@ import static org.briarproject.bramble.api.keyagreement.KeyAgreementConstants.RE
 import static org.briarproject.bramble.api.keyagreement.RecordTypes.ABORT;
 import static org.briarproject.bramble.api.keyagreement.RecordTypes.CONFIRM;
 import static org.briarproject.bramble.api.keyagreement.RecordTypes.KEY;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.junit.Assert.assertArrayEquals;
 import static org.junit.Assert.assertEquals;
 
@@ -31,7 +32,7 @@ public class KeyAgreementTransportTest extends BrambleMockTestCase {
 	private final TransportConnectionWriter transportConnectionWriter =
 			context.mock(TransportConnectionWriter.class);
 
-	private final TransportId transportId = new TransportId("test");
+	private final TransportId transportId = getTransportId();
 	private final KeyAgreementConnection keyAgreementConnection =
 			new KeyAgreementConnection(duplexTransportConnection, transportId);
 
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/plugin/ConnectionRegistryImplTest.java b/bramble-core/src/test/java/org/briarproject/bramble/plugin/ConnectionRegistryImplTest.java
index d0cbb7732ac0ded2427fc874757ce366c9cd7a88..59dfb892279c39d3d10bb611841ae24a87d33d4f 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/plugin/ConnectionRegistryImplTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/plugin/ConnectionRegistryImplTest.java
@@ -17,6 +17,7 @@ import java.util.Collection;
 import java.util.Collections;
 import java.util.NoSuchElementException;
 
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertTrue;
 import static org.junit.Assert.fail;
@@ -29,8 +30,8 @@ public class ConnectionRegistryImplTest extends BrambleTestCase {
 	public ConnectionRegistryImplTest() {
 		contactId = new ContactId(1);
 		contactId1 = new ContactId(2);
-		transportId = new TransportId("id");
-		transportId1 = new TransportId("id1");
+		transportId = getTransportId();
+		transportId1 = getTransportId();
 	}
 
 	@Test
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/plugin/PluginManagerImplTest.java b/bramble-core/src/test/java/org/briarproject/bramble/plugin/PluginManagerImplTest.java
index 9276baf0e93513a8700f07cf4a566817d770beb8..aa96dc3966e3ba984ea03994180c865f3766bfc2 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/plugin/PluginManagerImplTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/plugin/PluginManagerImplTest.java
@@ -24,6 +24,8 @@ import java.util.Arrays;
 import java.util.concurrent.Executor;
 import java.util.concurrent.Executors;
 
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
+
 public class PluginManagerImplTest extends BrambleTestCase {
 
 	@Test
@@ -46,21 +48,21 @@ public class PluginManagerImplTest extends BrambleTestCase {
 		SimplexPluginFactory simplexFactory =
 				context.mock(SimplexPluginFactory.class);
 		SimplexPlugin simplexPlugin = context.mock(SimplexPlugin.class);
-		TransportId simplexId = new TransportId("simplex");
+		TransportId simplexId = getTransportId();
 		SimplexPluginFactory simplexFailFactory =
 				context.mock(SimplexPluginFactory.class, "simplexFailFactory");
 		SimplexPlugin simplexFailPlugin =
 				context.mock(SimplexPlugin.class, "simplexFailPlugin");
-		TransportId simplexFailId = new TransportId("simplex1");
+		TransportId simplexFailId = getTransportId();
 
 		// Two duplex plugin factories: one creates a plugin, the other fails
 		DuplexPluginFactory duplexFactory =
 				context.mock(DuplexPluginFactory.class);
 		DuplexPlugin duplexPlugin = context.mock(DuplexPlugin.class);
-		TransportId duplexId = new TransportId("duplex");
+		TransportId duplexId = getTransportId();
 		DuplexPluginFactory duplexFailFactory =
 				context.mock(DuplexPluginFactory.class, "duplexFailFactory");
-		TransportId duplexFailId = new TransportId("duplex1");
+		TransportId duplexFailId = getTransportId();
 
 		context.checking(new Expectations() {{
 			allowing(simplexPlugin).getId();
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/plugin/PollerTest.java b/bramble-core/src/test/java/org/briarproject/bramble/plugin/PollerTest.java
index c27c82a4ffef392a1d81b1bcd955a6431539b16e..5b0297595ce6e6b344774b3bb61ce2f4b0dcd0ef 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/plugin/PollerTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/plugin/PollerTest.java
@@ -32,6 +32,7 @@ import java.util.concurrent.ScheduledExecutorService;
 import java.util.concurrent.ScheduledFuture;
 
 import static java.util.concurrent.TimeUnit.MILLISECONDS;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 
 public class PollerTest extends BrambleMockTestCase {
 
@@ -48,7 +49,7 @@ public class PollerTest extends BrambleMockTestCase {
 	private final SecureRandom random;
 
 	private final Executor ioExecutor = new ImmediateExecutor();
-	private final TransportId transportId = new TransportId("id");
+	private final TransportId transportId = getTransportId();
 	private final ContactId contactId = new ContactId(234);
 	private final int pollingInterval = 60 * 1000;
 	private final long now = System.currentTimeMillis();
@@ -64,7 +65,7 @@ public class PollerTest extends BrambleMockTestCase {
 		SimplexPlugin simplexPlugin = context.mock(SimplexPlugin.class);
 		SimplexPlugin simplexPlugin1 =
 				context.mock(SimplexPlugin.class, "simplexPlugin1");
-		TransportId simplexId1 = new TransportId("simplex1");
+		TransportId simplexId1 = getTransportId();
 		List<SimplexPlugin> simplexPlugins = Arrays.asList(simplexPlugin,
 				simplexPlugin1);
 		TransportConnectionWriter simplexWriter =
@@ -72,7 +73,7 @@ public class PollerTest extends BrambleMockTestCase {
 
 		// Two duplex plugins: one supports polling, the other doesn't
 		DuplexPlugin duplexPlugin = context.mock(DuplexPlugin.class);
-		TransportId duplexId = new TransportId("duplex");
+		TransportId duplexId = getTransportId();
 		DuplexPlugin duplexPlugin1 =
 				context.mock(DuplexPlugin.class, "duplexPlugin1");
 		List<DuplexPlugin> duplexPlugins = Arrays.asList(duplexPlugin,
@@ -349,7 +350,6 @@ public class PollerTest extends BrambleMockTestCase {
 	@Test
 	public void testCancelsPollingOnTransportDisabled() throws Exception {
 		Plugin plugin = context.mock(Plugin.class);
-		List<ContactId> connected = Collections.singletonList(contactId);
 
 		context.checking(new Expectations() {{
 			allowing(plugin).getId();
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/properties/TransportPropertyValidatorTest.java b/bramble-core/src/test/java/org/briarproject/bramble/properties/TransportPropertyValidatorTest.java
index 0ffc9e733298dd9fdbe6d14aa273decdd43033b0..eecbbf894c0cf8c9b03557efd817c10246343397 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/properties/TransportPropertyValidatorTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/properties/TransportPropertyValidatorTest.java
@@ -6,14 +6,11 @@ import org.briarproject.bramble.api.data.BdfDictionary;
 import org.briarproject.bramble.api.data.BdfList;
 import org.briarproject.bramble.api.data.MetadataEncoder;
 import org.briarproject.bramble.api.plugin.TransportId;
-import org.briarproject.bramble.api.sync.ClientId;
 import org.briarproject.bramble.api.sync.Group;
-import org.briarproject.bramble.api.sync.GroupId;
 import org.briarproject.bramble.api.sync.Message;
 import org.briarproject.bramble.api.sync.MessageId;
 import org.briarproject.bramble.api.system.Clock;
 import org.briarproject.bramble.test.BrambleTestCase;
-import org.briarproject.bramble.test.TestUtils;
 import org.briarproject.bramble.util.StringUtils;
 import org.jmock.Mockery;
 import org.junit.Test;
@@ -22,6 +19,11 @@ import java.io.IOException;
 
 import static org.briarproject.bramble.api.plugin.TransportId.MAX_TRANSPORT_ID_LENGTH;
 import static org.briarproject.bramble.api.properties.TransportPropertyConstants.MAX_PROPERTIES_PER_TRANSPORT;
+import static org.briarproject.bramble.test.TestUtils.getClientId;
+import static org.briarproject.bramble.test.TestUtils.getGroup;
+import static org.briarproject.bramble.test.TestUtils.getRandomBytes;
+import static org.briarproject.bramble.test.TestUtils.getRandomId;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.junit.Assert.assertEquals;
 
 public class TransportPropertyValidatorTest extends BrambleTestCase {
@@ -33,18 +35,14 @@ public class TransportPropertyValidatorTest extends BrambleTestCase {
 	private final TransportPropertyValidator tpv;
 
 	public TransportPropertyValidatorTest() {
-		transportId = new TransportId("test");
+		transportId = getTransportId();
 		bdfDictionary = new BdfDictionary();
 
-		GroupId groupId = new GroupId(TestUtils.getRandomId());
-		ClientId clientId = new ClientId(StringUtils.getRandomString(5));
-		byte[] descriptor = TestUtils.getRandomBytes(12);
-		group = new Group(groupId, clientId, descriptor);
-
-		MessageId messageId = new MessageId(TestUtils.getRandomId());
+		group = getGroup(getClientId());
+		MessageId messageId = new MessageId(getRandomId());
 		long timestamp = System.currentTimeMillis();
-		byte[] body = TestUtils.getRandomBytes(123);
-		message = new Message(messageId, groupId, timestamp, body);
+		byte[] body = getRandomBytes(123);
+		message = new Message(messageId, group.getId(), timestamp, body);
 
 		Mockery context = new Mockery();
 		ClientHelper clientHelper = context.mock(ClientHelper.class);
@@ -63,7 +61,7 @@ public class TransportPropertyValidatorTest extends BrambleTestCase {
 		BdfDictionary result = tpv.validateMessage(message, group, body)
 				.getDictionary();
 
-		assertEquals("test", result.getString("transportId"));
+		assertEquals(transportId.getString(), result.getString("transportId"));
 		assertEquals(4, result.getLong("version").longValue());
 	}
 
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/sync/SyncIntegrationTest.java b/bramble-core/src/test/java/org/briarproject/bramble/sync/SyncIntegrationTest.java
index c5f3136129864c45040cfbce9bf63f5e7c5ffb88..593a8ef71eeb034799dcd22d80a2e53e145ebf9a 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/sync/SyncIntegrationTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/sync/SyncIntegrationTest.java
@@ -36,7 +36,8 @@ import javax.inject.Inject;
 import static org.briarproject.bramble.api.sync.SyncConstants.MAX_GROUP_DESCRIPTOR_LENGTH;
 import static org.briarproject.bramble.api.transport.TransportConstants.PROTOCOL_VERSION;
 import static org.briarproject.bramble.api.transport.TransportConstants.TAG_LENGTH;
-import static org.briarproject.bramble.util.StringUtils.getRandomString;
+import static org.briarproject.bramble.test.TestUtils.getClientId;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.junit.Assert.assertArrayEquals;
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertFalse;
@@ -73,13 +74,13 @@ public class SyncIntegrationTest extends BrambleTestCase {
 		component.inject(this);
 
 		contactId = new ContactId(234);
-		transportId = new TransportId("id");
+		transportId = getTransportId();
 		// Create the transport keys
 		tagKey = TestUtils.getSecretKey();
 		headerKey = TestUtils.getSecretKey();
 		streamNumber = 123;
 		// Create a group
-		ClientId clientId = new ClientId(getRandomString(123));
+		ClientId clientId = getClientId();
 		int clientVersion = 1234567890;
 		byte[] descriptor = new byte[MAX_GROUP_DESCRIPTOR_LENGTH];
 		Group group = groupFactory.createGroup(clientId, clientVersion,
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/sync/ValidationManagerImplTest.java b/bramble-core/src/test/java/org/briarproject/bramble/sync/ValidationManagerImplTest.java
index cf6b73fa028eb9adf465eb0debbe2e76dc1d78b5..5c197c46257f2cd5cec05d36ec86d4d50df7aefd 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/sync/ValidationManagerImplTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/sync/ValidationManagerImplTest.java
@@ -21,9 +21,7 @@ import org.briarproject.bramble.api.sync.ValidationManager.State;
 import org.briarproject.bramble.api.sync.event.MessageAddedEvent;
 import org.briarproject.bramble.test.BrambleMockTestCase;
 import org.briarproject.bramble.test.ImmediateExecutor;
-import org.briarproject.bramble.test.TestUtils;
 import org.briarproject.bramble.util.ByteUtils;
-import org.briarproject.bramble.util.StringUtils;
 import org.jmock.Expectations;
 import org.junit.Before;
 import org.junit.Test;
@@ -38,6 +36,8 @@ import static org.briarproject.bramble.api.sync.ValidationManager.State.DELIVERE
 import static org.briarproject.bramble.api.sync.ValidationManager.State.INVALID;
 import static org.briarproject.bramble.api.sync.ValidationManager.State.PENDING;
 import static org.briarproject.bramble.api.sync.ValidationManager.State.UNKNOWN;
+import static org.briarproject.bramble.test.TestUtils.getClientId;
+import static org.briarproject.bramble.test.TestUtils.getRandomId;
 
 public class ValidationManagerImplTest extends BrambleMockTestCase {
 
@@ -51,12 +51,11 @@ public class ValidationManagerImplTest extends BrambleMockTestCase {
 
 	private final Executor dbExecutor = new ImmediateExecutor();
 	private final Executor validationExecutor = new ImmediateExecutor();
-	private final ClientId clientId =
-			new ClientId(StringUtils.getRandomString(5));
-	private final MessageId messageId = new MessageId(TestUtils.getRandomId());
-	private final MessageId messageId1 = new MessageId(TestUtils.getRandomId());
-	private final MessageId messageId2 = new MessageId(TestUtils.getRandomId());
-	private final GroupId groupId = new GroupId(TestUtils.getRandomId());
+	private final ClientId clientId = getClientId();
+	private final MessageId messageId = new MessageId(getRandomId());
+	private final MessageId messageId1 = new MessageId(getRandomId());
+	private final MessageId messageId2 = new MessageId(getRandomId());
+	private final GroupId groupId = new GroupId(getRandomId());
 	private final byte[] descriptor = new byte[32];
 	private final Group group = new Group(groupId, clientId, descriptor);
 	private final long timestamp = System.currentTimeMillis();
@@ -716,8 +715,8 @@ public class ValidationManagerImplTest extends BrambleMockTestCase {
 
 	@Test
 	public void testRecursiveInvalidation() throws Exception {
-		MessageId messageId3 = new MessageId(TestUtils.getRandomId());
-		MessageId messageId4 = new MessageId(TestUtils.getRandomId());
+		MessageId messageId3 = new MessageId(getRandomId());
+		MessageId messageId4 = new MessageId(getRandomId());
 		Map<MessageId, State> twoDependents = new LinkedHashMap<>();
 		twoDependents.put(messageId1, PENDING);
 		twoDependents.put(messageId2, PENDING);
@@ -819,8 +818,8 @@ public class ValidationManagerImplTest extends BrambleMockTestCase {
 
 	@Test
 	public void testPendingDependentsGetDelivered() throws Exception {
-		MessageId messageId3 = new MessageId(TestUtils.getRandomId());
-		MessageId messageId4 = new MessageId(TestUtils.getRandomId());
+		MessageId messageId3 = new MessageId(getRandomId());
+		MessageId messageId4 = new MessageId(getRandomId());
 		Message message3 = new Message(messageId3, groupId, timestamp,
 				raw);
 		Message message4 = new Message(messageId4, groupId, timestamp,
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/test/TestPluginConfigModule.java b/bramble-core/src/test/java/org/briarproject/bramble/test/TestPluginConfigModule.java
index 5709770b5ed6de02739fba08d24dc27dd6a25bd2..e016abc4d9a0ee6328fc77e6ebfc3a8348faf126 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/test/TestPluginConfigModule.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/test/TestPluginConfigModule.java
@@ -16,10 +16,12 @@ import javax.annotation.Nullable;
 import dagger.Module;
 import dagger.Provides;
 
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
+
 @Module
 public class TestPluginConfigModule {
 
-	public static final TransportId TRANSPORT_ID = new TransportId("id");
+	public static final TransportId TRANSPORT_ID = getTransportId();
 	public static final int MAX_LATENCY = 2 * 60 * 1000; // 2 minutes
 
 	@NotNullByDefault
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/test/ValidatorTestCase.java b/bramble-core/src/test/java/org/briarproject/bramble/test/ValidatorTestCase.java
index 1629e5335926cca173d33ec113f1ce2cbc3189f6..7f38f7ad33711f991ca31eda9e6a5a4913df7add 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/test/ValidatorTestCase.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/test/ValidatorTestCase.java
@@ -10,9 +10,9 @@ import org.briarproject.bramble.api.sync.Message;
 import org.briarproject.bramble.api.sync.MessageId;
 import org.briarproject.bramble.api.system.Clock;
 
+import static org.briarproject.bramble.test.TestUtils.getClientId;
 import static org.briarproject.bramble.test.TestUtils.getRandomBytes;
 import static org.briarproject.bramble.test.TestUtils.getRandomId;
-import static org.briarproject.bramble.util.StringUtils.getRandomString;
 
 public abstract class ValidatorTestCase extends BrambleMockTestCase {
 
@@ -30,7 +30,7 @@ public abstract class ValidatorTestCase extends BrambleMockTestCase {
 	protected final byte[] raw = getRandomBytes(123);
 	protected final Message message =
 			new Message(messageId, groupId, timestamp, raw);
-	protected final ClientId clientId = new ClientId(getRandomString(123));
+	protected final ClientId clientId = getClientId();
 	protected final byte[] descriptor = getRandomBytes(123);
 	protected final Group group = new Group(groupId, clientId, descriptor);
 
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/transport/KeyManagerImplTest.java b/bramble-core/src/test/java/org/briarproject/bramble/transport/KeyManagerImplTest.java
index ed7a357ed092f32427496906bc27ddf009ae2697..cc3b466b643ed015bfb0444ba16f08dbfc5930fc 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/transport/KeyManagerImplTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/transport/KeyManagerImplTest.java
@@ -31,6 +31,7 @@ import static org.briarproject.bramble.test.TestUtils.getAuthor;
 import static org.briarproject.bramble.test.TestUtils.getRandomBytes;
 import static org.briarproject.bramble.test.TestUtils.getRandomId;
 import static org.briarproject.bramble.test.TestUtils.getSecretKey;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.junit.Assert.assertEquals;
 
 public class KeyManagerImplTest extends BrambleMockTestCase {
@@ -47,8 +48,8 @@ public class KeyManagerImplTest extends BrambleMockTestCase {
 	private final ContactId contactId = new ContactId(123);
 	private final ContactId inactiveContactId = new ContactId(234);
 	private final KeySetId keySetId = new KeySetId(345);
-	private final TransportId transportId = new TransportId("known");
-	private final TransportId unknownTransportId = new TransportId("unknown");
+	private final TransportId transportId = getTransportId();
+	private final TransportId unknownTransportId = getTransportId();
 	private final StreamContext streamContext =
 			new StreamContext(contactId, transportId, getSecretKey(),
 					getSecretKey(), 1);
diff --git a/bramble-core/src/test/java/org/briarproject/bramble/transport/TransportKeyManagerImplTest.java b/bramble-core/src/test/java/org/briarproject/bramble/transport/TransportKeyManagerImplTest.java
index 21350ae6d7414409091bb5fafaa81b6b7fb87a1b..8ae42e396c235f1781fbada5f035a7c985bc7306 100644
--- a/bramble-core/src/test/java/org/briarproject/bramble/transport/TransportKeyManagerImplTest.java
+++ b/bramble-core/src/test/java/org/briarproject/bramble/transport/TransportKeyManagerImplTest.java
@@ -36,6 +36,7 @@ import static org.briarproject.bramble.api.transport.TransportConstants.MAX_CLOC
 import static org.briarproject.bramble.api.transport.TransportConstants.PROTOCOL_VERSION;
 import static org.briarproject.bramble.api.transport.TransportConstants.REORDERING_WINDOW_SIZE;
 import static org.briarproject.bramble.api.transport.TransportConstants.TAG_LENGTH;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.briarproject.bramble.util.ByteUtils.MAX_32_BIT_UNSIGNED;
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertFalse;
@@ -53,7 +54,7 @@ public class TransportKeyManagerImplTest extends BrambleMockTestCase {
 			context.mock(ScheduledExecutorService.class);
 	private final Clock clock = context.mock(Clock.class);
 
-	private final TransportId transportId = new TransportId("id");
+	private final TransportId transportId = getTransportId();
 	private final long maxLatency = 30 * 1000; // 30 seconds
 	private final long rotationPeriodLength = maxLatency + MAX_CLOCK_DIFFERENCE;
 	private final ContactId contactId = new ContactId(123);
diff --git a/briar-core/src/test/java/org/briarproject/briar/client/MessageQueueManagerImplTest.java b/briar-core/src/test/java/org/briarproject/briar/client/MessageQueueManagerImplTest.java
index 5c540c13b16dc4ddc9950378f2ec9663f80d9bb9..3ecc24c4ad430a1bc36f1dcc29439d4f7ea0a7db 100644
--- a/briar-core/src/test/java/org/briarproject/briar/client/MessageQueueManagerImplTest.java
+++ b/briar-core/src/test/java/org/briarproject/briar/client/MessageQueueManagerImplTest.java
@@ -19,7 +19,6 @@ import org.briarproject.bramble.api.sync.ValidationManager.MessageValidator;
 import org.briarproject.bramble.test.CaptureArgumentAction;
 import org.briarproject.bramble.test.TestUtils;
 import org.briarproject.bramble.util.ByteUtils;
-import org.briarproject.bramble.util.StringUtils;
 import org.briarproject.briar.api.client.MessageQueueManager.IncomingQueueMessageHook;
 import org.briarproject.briar.api.client.MessageQueueManager.QueueMessageValidator;
 import org.briarproject.briar.api.client.QueueMessage;
@@ -35,6 +34,7 @@ import org.junit.Test;
 import java.util.concurrent.atomic.AtomicReference;
 
 import static org.briarproject.bramble.api.sync.SyncConstants.MESSAGE_HEADER_LENGTH;
+import static org.briarproject.bramble.test.TestUtils.getClientId;
 import static org.briarproject.briar.api.client.MessageQueueManager.QUEUE_STATE_KEY;
 import static org.briarproject.briar.api.client.QueueMessage.QUEUE_MESSAGE_HEADER_LENGTH;
 import static org.junit.Assert.assertEquals;
@@ -45,8 +45,7 @@ import static org.junit.Assert.fail;
 public class MessageQueueManagerImplTest extends BriarTestCase {
 
 	private final GroupId groupId = new GroupId(TestUtils.getRandomId());
-	private final ClientId clientId =
-			new ClientId(StringUtils.getRandomString(5));
+	private final ClientId clientId = getClientId();
 	private final byte[] descriptor = new byte[0];
 	private final Group group = new Group(groupId, clientId, descriptor);
 	private final long timestamp = System.currentTimeMillis();
diff --git a/briar-core/src/test/java/org/briarproject/briar/introduction/IntroductionIntegrationTest.java b/briar-core/src/test/java/org/briarproject/briar/introduction/IntroductionIntegrationTest.java
index 0cfa068f816b87d1ab51e545fce12c0288712c32..9b485e5c42b1ce13b9ab9414cb90eb48de20432d 100644
--- a/briar-core/src/test/java/org/briarproject/briar/introduction/IntroductionIntegrationTest.java
+++ b/briar-core/src/test/java/org/briarproject/briar/introduction/IntroductionIntegrationTest.java
@@ -19,7 +19,6 @@ import org.briarproject.bramble.api.event.EventListener;
 import org.briarproject.bramble.api.nullsafety.MethodsNotNullByDefault;
 import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
 import org.briarproject.bramble.api.nullsafety.ParametersNotNullByDefault;
-import org.briarproject.bramble.api.plugin.TransportId;
 import org.briarproject.bramble.api.properties.TransportProperties;
 import org.briarproject.bramble.api.properties.TransportPropertyManager;
 import org.briarproject.bramble.api.sync.Group;
@@ -54,6 +53,7 @@ import javax.inject.Inject;
 import static org.briarproject.bramble.api.identity.AuthorConstants.MAX_PUBLIC_KEY_LENGTH;
 import static org.briarproject.bramble.test.TestPluginConfigModule.TRANSPORT_ID;
 import static org.briarproject.bramble.test.TestUtils.getRandomBytes;
+import static org.briarproject.bramble.test.TestUtils.getTransportId;
 import static org.briarproject.bramble.util.StringUtils.getRandomString;
 import static org.briarproject.briar.api.client.MessageQueueManager.QUEUE_STATE_KEY;
 import static org.briarproject.briar.api.introduction.IntroductionConstants.ALICE_MAC_KEY_LABEL;
@@ -372,7 +372,7 @@ public class IntroductionIntegrationTest
 		TransportProperties tp = new TransportProperties(
 				Collections.singletonMap("key", "value"));
 		c0.getTransportPropertyManager()
-				.mergeLocalProperties(new TransportId("fake"), tp);
+				.mergeLocalProperties(getTransportId(), tp);
 		sync0To1(1, true);
 
 		// sync second response
diff --git a/briar-core/src/test/java/org/briarproject/briar/introduction/IntroductionManagerImplTest.java b/briar-core/src/test/java/org/briarproject/briar/introduction/IntroductionManagerImplTest.java
index ef05fe8a2e105959507ff56dbf3ce62f617c87b5..fa480dc1a5049e69e75385d8d6b2d46a81eec2f2 100644
--- a/briar-core/src/test/java/org/briarproject/briar/introduction/IntroductionManagerImplTest.java
+++ b/briar-core/src/test/java/org/briarproject/briar/introduction/IntroductionManagerImplTest.java
@@ -33,9 +33,9 @@ import java.util.Map;
 
 import static org.briarproject.bramble.api.sync.SyncConstants.MESSAGE_HEADER_LENGTH;
 import static org.briarproject.bramble.test.TestUtils.getAuthor;
+import static org.briarproject.bramble.test.TestUtils.getClientId;
 import static org.briarproject.bramble.test.TestUtils.getRandomBytes;
 import static org.briarproject.bramble.test.TestUtils.getRandomId;
-import static org.briarproject.bramble.util.StringUtils.getRandomString;
 import static org.briarproject.briar.api.introduction.IntroductionConstants.GROUP_ID_1;
 import static org.briarproject.briar.api.introduction.IntroductionConstants.GROUP_ID_2;
 import static org.briarproject.briar.api.introduction.IntroductionConstants.ROLE;
@@ -79,7 +79,7 @@ public class IntroductionManagerImplTest extends BriarTestCase {
 		introducee2 =
 				new Contact(contactId2, author2, localAuthorId2, true, true);
 
-		ClientId clientId = new ClientId(getRandomString(5));
+		ClientId clientId = getClientId();
 		introductionGroup1 = new Group(new GroupId(getRandomId()),
 				clientId, new byte[0]);
 		introductionGroup2 = new Group(new GroupId(getRandomId()),
diff --git a/briar-core/src/test/java/org/briarproject/briar/introduction/MessageSenderTest.java b/briar-core/src/test/java/org/briarproject/briar/introduction/MessageSenderTest.java
index ed47f104e03283435240829144574876f0402128..56522918d7a218f39e53400552f8719406fe9f5e 100644
--- a/briar-core/src/test/java/org/briarproject/briar/introduction/MessageSenderTest.java
+++ b/briar-core/src/test/java/org/briarproject/briar/introduction/MessageSenderTest.java
@@ -10,12 +10,9 @@ import org.briarproject.bramble.api.db.DatabaseComponent;
 import org.briarproject.bramble.api.db.DbException;
 import org.briarproject.bramble.api.db.Metadata;
 import org.briarproject.bramble.api.db.Transaction;
-import org.briarproject.bramble.api.sync.ClientId;
 import org.briarproject.bramble.api.sync.Group;
 import org.briarproject.bramble.api.sync.GroupId;
 import org.briarproject.bramble.api.system.Clock;
-import org.briarproject.bramble.test.TestUtils;
-import org.briarproject.bramble.util.StringUtils;
 import org.briarproject.briar.api.client.MessageQueueManager;
 import org.briarproject.briar.api.client.SessionId;
 import org.briarproject.briar.test.BriarTestCase;
@@ -24,6 +21,9 @@ import org.jmock.Mockery;
 import org.junit.Test;
 
 import static org.briarproject.bramble.api.identity.AuthorConstants.MAX_SIGNATURE_LENGTH;
+import static org.briarproject.bramble.test.TestUtils.getClientId;
+import static org.briarproject.bramble.test.TestUtils.getRandomBytes;
+import static org.briarproject.bramble.test.TestUtils.getRandomId;
 import static org.briarproject.briar.api.introduction.IntroductionConstants.GROUP_ID;
 import static org.briarproject.briar.api.introduction.IntroductionConstants.MAC;
 import static org.briarproject.briar.api.introduction.IntroductionConstants.SESSION_ID;
@@ -59,13 +59,11 @@ public class MessageSenderTest extends BriarTestCase {
 	@Test
 	public void testSendMessage() throws DbException, FormatException {
 		Transaction txn = new Transaction(null, false);
-		Group privateGroup =
-				new Group(new GroupId(TestUtils.getRandomId()),
-						new ClientId(StringUtils.getRandomString(5)),
-						new byte[0]);
-		SessionId sessionId = new SessionId(TestUtils.getRandomId());
-		byte[] mac = TestUtils.getRandomBytes(42);
-		byte[] sig = TestUtils.getRandomBytes(MAX_SIGNATURE_LENGTH);
+		Group privateGroup = new Group(new GroupId(getRandomId()),
+				getClientId(), new byte[0]);
+		SessionId sessionId = new SessionId(getRandomId());
+		byte[] mac = getRandomBytes(42);
+		byte[] sig = getRandomBytes(MAX_SIGNATURE_LENGTH);
 		long time = 42L;
 		BdfDictionary msg = BdfDictionary.of(
 				new BdfEntry(TYPE, TYPE_ACK),
@@ -76,7 +74,7 @@ public class MessageSenderTest extends BriarTestCase {
 		);
 		BdfList bodyList =
 				BdfList.of(TYPE_ACK, sessionId.getBytes(), mac, sig);
-		byte[] body = TestUtils.getRandomBytes(8);
+		byte[] body = getRandomBytes(8);
 		Metadata metadata = new Metadata();
 
 		context.checking(new Expectations() {{