2010-05-15 26 views
5

He estado trabajando durante semanas en la creación de un cliente/servidor para controlar una aplicación de servidor de música ubicada en el lado del servidor que está controlada por varias aplicaciones cliente ubicadas en la LAN. He logrado que el cliente se comunique con el servidor, envíe comandos para operar el servidor de música y, mediante el uso de devoluciones de llamada, responda a los clientes para que todas las IU del cliente puedan actualizarse de manera adecuada. Sin embargo, mi problema es que no puedo descifrar cómo transmitir otros mensajes que deben enviarse desde la aplicación del servidor a los clientes. Esperaba utilizar el método de devolución de llamada; sin embargo, no he podido acceder desde el lado del servidor. ¿Debo modificar o crear otro contrato que permita la comunicación del servidor a los clientes? ¿El enlace requiere modificación? Como mencioné anteriormente, he estado trabajando en esto por semanas (que comienza a sentirse como 'años'), y espero que funcione esta última parte de la aplicación. ¿Alguien podría dirigirme en la dirección correcta?WCF bidireccional Comunicación cliente-servidor

cliente de servicio lado de referencia:

<?xml version="1.0" encoding="utf-8"?> 
<ServiceReference> 
<ProxyGenerationParameters 
    ServiceReferenceUri="http://localhost:8001/APService/mex" 
    Name="APGateway" 
    NotifyPropertyChange="True" 
    UseObservableCollection="False"> 
</ProxyGenerationParameters> 
<EndPoints> 
    <EndPoint 
     Address="net.tcp://localhost:8000/APService/service" 
     BindingConfiguration="TcpBinding" 
     Contract="APClient.APGateway.APUserService" 
     > 
    </EndPoint> 
    <EndPoint 
     Address="http://localhost:8001/APService/service" 
     BindingConfiguration="HttpBinding" 
     Contract="APClient.APGateway.APUserService" 
     > 
    </EndPoint> 
</EndPoints> 
</ServiceReference> 

lado del cliente AP CONFIG

<?xml version="1.0" encoding="utf-8" ?> 
<configuration> 
<configSections> 
    <sectionGroup name="applicationSettings" type="System.Configuration.ApplicationSettingsGroup, System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" > 
     <section name="APClient.Properties.Settings" type="System.Configuration.ClientSettingsSection, System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" /> 
    </sectionGroup> 
</configSections> 
<system.serviceModel> 
    <client> 
     <endpoint 
      address="net.tcp://localhost:8000/APService/service" 
      binding="netTcpBinding" 
      contract="APClient.APGateway.APUserService" 
      name="TcpBinding" /> 
     <endpoint 
      address="http://localhost:8001/APService/service" 
      binding="wsDualHttpBinding" 
      contract="APClient.APGateway.APUserService" 
      name="HttpBinding" /> 
    </client> 
</system.serviceModel> 
<applicationSettings> 
    <APClient.Properties.Settings> 
     <setting name="pathToDatabase" serializeAs="String"> 
      <value>C:\Users\Bill\Documents\APData\</value> 
     </setting> 
    </APClient.Properties.Settings> 
</applicationSettings> 

lado del servidor AP.CONFIG

<?xml version="1.0" encoding="utf-8" ?> 
<configuration> 
    <system.serviceModel> 
    <behaviors> 
     <serviceBehaviors> 
     <behavior name="MetadataBehavior"> 
      <serviceMetadata httpGetEnabled="true" httpGetUrl="http://localhost:8001/APService/mex" /> 
     </behavior> 
     </serviceBehaviors> 
    </behaviors> 
    <services> 
     <service behaviorConfiguration="MetadataBehavior" name="APService.APService"> 
     <endpoint address="service" binding="netTcpBinding" name="TcpBinding" 
      contract="APService.IAPServiceInventory" /> 
     <endpoint address="service" binding="wsDualHttpBinding" name="HttpBinding" 
     contract="APService.IAPServiceInventory" /> 
     <endpoint address="mex" binding="mexHttpBinding" name="MexBinding" 
      contract="IMetadataExchange" /> 
     <host> 
      <baseAddresses> 
      <add baseAddress="net.tcp://localhost:8000/APService/" /> 
      <add baseAddress="http://localhost:8001/APService/" /> 
      </baseAddresses> 
     </host> 
     </service> 
    </services> 
    </system.serviceModel> 
</configuration> 

lado del servidor APSERVICE.CS

namespace APService 
{ 
    [ServiceBehavior(ConcurrencyMode=ConcurrencyMode.Single,InstanceContextMode=InstanceContextMode.PerCall)] 
public class APService : IAPServiceInventory 
{ 
     private static List<IClientCallback> _callbackList = new List<IClientCallback>(); 
     private static int _beerInventory = Convert.ToInt32(System.Configuration.ConfigurationManager.AppSettings["InitialBeerInventory"]); 
     public APService() {} 
     public int SubscribeToServer(string guestName) 
     { 
      IClientCallback guest = OperationContext.Current.GetCallbackChannel<IClientCallback>(); 
      if(!_callbackList.Contains(guest)) { _callbackList.Add(guest); } 
      else { Console.WriteLine(guest + " is already logged onto the Server."); } 
      _callbackList.ForEach(delegate(IClientCallback callback) { callback.NotifyGuestJoinedParty(guestName); }); 
     } 
     public void UpdateClients(string guestName,string UpdateInfo) 
     { 
      _callbackList.ForEach(delegate(IClientCallback callback) { callback.NotifyUpdateClients(guestName,UpdateInfo); }); 
     } 
     public void SendRequestToServer(string guestName, string request) 
     { 
      _callbackList.ForEach(delegate(IClientCallback callback) { callback.NotifyRequestMadeToServer(guestName,request); }); 
      if(request == "Play") { APControl.Play(); } 
      else if(request == "Stop") { APControl.Stop(); } 
      else if(request == "Pause") { APControl.PlayPause(); } 
      else if(request == "Next Track") { APControl.NextTrack(); } 
      else if(request == "Previous Track") { APControl.PreviousTrack(); } 
      else if(request == "Mute") { APControl.Mute(); } 
      else if(request == "Volume Up") { APControl.VolumeUp(5); } 
      else if(request == "Volume Down") { APControl.VolumeDown(5); } 
     } 
     public void CancelServerSubscription(string guestName) 
     { 
      IClientCallback guest = OperationContext.Current.GetCallbackChannel<IClientCallback>(); 
      if(_callbackList.Contains(guest)) { _callbackList.Remove(guest); } 
      _callbackList.ForEach(delegate(IClientCallback callback) { callback.NotifyGuestLeftParty(guestName); }); 
     } 
} 

lado del servidor IAPSERVICE.CS

namespace APService 
{ 
    [ServiceContract(Name="APUserService",Namespace="http://AP.com/WCFClientServer/",SessionMode=SessionMode.Required, CallbackContract=typeof(IClientCallback))] 
public interface IAPServiceInventory 
{ 
     [OperationContract()] 
     int SubscribeToServer(string guestName); 
     [OperationContract(IsOneWay=true)] 
     void SendRequestToServer(string guestName,string request); 
     [OperationContract(IsOneWay=true)] 
     void UpdateClients(string guestName,string UpdateInfo); 
     [OperationContract(IsOneWay=true)] 
     void CancelServerSubscription(string guestName); 
} 
} 

lado del servidor - IAPServiceCallback.cs

namespace APService 
{ 
    public interface IClientCallback 
    { 
      [OperationContract(IsOneWay=true)] 
      void NotifyGuestJoinedParty(string guestName); 
      [OperationContract(IsOneWay=true)] 
      void NotifyUpdateClients(string guestName,string UpdateInfo); 
      [OperationContract(IsOneWay=true)] 
      void NotifyRequestMadeToServer(string guestName,string request); 
      [OperationContract(IsOneWay=true)] 
      void NotifyGuestLeftParty(string guestName); 
    } 

Respuesta

1

supongo que puede seguir this link para comprender el mecanismo.

NLV

Cuestiones relacionadas