Ignore URI when local.mongo.port is set
This commit makes sure that if `local.mongo.port` is set, a `MongoClient` on the embedded MongoDB instance is created. When an embedded instance is detected, only the `host` property is used and the `uri` is ignored if set. This makes sure that the auto-configured `MongoClient` automatically switches to the embedded server, even if a production uri has been specified. Closes gh-8219
This commit is contained in:
@@ -202,35 +202,63 @@ public class MongoProperties {
|
||||
public MongoClient createMongoClient(MongoClientOptions options,
|
||||
Environment environment) throws UnknownHostException {
|
||||
try {
|
||||
if (hasCustomAddress() || hasCustomCredentials()) {
|
||||
if (this.uri != null) {
|
||||
throw new IllegalStateException("Invalid mongo configuration, "
|
||||
+ "either uri or host/port/credentials must be specified");
|
||||
}
|
||||
if (options == null) {
|
||||
options = MongoClientOptions.builder().build();
|
||||
}
|
||||
List<MongoCredential> credentials = new ArrayList<MongoCredential>();
|
||||
if (hasCustomCredentials()) {
|
||||
String database = this.authenticationDatabase == null
|
||||
? getMongoClientDatabase() : this.authenticationDatabase;
|
||||
credentials.add(MongoCredential.createCredential(this.username,
|
||||
database, this.password));
|
||||
}
|
||||
String host = this.host == null ? "localhost" : this.host;
|
||||
int port = determinePort(environment);
|
||||
return new MongoClient(
|
||||
Collections.singletonList(new ServerAddress(host, port)),
|
||||
credentials, options);
|
||||
Integer embeddedPort = getEmbeddedPort(environment);
|
||||
if (embeddedPort != null) {
|
||||
return createEmbeddedMongoClient(options, embeddedPort);
|
||||
}
|
||||
// The options and credentials are in the URI
|
||||
return new MongoClient(new MongoClientURI(determineUri(), builder(options)));
|
||||
return createNetworkMongoClient(options);
|
||||
}
|
||||
finally {
|
||||
clearPassword();
|
||||
}
|
||||
}
|
||||
|
||||
private Integer getEmbeddedPort(Environment environment) {
|
||||
if (environment != null) {
|
||||
String localPort = environment.getProperty("local.mongo.port");
|
||||
if (localPort != null) {
|
||||
return Integer.valueOf(localPort);
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private MongoClient createEmbeddedMongoClient(MongoClientOptions options, int port) {
|
||||
if (options == null) {
|
||||
options = MongoClientOptions.builder().build();
|
||||
}
|
||||
String host = this.host == null ? "localhost" : this.host;
|
||||
return new MongoClient(
|
||||
Collections.singletonList(new ServerAddress(host, port)),
|
||||
Collections.<MongoCredential>emptyList(), options);
|
||||
}
|
||||
|
||||
private MongoClient createNetworkMongoClient(MongoClientOptions options) {
|
||||
if (hasCustomAddress() || hasCustomCredentials()) {
|
||||
if (this.uri != null) {
|
||||
throw new IllegalStateException("Invalid mongo configuration, "
|
||||
+ "either uri or host/port/credentials must be specified");
|
||||
}
|
||||
if (options == null) {
|
||||
options = MongoClientOptions.builder().build();
|
||||
}
|
||||
List<MongoCredential> credentials = new ArrayList<MongoCredential>();
|
||||
if (hasCustomCredentials()) {
|
||||
String database = this.authenticationDatabase == null
|
||||
? getMongoClientDatabase() : this.authenticationDatabase;
|
||||
credentials.add(MongoCredential.createCredential(this.username,
|
||||
database, this.password));
|
||||
}
|
||||
String host = this.host == null ? "localhost" : this.host;
|
||||
int port = this.port != null ? this.port : DEFAULT_PORT;
|
||||
return new MongoClient(
|
||||
Collections.singletonList(new ServerAddress(host, port)),
|
||||
credentials, options);
|
||||
}
|
||||
// The options and credentials are in the URI
|
||||
return new MongoClient(new MongoClientURI(determineUri(), builder(options)));
|
||||
}
|
||||
|
||||
private boolean hasCustomAddress() {
|
||||
return this.host != null || this.port != null;
|
||||
}
|
||||
@@ -239,24 +267,6 @@ public class MongoProperties {
|
||||
return this.username != null && this.password != null;
|
||||
}
|
||||
|
||||
private int determinePort(Environment environment) {
|
||||
if (this.port == null) {
|
||||
return DEFAULT_PORT;
|
||||
}
|
||||
if (this.port == 0) {
|
||||
if (environment != null) {
|
||||
String localPort = environment.getProperty("local.mongo.port");
|
||||
if (localPort != null) {
|
||||
return Integer.valueOf(localPort);
|
||||
}
|
||||
}
|
||||
throw new IllegalStateException(
|
||||
"spring.data.mongodb.port=0 and no local mongo port configuration "
|
||||
+ "is available");
|
||||
}
|
||||
return this.port;
|
||||
}
|
||||
|
||||
private Builder builder(MongoClientOptions options) {
|
||||
if (options != null) {
|
||||
return MongoClientOptions.builder(options);
|
||||
|
||||
@@ -158,7 +158,6 @@ public class EmbeddedMongoAutoConfiguration {
|
||||
}
|
||||
|
||||
private void setEmbeddedPort(int port) {
|
||||
this.properties.setPort(port);
|
||||
setPortProperty(this.context, port);
|
||||
}
|
||||
|
||||
|
||||
@@ -33,6 +33,7 @@ import org.springframework.boot.context.properties.EnableConfigurationProperties
|
||||
import org.springframework.boot.test.util.EnvironmentTestUtils;
|
||||
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.mock.env.MockEnvironment;
|
||||
import org.springframework.test.util.ReflectionTestUtils;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
@@ -49,6 +50,8 @@ public class MongoPropertiesTests {
|
||||
@Rule
|
||||
public ExpectedException thrown = ExpectedException.none();
|
||||
|
||||
private MockEnvironment environment = new MockEnvironment();
|
||||
|
||||
@Test
|
||||
public void canBindCharArrayPassword() {
|
||||
// gh-1572
|
||||
@@ -151,6 +154,17 @@ public class MongoPropertiesTests {
|
||||
properties.createMongoClient(null, null);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void uriIsIgnoredInEmbeddedMode() throws UnknownHostException {
|
||||
MongoProperties properties = new MongoProperties();
|
||||
properties.setUri("mongodb://mongo.example.com:1234/mydb");
|
||||
this.environment.setProperty("local.mongo.port", "4000");
|
||||
MongoClient client = properties.createMongoClient(null, this.environment);
|
||||
List<ServerAddress> allAddresses = extractServerAddresses(client);
|
||||
assertThat(allAddresses).hasSize(1);
|
||||
assertServerAddress(allAddresses.get(0), "localhost", 4000);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void allMongoClientOptionsCanBeSet() throws UnknownHostException {
|
||||
MongoClientOptions.Builder builder = MongoClientOptions.builder();
|
||||
|
||||
Reference in New Issue
Block a user