소스 검색

Remove usage of internal StorageConnectionString in repository-azure (#94054)

This change replaces the usage of the internal Azure API, that parses the connection string in order to retrieve the primary and secondary URI's, with our own implementation.
Chris Hegarty 2 년 전
부모
커밋
e5649bda9b

+ 1 - 6
modules/repository-azure/src/main/java/org/elasticsearch/repositories/azure/AzureClientProvider.java

@@ -28,11 +28,9 @@ import com.azure.core.http.HttpResponse;
 import com.azure.core.http.ProxyOptions;
 import com.azure.core.http.netty.NettyAsyncHttpClientBuilder;
 import com.azure.core.http.policy.HttpPipelinePolicy;
-import com.azure.core.util.logging.ClientLogger;
 import com.azure.storage.blob.BlobServiceAsyncClient;
 import com.azure.storage.blob.BlobServiceClient;
 import com.azure.storage.blob.BlobServiceClientBuilder;
-import com.azure.storage.common.implementation.connectionstring.StorageConnectionString;
 import com.azure.storage.common.policy.RequestRetryOptions;
 
 import org.apache.logging.log4j.LogManager;
@@ -95,7 +93,6 @@ class AzureClientProvider extends AbstractLifecycleComponent {
     private final EventLoopGroup eventLoopGroup;
     private final ConnectionProvider connectionProvider;
     private final ByteBufAllocator byteBufAllocator;
-    private final ClientLogger clientLogger = new ClientLogger(AzureClientProvider.class);
     private final LoopResources nioLoopResources;
     private volatile boolean closed = false;
 
@@ -176,9 +173,7 @@ class AzureClientProvider extends AbstractLifecycleComponent {
         }
 
         if (locationMode.isSecondary()) {
-            // TODO: maybe extract this logic so we don't need to have a client logger around?
-            StorageConnectionString storageConnectionString = StorageConnectionString.create(connectionString, clientLogger);
-            String secondaryUri = storageConnectionString.getBlobEndpoint().getSecondaryUri();
+            String secondaryUri = settings.getStorageEndpoint().secondaryURI();
             if (secondaryUri == null) {
                 throw new IllegalArgumentException(
                     "Unable to configure an AzureClient using a secondary location without a secondary " + "endpoint"

+ 3 - 5
modules/repository-azure/src/main/java/org/elasticsearch/repositories/azure/AzureStorageService.java

@@ -10,7 +10,6 @@ package org.elasticsearch.repositories.azure;
 
 import com.azure.core.http.ProxyOptions;
 import com.azure.core.util.logging.ClientLogger;
-import com.azure.storage.common.implementation.connectionstring.StorageConnectionString;
 import com.azure.storage.common.policy.RequestRetryOptions;
 import com.azure.storage.common.policy.RetryPolicyType;
 
@@ -125,10 +124,9 @@ public class AzureStorageService {
 
     // non-static, package private for testing
     RequestRetryOptions getRetryOptions(LocationMode locationMode, AzureStorageSettings azureStorageSettings) {
-        String connectString = azureStorageSettings.getConnectString();
-        StorageConnectionString storageConnectionString = StorageConnectionString.create(connectString, clientLogger);
-        String primaryUri = storageConnectionString.getBlobEndpoint().getPrimaryUri();
-        String secondaryUri = storageConnectionString.getBlobEndpoint().getSecondaryUri();
+        AzureStorageSettings.StorageEndpoint endpoint = azureStorageSettings.getStorageEndpoint();
+        String primaryUri = endpoint.primaryURI();
+        String secondaryUri = endpoint.secondaryURI();
 
         if (locationMode == LocationMode.PRIMARY_THEN_SECONDARY && secondaryUri == null) {
             throw new IllegalArgumentException("Unable to use " + locationMode + " location mode without a secondary location URI");

+ 54 - 0
modules/repository-azure/src/main/java/org/elasticsearch/repositories/azure/AzureStorageSettings.java

@@ -22,6 +22,8 @@ import org.elasticsearch.core.TimeValue;
 import java.net.InetAddress;
 import java.net.InetSocketAddress;
 import java.net.Proxy;
+import java.net.URI;
+import java.net.URISyntaxException;
 import java.net.UnknownHostException;
 import java.util.Collections;
 import java.util.HashMap;
@@ -266,4 +268,56 @@ final class AzureStorageSettings {
         final String fullKey = k.toConcreteKey(groupName).toString();
         return setting.getConcreteSetting(fullKey).get(settings);
     }
+
+    private static final String BLOB_ENDPOINT_NAME = "BlobEndpoint";
+    private static final String BLOB_SECONDARY_ENDPOINT_NAME = "BlobSecondaryEndpoint";
+
+    record StorageEndpoint(String primaryURI, @Nullable String secondaryURI) {}
+
+    StorageEndpoint getStorageEndpoint() {
+        String primaryURI = getProperty(BLOB_ENDPOINT_NAME);
+        String secondaryURI = getProperty(BLOB_SECONDARY_ENDPOINT_NAME);
+        if (primaryURI != null) {
+            return new StorageEndpoint(primaryURI, secondaryURI);
+        }
+        return new StorageEndpoint(deriveURIFromSettings(true), deriveURIFromSettings(false));
+    }
+
+    /**
+     * Returns the value for the given property name, or null if not configured.
+     * @throws IllegalArgumentException if the connectionString is malformed
+     */
+    private String getProperty(String propertyName) {
+        final String[] settings = getConnectString().split(";");
+        for (int i = 0; i < settings.length; i++) {
+            String setting = settings[i].trim();
+            if (setting.length() > 0) {
+                final int idx = setting.indexOf("=");
+                if (idx == -1 || idx == 0 || idx == settings[i].length() - 1) {
+                    new IllegalArgumentException("Invalid connection string: " + getConnectString());
+                }
+                if (propertyName.equals(setting.substring(0, idx))) {
+                    return setting.substring(idx + 1);
+                }
+            }
+        }
+        return null;
+    }
+
+    private static final String DEFAULT_DNS = "core.windows.net";
+
+    /** Derives the primary or secondary endpoint from the settings. */
+    private String deriveURIFromSettings(boolean isPrimary) {
+        String uriString = new StringBuilder().append("https://")
+            .append(account)
+            .append(isPrimary ? "" : "-secondary")
+            .append(".blob.")
+            .append(Strings.isNullOrEmpty(endpointSuffix) ? DEFAULT_DNS : endpointSuffix)
+            .toString();
+        try {
+            return new URI(uriString).toString();  // validates the URI
+        } catch (URISyntaxException e) {
+            throw new IllegalArgumentException(e);
+        }
+    }
 }

+ 20 - 4
modules/repository-azure/src/test/java/org/elasticsearch/repositories/azure/AzureStorageServiceTests.java

@@ -350,9 +350,17 @@ public class AzureStorageServiceTests extends ESTestCase {
         }
     }
 
-    public void testRetryConfigurationForSecondaryFallbackLocationMode() throws Exception {
+    public void testRetryConfigurationForSecondaryFallbackLocationMode1() throws Exception {
+        testRetryConfigurationForSecondaryFallbackLocationModeImpl(true);
+    }
+
+    public void testRetryConfigurationForSecondaryFallbackLocationMode2() throws Exception {
+        testRetryConfigurationForSecondaryFallbackLocationModeImpl(false);
+    }
+
+    public void testRetryConfigurationForSecondaryFallbackLocationModeImpl(boolean endpointSetting) throws Exception {
         final String endpoint;
-        if (randomBoolean()) {
+        if (endpointSetting) {
             endpoint = "core.windows.net";
         } else {
             endpoint = "ignored;BlobEndpoint=https://myaccount1.blob.core.windows.net;"
@@ -375,9 +383,17 @@ public class AzureStorageServiceTests extends ESTestCase {
         }
     }
 
-    public void testRetryConfigurationForPrimaryFallbackLocationMode() throws Exception {
+    public void testRetryConfigurationForPrimaryFallbackLocationMode1() throws Exception {
+        testRetryConfigurationForPrimaryFallbackLocationModeImpl(true);
+    }
+
+    public void testRetryConfigurationForPrimaryFallbackLocationMode2() throws Exception {
+        testRetryConfigurationForPrimaryFallbackLocationModeImpl(false);
+    }
+
+    private void testRetryConfigurationForPrimaryFallbackLocationModeImpl(boolean endpointSetting) throws Exception {
         final String endpoint;
-        if (randomBoolean()) {
+        if (endpointSetting) {
             endpoint = "core.windows.net";
         } else {
             endpoint = "ignored;BlobEndpoint=https://myaccount1.blob.core.windows.net;"