私はWCF Duplexを使用して、サーバーのWCFで購読しているユーザー間でメッセージを送受信します。 WCFには、Join(購読する)、Leave(離脱する)、SendAlert(ユーザーから他のユーザーにメッセージを送信する)という3つのメソッドがあります。クライアントが突然WCFデュプレックスでクラッシュするときに行うべきこと
using System;
using System.Collections.Generic;
using System.ServiceModel;
namespace RahatWCF
{
[ServiceContract(Name = "AlertService",
Namespace = "RahatWCF",
SessionMode = SessionMode.Required,
CallbackContract = typeof(IAlertCallback))]
public interface IAlert
{
[OperationContract]
int JoinTheConversation(int userId);
[OperationContract(IsOneWay = true)]
void SendAlert(int senderUserId, List<int> recieversUserId, string caption, string messageText);
[OperationContract]
int LeaveTheConversation(int userId);
}
public interface IAlertCallback
{
[OperationContract(IsOneWay = true)]
void NotifyUserOfMessage(int senderUserId, List<int> recieversUserId, string caption, String messageText);
}
[ServiceBehavior(ConcurrencyMode = ConcurrencyMode.Single, InstanceContextMode = InstanceContextMode.PerCall)]
public class AlertService : IAlert
{
private static List<IAlertCallback> _callbackList = new List<IAlertCallback>();
public AlertService() { }
public int JoinTheConversation(int userId)
{
IAlertCallback registeredUser = OperationContext.Current.GetCallbackChannel<IAlertCallback>();
if (!_callbackList.Contains(registeredUser))
_callbackList.Add(registeredUser);
return _callbackList.Count;
}
public int LeaveTheConversation(int userId)
{
IAlertCallback registeredUser = OperationContext.Current.GetCallbackChannel<IAlertCallback>();
if (_callbackList.Contains(registeredUser))
_callbackList.Remove(registeredUser);
return _callbackList.Count;
}
public void SendAlert(int senderUserId, List<int> recieversUserId, string caption, string messageText)
{
_callbackList.ForEach(
delegate (IAlertCallback callback)
{
callback.NotifyUserOfMessage(senderUserId, recieversUserId, caption, messageText);
});
}
}
}
上記のコードは、私はサーバ側に実装WCFデュプレックスである:以下は、サーバ側のコード(サーバにおけるAlertService WCFで二重)です。ユーザーがアプリケーションにログインすると、私のWCFクライアントアプリケーションがこのWCFに参加します。ユーザーがアプリケーションからログアウトすると、クライアントアプリケーションはWCFを終了します。問題は、ユーザーが突然アプリケーションを終了し、クライアントアプリケーションからログアウトしないと、後で他のユーザーにメッセージを送信できなくなることです。私は問題をチェックして、ユーザーがログインしたとき(ジョイン)、ログアウトしないと(leave)、サーバーで2つのチャンネルが作成され、この状況でSendAlertがもう機能しないことを確認します。どうすればこの問題を解決できますか?
私は 'receiveTimeout'と 'inactivityTimeout'を増やしましたが、時には(なぜ私にはわからない)、エラーが発生します。 '通信オブジェクトSystem.ServiceModel.Channels.ServiceChannelは通信に使用できません中止されました。このエラーを解決するにはどうすればよいですか? – Mohsen
[再接続ロジック](http://stackoverflow.com/questions/14547034/wcf-channelfactory-and-channels-caching-reusing-closing-and-recovery/22124269#22124269)をご覧になることはできますが、あなたが行うことができるのはチャネルを再作成することだけです。 –
ありがとうございます。確認してお知らせします。 – Mohsen