Что может быть лучшим подходом для обработки java.net.UnknownHostException для пользователей AWS?
Мое приложение отправляет сообщение в раздел Amazon Simple Notification Service (SNS), но иногда (6/10) я получаю исключение java.net.UnknownHostException:sqs.ap-southeast-1.amazonaws.com. Причина исключения описана на форумах Amazon по веб-сервисам, пожалуйста, посмотрите: https://forums.aws.amazon.com/thread.jspa?messageID=499290&;.
Моя проблема похожа на ту, что описана на форумах Amazon, но моя скорость публикации сообщений в теме очень динамична. Это может быть 1 сообщение / секунда или 1 сообщение / минута или отсутствие сообщения в час. Я ищу более чистый, лучший и безопасный подход, который гарантирует отправку сообщения в тему SNS.
Описание проблемы в деталях:
Topic_Arn = arn темы SNS, где приложение хочет опубликовать сообщение
msg = Сообщение для отправки в теме
// Just a sample example which publish message to Amazon SNS topic
class SimpleNotificationService {
AmazonSNSClient mSnsClient = null;
static {
createSnsClient()
}
private void static createSnsClient() {
Region region = Region.getRegion(Regions.AP_SOUTHEAST_1);
AWSCredentials credentials = new
BasicAWSCredentials(AwsPropertyLoader.getInstance().getAccessKey(),
AwsPropertyLoader.getInstance().getSecretKey());
mSqsClient = new AmazonSQSClient(credentials);
mSqsClient.setRegion(region);
}
public void static publishMessage(String Topic_Arn, String msg) {
PublishRequest req = new PublishRequest(Topic_Arn, msg);
mSnsClient.publish(req);
}
}
класс, который вызывает SimpleNotificationService
class MessagingManager {
public void sendMessage(String message) {
String topic_arn = "arn:of:amazon:sns:topic";
SimpleNotificationService.publishMessage(topic_arn, message);
}
}
Обратите внимание, что это пример кода, а не мой настоящий код. Здесь может быть проблема дизайна класса, но, пожалуйста, игнорируйте их, если они не связаны с проблемой.
Мой мыслительный процесс говорит, что внутри sendMessage есть блок try-catch, поэтому, когда мы перехватываем UnknownHostException, снова повторяем попытку, но я не уверен, как написать это более безопасным, чистым и лучшим способом.
Так что класс MessagingManager будет выглядеть примерно так:
class MessagingManager {
public void sendMessage(String message) {
String topic_arn = "arn:of:amazon:sns:topic";
try {
SimpleNotificationService.publishMessage(topic_arn, message);
} catch (UnknownHostException uhe) {
// I need to catch AmazonClientException as aws throws
//AmazonClientException when sees UnknownHostException.
// I am mentioning UnknownHostException for non-aws user to understand
// my problem in better way.
sendMessage(message); // Isn't unsafe? - may falls into infinite loop
}
}
}
Я открыт для таких ответов: java.net.UnknownHostException: Неверное имя хоста для сервера: локальное, но моя задача - зависеть от решения на уровне кода приложения и меньше зависеть от изменений на компьютере. Поскольку мое серверное приложение будет работать во многих блоках (блоках разработчика, блоках тестирования или производственных блоках) Если изменения в хост-файлах компьютера и т. Д. Являются только гарантированным решением, то я предпочитаю включать их в изменения уровня кода.
2 ответа
Каждый AWS SDK реализует логику автоматического повтора. AWS SDK для Java автоматически повторяет запросы, и вы можете настроить параметры повторных попыток, используя класс ClientConfiguration.
Ниже приведен пример примера создания клиента SNS. Он повторяет 25 раз, если встречает UnKnownHostException. Используется заданный по умолчанию режим BackOff и повторная попытка. Если вы хотите иметь свой собственный, тогда вам нужно реализовать эти два интерфейса: http://docs.aws.amazon.com/AWSJavaSDK/latest/javadoc/com/amazonaws/retry/RetryPolicy.html
private void static createSnsClient() {
Region region = Region.getRegion(Regions.AP_SOUTHEAST_1);
AWSCredentials credentials = new
BasicAWSCredentials(AwsPropertyLoader.getInstance().getAccessKey(),
AwsPropertyLoader.getInstance().getSecretKey());
ClientConfiguration clientConfiguration = new ClientConfiguration();
clientConfiguration.setMaxErrorRetry(25);
clientConfiguration.setRetryPolicy(new RetryPolicy(null, null, 25, true));
mSnsClient = new AmazonSNSClient(credentials, clientConfiguration);
mSnsClient.setRegion(region);
}
Вы рассматривали возможность изучения TTL JVM для кэша DNS?
http://docs.aws.amazon.com/AWSSdkDocsJava/latest//DeveloperGuide/java-dg-jvm-ttl.html