2013-02-25 8 views
6

W mojej aplikacji testowej widzę wiadomości, które zostały przetworzone, a wyjątek jest automatycznie wstawiany do domyślnej wartości EasyNetQ_Default_Error_Queue, co jest świetne. Mogę wtedy z powodzeniem zrzucić lub zresetować te komunikaty za pomocą Hosepipe, która również działa dobrze, ale wymaga zejścia do linii poleceń i wywołania zarówno z Hosepipe, jak i RabbitMQ API, aby oczyścić kolejkę ponawianych wiadomości.Czy można łatwo subskrybować domyślną kolejkę błędów w programie EasyNetQ?

Myślę, że najłatwiejszym podejściem do mojej aplikacji jest po prostu zasubskrybowanie kolejki błędów, więc mogę ponownie przetworzyć je za pomocą tej samej infrastruktury. Ale w EastNetQ kolejka błędów wydaje się być wyjątkowa. Musimy subskrybować za pomocą odpowiedniego typu i routingu identyfikator, więc nie jestem pewien, co te wartości powinny być dla kolejki błędu:

bus.Subscribe<WhatShouldThisBe>("and-this", ReprocessErrorMessage);

mogę użyć prostego API zapisać się do kolejki błędów, lub czy muszę zagłębić się w advanced API?

Jeśli typ mojej oryginalnej wiadomości był TestMessage, to chciałbym być w stanie zrobić coś takiego:

bus.Subscribe<ErrorMessage<TestMessage>>("???", ReprocessErrorMessage);

gdzie ErrorMessage jest klasą dostarczone przez EasyNetQ owinąć wszystkie błędy. czy to możliwe?

Odpowiedz

3

Nie można użyć prostego API zapisać się do kolejki błędów, ponieważ nie wynika EasyNetQ typ kolejki nazewnictwa - może to jest coś, co powinno być ustalone;)

Ale zaawansowane API działa dobrze. Nie dostaniesz oryginalnej wiadomości, ale łatwo jest uzyskać reprezentację JSON, którą możesz całkiem odserializować (używając Newtonsoft.JSON). Oto przykład tego, co Twój kod subskrypcja powinna wyglądać następująco:

[Test] 
[Explicit("Requires a RabbitMQ server on localhost")] 
public void Should_be_able_to_subscribe_to_error_messages() 
{ 
    var errorQueueName = new Conventions().ErrorQueueNamingConvention(); 
    var queue = Queue.DeclareDurable(errorQueueName); 
    var autoResetEvent = new AutoResetEvent(false); 

    bus.Advanced.Subscribe<SystemMessages.Error>(queue, (message, info) => 
    { 
     var error = message.Body; 

     Console.Out.WriteLine("error.DateTime = {0}", error.DateTime); 
     Console.Out.WriteLine("error.Exception = {0}", error.Exception); 
     Console.Out.WriteLine("error.Message = {0}", error.Message); 
     Console.Out.WriteLine("error.RoutingKey = {0}", error.RoutingKey); 

     autoResetEvent.Set(); 
     return Task.Factory.StartNew(() => { }); 
    }); 

    autoResetEvent.WaitOne(1000); 
} 

musiałem naprawić mały błąd w błędzie pisania kodu w EasyNetQ przed tym pracował, więc prosimy o wersji> = 0.9.2.73 przed próbą to. można zobaczyć przykładowy kod here

+0

Dzięki za pomoc Mike. Czy uważasz, że dobrym pomysłem byłoby wyeksponowanie tego przyjaznego opakowania? Domyślnie proste API zapisuje do tej kolejki błędów, więc dla mnie ma sens, aby miał mechanizm do przezroczystego spożywania tych błędów. Nawet z kodem powyżej, myślę, że trzeba mieć jakiś rodzaj instrukcji switch w module obsługi komunikat błędu ('przełącznik (error.BasicProperties.Type)'), który następnie pozwala mi deserializowania oryginalną wiadomość do odpowiedniego typu, który jest nieco brzydki. Byłoby miło, gdybym mógł zapisać się do konkretnego rodzaju błędu, który mnie interesuje. –

+0

BTW Uwielbiam bibliotekę EastNetQ. Dziękuję za ciężką pracę i wspaniałą dokumentację. –

+0

Dzięki za miłe słowa! Dodałem Twoją sugestię do listy problemów https://github.com/mikehadlow/EasyNetQ/issues/71, ale nie jestem do końca przekonany. –

0

kod, który działa: (wziąłem przypuszczenie)

screwyness z „foo”, ponieważ jeśli po prostu przekazać tę funkcję HandleErrorMessage2 się zużywają nazwać, to może” t wymyślić, że zwraca pustkę, a nie zadanie, więc nie może dowiedzieć się, którego przeciążenia użyć. (VS 2012) Przypisanie do var czyni go szczęśliwym. Będziesz chciał złapać zwracaną wartość połączenia, aby móc zrezygnować z subskrypcji przez wyrzucenie obiektu.

Należy również zauważyć, że ktoś użył nazwy obiektu systemowego (kolejka) zamiast uczynić ją funkcją EasyNetQueue lub coś podobnego, więc trzeba dodać wyjaśnienie użycia dla kompilatora lub w pełni go określić.

using Queue = EasyNetQ.Topology.Queue; 

    private const string QueueName = "EasyNetQ_Default_Error_Queue"; 
    public static void Should_be_able_to_subscribe_to_error_messages(IBus bus) 
    { 
    Action <IMessage<Error>, MessageReceivedInfo> foo = HandleErrorMessage2; 

    IQueue queue = new Queue(QueueName,false); 
    bus.Advanced.Consume<Error>(queue, foo); 
    } 

    private static void HandleErrorMessage2(IMessage<Error> msg, MessageReceivedInfo info) 
{ 
} 
Powiązane problemy