2017-02-15 18 views
2

У меня есть класс утилиты, из которого я звоню в службу api. Если все в порядке, я получу желаемый результат, который находится в строковом формате. Итак, это случай успеха. Но может случиться так, что я получаю ошибку 404, если сервер не работает. В таких случаях я хочу назвать это api, предположим, 3 раза с интервалом в 1 секунду между ними. Если в течение этих трех попыток я получаю успех от Api, тогда я не буду проверять api и записывать результат, Или если после 3 попыток он все еще выдает ошибку, я не буду продолжать и просто зарегистрировать ошибку. мой класс UtilityВ akka actor, если сообщение является исключением, как вызвать то же самое за несколько раз с фиксированным интервалом между ними

public class Utils { 

public void doOperation(String service_Url) throws Exception { 
    Object message= someFunction(service_Url);//this function is calling the service api 
    final ActorSystem system = ActorSystem.create("helloakka"); 
    final ActorRef akkaBot=system.actorOf(Props.create(MyUntypedActor.class), "akkaBot"); 
    akkaBot.tell(message, ActorRef.noSender()); 
} 

} 

Вот актер

public class MyUntypedActor extends UntypedActor { 
    @Override 
    public void onReceive(Object message) { 
    if (message instanceof HTTPException) { 
     System.out.println(message); 
     //Here as it got exception.I want to call the actor 3 times with 1 second interval between them 
    } 
else if (message instanceof String) { 
     System.out.println(message); 
     getSender().tell(value, getSelf()); 
    } 
else { 
     unhandled(message); 
    } 
    } 
} 

Целью является проверить конкретный апи работает или не используя Akka actor.If API-интерфейс возвращает исключение, то назвать это апи используя актеру 3 раза с интервалом в 1 секунду между каждым вызовом. Если после 3-х раз мы все равно получаем ошибку, тогда регистрируем ошибку, если при повторной попытке получаем желаемый результат, запишите его.

Я не знаю, как достичь этого, используя акк-актеров. Пожалуйста, расскажите мне, если вы знаете.

ответ

2

То, о чем вы просите, может быть выполнено с небольшой модификацией организации вашего кода. Было бы проще, если бы ваш актер выполнил все запросы, а не только запросы после сбоя.

Вам сначала нужно каким-то образом представлять неудачи:

public class RequestFailure { 
    public String request; 
    public int count; 

    public RequestFailure(String r, int c) { 
    request = r; 
    count = c; 
    } 
} 

Этот класс может затем быть тип сообщения, отправленного на ваш актер, который будет действовать соответствующим образом:

public class MyUntypedActor extends UntypedActor { 
    public void onReceive(Object message) { 
    if(message instanceOf String) { 
     Object response = someFunction((String) message); 
     if(response instanceOf HTTPException) { 
     Thread.sleep(1000); 
     getSelf().tell(new RequestFailure((String) message, 1), getSender()); 
     } 
     else 
     getSender().tell(response, getSelf()) 
    } 
    else if(message instanceOf RequestFailure) { 
     RequestFailure rf = (RequestFailure) message; 
     if(rf.count <= 3) { 
     Object response = someFunction(rf.request); 
     if(response instanceOf HTTPException) { 
      Thread.sleep(1000); 
      getSelf().tell(new RequestFailure(rf.request, rf.count + 1), getSender(); 
     } 
     else 
      getSender().tell(response, getSelf()) 
     } 
     } 
     else 
     //FIXME : question doesn't specify what to return 
     //  if max count reached 
    } 
    } 
} 

Вы бы тогда запросите Actor с запросом String, чтобы начать процесс.

+1

Если его успех в первый раз, он работает по желанию. Но если при первой попытке это ошибка, то он создает объект RequestFailure и вызывает второй раз с использованием rf.request.If во второй раз (или в любой попытке) его успех тогда как его не экземпляр исключения, поэтому 'getSender(). tell (response, getSelf());' выполняется. Но здесь происходит то, что происходит в public void onReceive (сообщение Object) {'метод' class MyUntypedActor' получает ответ, что 'getSender(). Tell' отправляет, и актер выполняется снова и снова. Это происходит, когда count > 3, а затем отправить getSender() @Ramon J –

+2

@MithunDebnath Ответ обновлен. Я ссылался на «MyUntypedActor» как отправитель исходного запроса вместо фактического отправителя. Дайте мне знать, если вы увидите какие-либо другие проблемы ... –

+1

Я буду тестировать код завтра, поскольку у меня нет приложения со мной прямо сейчас. Одна вещь, которую я заметил, но я забыл спросить вас. 'if (rf.count < = 3) {Object response = someFunction (rf.request); 'здесь if' if (response instanceOf HTTPException) {'тогда вы написали' getSelf(). Tell (новое сообщение RequestFailure ((String), rf.count + 1), getSender(); 'не должно быть' getSelf(). tell (new RequestFailure ((String) rf.request, rf.count + 1), getSender(); '. Другое дело, если количество достигнуто max номер Я хочу отправить фактическому отправителю информацию о том, что 'максимальное количество достигнуто'. Из чего еще я его отправил? @ Ramon –