Poniższy tekst jest próbą, aby rozwinąć i dodać kolor do tego pytania:WCF klient wywołuje serwer powiesić aż awarii zasilania
Jak mogę zapobiec występują problemy klienta z zdejmując całą usługę?
Mam zasadniczo ten scenariusz: usługa WCF jest uruchomiony z zwrotna klient ma prosty, prosty jednokierunkowy komunikacji, nie bardzo różni się od tego jednego:
public interface IMyClientContract
{
[OperationContract(IsOneWay = true)]
void SomethingChanged(simpleObject myObj);
}
Dzwonię tej metody potencjalnie tysiące razy na sekundę od usługi do tego, co ostatecznie będzie około 50 jednocześnie połączonych klientów, z możliwie jak najmniejszym opóźnieniem (< 15 ms byłoby miłe). Działa to dobrze, dopóki nie ustawię punktu przerwania na jeden aplikacji klienckich połączonych z serwerem, a następnie wszystko zawiesza się po około 2-5 sekundach, gdy usługa się zawiesza i żaden z pozostałych klientów nie otrzymuje żadnych danych przez około 30 sekund, dopóki usługa rejestruje zdarzenie błędu połączenia i odłącza obrażającego klienta. Następnie wszyscy pozostali klienci kontynuują wesołe otrzymywanie wiadomości.
Zrobiłem badania nad usługąDziękuję, poprawianie współbieżności, ustawianie wątków minimalnych wątków, tajnych sosów WCF i całych 9 jardów, ale pod koniec dnia ten artykuł MSDN - WCF essentials, One-Way Calls, Callbacks and Events opisuje dokładnie problem, który mam, bez tworzenia Rekomendacja.
Trzecie rozwiązanie, które pozwala usłudze bezpiecznie odwołać się do klienta, powoduje, że operacje kontraktu oddzwonienia są skonfigurowane jako operacje jednokierunkowe. Dzięki temu usługa może oddzwonić nawet wtedy, gdy współbieżność jest ustawiona na jednowątkową, ponieważ nie będzie żadnej odpowiedzi na żądanie blokady.
ale wcześniej w artykule opisuje problem widzę, tylko z perspektywy klienta
Kiedy jednokierunkowe połączenia dotrzeć usługę, mogą one nie być wysłane wszystkie naraz i may należy umieścić w kolejce po stronie usługi, aby były wysyłane pojedynczo, wszystko zgodnie z zachowaniem w trybie współbieżności usługi i trybem sesji. Ile komunikatów (czy to w jedną stronę, czy w odpowiedzi na żądanie), czy usługa jest gotowa do umieszczenia w kolejce, jest produktem skonfigurowanego kanału i trybu niezawodności. Jeśli liczba oczekujących wiadomości przekroczyła pojemność kolejki, wtedy klient będzie blokował, nawet przy wydawaniu jednokierunkowego połączenia
Mogę tylko przypuszczać, że jest odwrotnie, liczba oczekujących wiadomości do klienta Przekroczono pojemność kolejki i wątek jest teraz wypełniony wątkami próbującymi wywołać tego klienta, które są teraz zablokowane.
Jaki jest właściwy sposób postępowania z tym? Czy powinienem zbadać sposób sprawdzenia, ile wiadomości są umieszczane w kolejce w warstwie komunikacji usług na klienta i przerwać połączenie po osiągnięciu określonego limitu?
Wygląda na to, że jeśli sama usługa WCF blokuje zapełnianie kolejki, wszystkie strategie asynchroniczne/oneway/fire-and-forget, które mogę wprowadzić w ramach usługi, będą nadal blokowane za każdym razem, gdy kolejka jednego klienta się zapełni. .
Longform w/szczegóły są doceniane, ale podsumowanie exec/TL; DR również będzie docenione. –
Czy sprawdziłeś liczniki wydajności lub śledzoną aktywność sieciową, aby sprawdzić, ile żądań zostało zablokowanych na wstrzymanym kliencie? –
Eksperymentuję z [fire-and-forget] (http://www.yoda.arachsys.com/csharp/threads/threadpool.shtml) i to faktycznie pokazuje pewien postęp. Zawijam synchronicznego delegata DynamicInvoke z blokiem catch, a następnie używając delegate.Target.GetHashCode() jako klucza do słownika bieżących połączeń, aby zidentyfikować obrażający kanał klienta, używając go do zabicia połączenia klienta ... wiem, czy to jest skalowalne –