diff --git a/service/config/sample.yml b/service/config/sample.yml index f680be176..6300a3b9c 100644 --- a/service/config/sample.yml +++ b/service/config/sample.yml @@ -457,6 +457,7 @@ turn: password: secret://turn.cloudflare.password urls: - turns:turn.cloudflare.example.com:443?transport=tcp + hostname: turn.cloudflare.example.com linkDevice: secret: secret://linkDevice.secret diff --git a/service/src/main/java/org/whispersystems/textsecuregcm/auth/TurnToken.java b/service/src/main/java/org/whispersystems/textsecuregcm/auth/TurnToken.java index a7a9df4fd..738e0810d 100644 --- a/service/src/main/java/org/whispersystems/textsecuregcm/auth/TurnToken.java +++ b/service/src/main/java/org/whispersystems/textsecuregcm/auth/TurnToken.java @@ -10,7 +10,4 @@ import java.util.List; public record TurnToken(String username, String password, List urls, @Nullable List urlsWithIps, @Nullable String hostname) { - public TurnToken(String username, String password, List urls) { - this(username, password, urls, null, null); - } } diff --git a/service/src/main/java/org/whispersystems/textsecuregcm/auth/TurnTokenGenerator.java b/service/src/main/java/org/whispersystems/textsecuregcm/auth/TurnTokenGenerator.java index 48e57727e..bd1b2400f 100644 --- a/service/src/main/java/org/whispersystems/textsecuregcm/auth/TurnTokenGenerator.java +++ b/service/src/main/java/org/whispersystems/textsecuregcm/auth/TurnTokenGenerator.java @@ -41,6 +41,7 @@ public class TurnTokenGenerator { private final String cloudflareTurnUsername; private final String cloudflareTurnPassword; private final List cloudflareTurnUrls; + private final String cloudflareTurnHostname; public TurnTokenGenerator(final DynamicConfigurationManager dynamicConfigurationManager, final byte[] turnSecret, final CloudflareTurnConfiguration cloudflareTurnConfiguration) { @@ -51,6 +52,7 @@ public class TurnTokenGenerator { this.cloudflareTurnUsername = cloudflareTurnConfiguration.username().value(); this.cloudflareTurnPassword = cloudflareTurnConfiguration.password().value(); this.cloudflareTurnUrls = cloudflareTurnConfiguration.urls(); + this.cloudflareTurnHostname = cloudflareTurnConfiguration.hostname(); } @Deprecated @@ -63,7 +65,7 @@ public class TurnTokenGenerator { } public TurnToken generateForCloudflareBeta() { - return new TurnToken(cloudflareTurnUsername, cloudflareTurnPassword, cloudflareTurnUrls); + return new TurnToken(cloudflareTurnUsername, cloudflareTurnPassword, cloudflareTurnUrls, null, cloudflareTurnHostname); } private TurnToken generateToken(String hostname, List urlsWithIps, List urlsWithHostname) { diff --git a/service/src/main/java/org/whispersystems/textsecuregcm/configuration/CloudflareTurnConfiguration.java b/service/src/main/java/org/whispersystems/textsecuregcm/configuration/CloudflareTurnConfiguration.java index 7dd5a80dd..040eb8a9b 100644 --- a/service/src/main/java/org/whispersystems/textsecuregcm/configuration/CloudflareTurnConfiguration.java +++ b/service/src/main/java/org/whispersystems/textsecuregcm/configuration/CloudflareTurnConfiguration.java @@ -12,6 +12,6 @@ import javax.validation.constraints.NotBlank; import javax.validation.constraints.NotNull; public record CloudflareTurnConfiguration(@NotNull SecretString username, @NotNull SecretString password, - @Valid @NotNull List<@NotBlank String> urls) { + @Valid @NotNull List<@NotBlank String> urls, @NotBlank String hostname) { } diff --git a/service/src/test/java/org/whispersystems/textsecuregcm/auth/TurnTokenGeneratorTest.java b/service/src/test/java/org/whispersystems/textsecuregcm/auth/TurnTokenGeneratorTest.java index fb94e273b..af95da260 100644 --- a/service/src/test/java/org/whispersystems/textsecuregcm/auth/TurnTokenGeneratorTest.java +++ b/service/src/test/java/org/whispersystems/textsecuregcm/auth/TurnTokenGeneratorTest.java @@ -20,7 +20,7 @@ import org.whispersystems.textsecuregcm.storage.DynamicConfigurationManager; public class TurnTokenGeneratorTest { private static final CloudflareTurnConfiguration CLOUDFLARE_TURN_CONFIGURATION = new CloudflareTurnConfiguration( - new SecretString("cf_username"), new SecretString("cf_password"), List.of("turn:cloudflare.example.com")); + new SecretString("cf_username"), new SecretString("cf_password"), List.of("turn:cloudflare.example.com"), "cloudflare.example.com"); @Test public void testAlwaysSelectFirst() throws JsonProcessingException { diff --git a/service/src/test/java/org/whispersystems/textsecuregcm/controllers/CallRoutingControllerTest.java b/service/src/test/java/org/whispersystems/textsecuregcm/controllers/CallRoutingControllerTest.java index 59ecb1cd6..74c821c25 100644 --- a/service/src/test/java/org/whispersystems/textsecuregcm/controllers/CallRoutingControllerTest.java +++ b/service/src/test/java/org/whispersystems/textsecuregcm/controllers/CallRoutingControllerTest.java @@ -59,7 +59,7 @@ class CallRoutingControllerTest { private static final TurnTokenGenerator turnTokenGenerator = new TurnTokenGenerator(dynamicConfigurationManager, "bloop".getBytes(StandardCharsets.UTF_8), new CloudflareTurnConfiguration(new SecretString("cf_username"), new SecretString("cf_password"), - List.of("turn:cf.example.com"))); + List.of("turn:cf.example.com"), "cf.example.com")); private static final TurnCallRouter turnCallRouter = mock(TurnCallRouter.class); private static final ResourceExtension resources = ResourceExtension.builder() @@ -128,7 +128,7 @@ class CallRoutingControllerTest { TurnToken token = response.readEntity(TurnToken.class); assertThat(token.username()).isNotEmpty(); assertThat(token.password()).isNotEmpty(); - assertThat(token.hostname()).isNull(); + assertThat(token.hostname()).isNotEmpty(); assertThat(token.urlsWithIps()).isNull(); assertThat(token.urls()).isEqualTo(List.of("turn:cf.example.com")); } diff --git a/service/src/test/java/org/whispersystems/textsecuregcm/grpc/CallingGrpcServiceTest.java b/service/src/test/java/org/whispersystems/textsecuregcm/grpc/CallingGrpcServiceTest.java index 3f75c7eb9..b8b5d46c5 100644 --- a/service/src/test/java/org/whispersystems/textsecuregcm/grpc/CallingGrpcServiceTest.java +++ b/service/src/test/java/org/whispersystems/textsecuregcm/grpc/CallingGrpcServiceTest.java @@ -48,9 +48,10 @@ class CallingGrpcServiceTest extends SimpleBaseGrpcTest urls = List.of("first", "second"); + final String hostname = "hostname"; MockUtils.updateRateLimiterResponseToAllow(turnCredentialRateLimiter, AUTHENTICATED_ACI); - when(turnTokenGenerator.generate(any())).thenReturn(new TurnToken(username, password, urls)); + when(turnTokenGenerator.generate(any())).thenReturn(new TurnToken(username, password, urls, null, hostname)); final GetTurnCredentialsResponse response = authenticatedServiceStub().getTurnCredentials(GetTurnCredentialsRequest.newBuilder().build()); diff --git a/service/src/test/resources/config/test.yml b/service/src/test/resources/config/test.yml index 2e92b7fb6..6c69461ac 100644 --- a/service/src/test/resources/config/test.yml +++ b/service/src/test/resources/config/test.yml @@ -448,6 +448,7 @@ turn: password: secret://turn.cloudflare.password urls: - turns:turn.cloudflare.example.com:443?transport=tcp + hostname: turn.cloudflare.example.com linkDevice: secret: secret://linkDevice.secret