Skip to content

Commit

Permalink
Bug 1774224: User should be prompt with the right message when tokens…
Browse files Browse the repository at this point in the history
… in azure cli expires.
  • Loading branch information
wangmingliang-ms committed Nov 3, 2020
1 parent 7a063e1 commit 73876a6
Show file tree
Hide file tree
Showing 3 changed files with 72 additions and 27 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
/*
* Copyright (c) Microsoft Corporation
*
* All rights reserved.
*
* MIT License
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated
* documentation files (the "Software"), to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and
* to permit persons to whom the Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all copies or substantial portions of
* the Software.
*
* THE SOFTWARE IS PROVIDED *AS IS*, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO
* THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/

package com.microsoft.azure.toolkit.lib.common.rest;

import com.google.common.base.Throwables;
import com.microsoft.aad.adal4j.AuthenticationException;
import com.microsoft.azuretools.enums.ErrorEnum;
import com.microsoft.azuretools.exception.AzureRuntimeException;
import okhttp3.Interceptor;
import okhttp3.Request;
import okhttp3.Response;

import java.io.IOException;
import java.net.UnknownHostException;
import java.util.List;

/**
* Interceptor to handle REST API related exceptions
*/
public class RestExceptionHandlerInterceptor implements Interceptor {
@Override
public Response intercept(final Chain chain) throws IOException {
try {
final Request request = chain.request();
return chain.proceed(request);
} catch (final Exception ex) {
final List<Throwable> exceptions = Throwables.getCausalChain(ex);
if (exceptions.stream().anyMatch(e -> e instanceof UnknownHostException)) {
throw new AzureRuntimeException(ErrorEnum.UNKNOWN_HOST_EXCEPTION);
} else if (exceptions.stream().anyMatch(e -> e instanceof AuthenticationException)) {
throw new AzureRuntimeException(ErrorEnum.INVALID_AUTHENTICATION);
}
throw ex;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,8 @@
public enum ErrorEnum {
UNKNOWN_HOST_EXCEPTION(100000, "Encountered an unknown host exception.",
"It seems you have an unstable network at the moment, please try again when network is available."),
INVALID_AUTHENTICATION(100401, "Invalid authentication",
"It seems you are not signed in properly, try signing out and then signing in again later"),
SOCKET_TIMEOUT_EXCEPTION(100002, "Encountered a socket timeout exception.",
"Timeout when accessing azure, please try your operation again."),
FAILED_TO_GET_ACCESS_TOKEN_BY_CLI(100003, "Failed to get access token by Azure CLI command.",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@

package com.microsoft.azuretools.sdkmanage;

import com.google.common.base.Throwables;
import com.microsoft.azure.AzureEnvironment;
import com.microsoft.azure.arm.resources.AzureConfigurable;
import com.microsoft.azure.credentials.AzureTokenCredentials;
Expand All @@ -31,17 +30,14 @@
import com.microsoft.azure.management.appplatform.v2019_05_01_preview.implementation.AppPlatformManager;
import com.microsoft.azure.management.resources.Subscription;
import com.microsoft.azure.management.resources.Tenant;
import com.microsoft.azure.toolkit.lib.common.rest.RestExceptionHandlerInterceptor;
import com.microsoft.azuretools.authmanage.*;
import com.microsoft.azuretools.exception.AzureRuntimeException;
import com.microsoft.azuretools.enums.ErrorEnum;
import com.microsoft.azuretools.telemetry.TelemetryInterceptor;
import com.microsoft.azuretools.utils.AzureRegisterProviderNamespaces;
import com.microsoft.azuretools.utils.Pair;
import org.apache.commons.lang3.StringUtils;
import rx.Observable;

import java.io.IOException;
import java.net.UnknownHostException;
import java.util.Collections;
import java.util.LinkedList;
import java.util.List;
Expand Down Expand Up @@ -128,10 +124,10 @@ public List<Pair<Subscription, Tenant>> getSubscriptionsWithTenant() throws IOEx
final Azure.Authenticated authentication = authTenant(getCurrentTenantId());
// could be multi tenant - return all subscriptions for the current account
final List<Tenant> tenants = getTenants(authentication);
for (Tenant tenant : tenants) {
for (final Tenant tenant : tenants) {
final Azure.Authenticated tenantAuthentication = authTenant(tenant.tenantId());
final List<Subscription> tenantSubscriptions = getSubscriptions(tenantAuthentication);
for (Subscription subscription : tenantSubscriptions) {
for (final Subscription subscription : tenantSubscriptions) {
subscriptions.add(new Pair<>(subscription, tenant));
}
}
Expand Down Expand Up @@ -234,51 +230,42 @@ public List<Subscription> getSubscriptions(String tenantId) {
return getSubscriptions(authTenant(tenantId));
}

private List<Subscription> getSubscriptions(Azure.Authenticated tenantAuthentication) {
return tenantAuthentication.subscriptions().listAsync()
.onErrorResumeNext(err -> {
LOGGER.warning(err.getMessage());
return Observable.empty();
})
private List<Subscription> getSubscriptions(Azure.Authenticated authentication) {
return authentication.subscriptions().listAsync()
.toList()
.toBlocking()
.singleOrDefault(Collections.emptyList());
}

private List<Tenant> getTenants(Azure.Authenticated authentication) {
try {
return authentication.tenants().listAsync()
.toList()
.toBlocking()
.singleOrDefault(Collections.emptyList());
} catch (Exception err) {
LOGGER.warning(Throwables.getStackTraceAsString(err));
if (Throwables.getCausalChain(err).stream().filter(e -> e instanceof UnknownHostException).count() > 0) {
throw new AzureRuntimeException(ErrorEnum.UNKNOWN_HOST_EXCEPTION);
} else if (err instanceof AzureRuntimeException) {
throw err;
}
return Collections.emptyList();
}
return authentication.tenants().listAsync()
.toList()
.toBlocking()
.singleOrDefault(Collections.emptyList());
}

protected Azure.Authenticated authTenant(String tenantId) {
final AzureTokenCredentials credentials = getCredentials(tenantId);
return Azure.configure()
.withInterceptor(new TelemetryInterceptor())
.withInterceptor(new RestExceptionHandlerInterceptor())
.withUserAgent(CommonSettings.USER_AGENT)
.authenticate(credentials);
}

protected AppPlatformManager authSpringCloud(String subscriptionId, String tenantId) {
final AzureTokenCredentials credentials = getCredentials(tenantId);
return buildAzureManager(AppPlatformManager.configure())
.withInterceptor(new TelemetryInterceptor())
.withInterceptor(new RestExceptionHandlerInterceptor())
.authenticate(credentials, subscriptionId);
}

protected InsightsManager authApplicationInsights(String subscriptionId, String tenantId) {
final AzureTokenCredentials credentials = getCredentials(tenantId);
return buildAzureManager(InsightsManager.configure())
.withInterceptor(new TelemetryInterceptor())
.withInterceptor(new RestExceptionHandlerInterceptor())
.authenticate(credentials, subscriptionId);
}
}

0 comments on commit 73876a6

Please sign in to comment.