2012-09-21 24 views
5

Implementé un servicio REST para WCF. El servicio ofrece una función que muchos clientes pueden llamar y esta función tarda más de 1 minuto en completarse. Entonces, lo que quería es que para cada cliente, se use un nuevo objeto, de modo que se puedan manejar muchos clientes a la vez.WCF REST Servicio: InstanceContextMode.PerCall no funciona

Mi interfaz se parece a esto:

[ServiceContract] 
public interface ISimulatorControlServices 
{ 
    [WebGet] 
    [OperationContract] 
    string DoSomething(string xml); 
} 

Y la (prueba) la implementación de la misma:

[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall] 
public class SimulatorControlService : SimulatorServiceInterfaces.ISimulatorControlServices 
{ 
    public SimulatorControlService() 
    { 
     Console.WriteLine("SimulatorControlService started."); 
    } 

    public string DoSomething(string xml) 
    { 
     System.Threading.Thread.Sleep(2000); 
     return "blub"; 
    } 
} 

El problema ahora es: si uso un cliente que crea 10 (o cualquier número) hilos, cada uno de ellos llamando al servicio, no se ejecutan al mismo tiempo. Esto significa que las llamadas se están manejando una detrás de otra. ¿Alguien tiene una idea de por qué sucede esto?

Agregado: del lado del cliente código

hilos de desove:

 for (int i = 0; i < 5; i++) 
     { 
      Thread thread = new Thread(new ThreadStart(DoSomethingTest)); 
      thread.Start(); 
     } 

Método:

private static void DoSomethingTest() 
    { 
     try 
     { 
      using (ChannelFactory<ISimulatorControlServices> cf = new ChannelFactory<ISimulatorControlServices>(new WebHttpBinding(), "http://localhost:9002/bla/SimulatorControlService")) 
      { 
       cf.Endpoint.Behaviors.Add(new WebHttpBehavior()); 

       ISimulatorControlServices channel = cf.CreateChannel(); 

       string s; 

       int threadID = Thread.CurrentThread.ManagedThreadId; 

       Console.WriteLine("Thread {0} calling DoSomething()...", threadID); 

       string testXml = "test"; 

       s = channel.StartPressureMapping(testXml); 

       Console.WriteLine("Thread {0} finished with reponse: {1}", threadID, s); 
      } 

     } 
     catch (CommunicationException cex) 
     { 
      Console.WriteLine("A communication exception occurred: {0}", cex.Message); 
     } 
    } 

Gracias de antemano!

+0

¿Cómo estás desove las solicitudes de los clientes? ¿Puedes mostrar algún código sobre eso? Tenga en cuenta que puede editar su pregunta para agregar detalles. – Jeroen

+0

Se agregó el código del lado del cliente. – Cleo

+0

si su servicio no usa recursos compartidos, puede cambiar ServiceBehavior a Single with Concurrency Multiple. Esto le dará una instancia de servicio, que tiene múltiples hilos (un hilo por cada llamada). '[ServiceBehavior (InstanceContextMode = InstanceContextMode.Single, ConcurrencyMode = ConcurrencyMode.Multiple)]' – JanW

Respuesta

1

Dado que el servicio se controla mediante una GUI, se necesita el atributo "UseSynchronizationContext" para resolver el problema:

[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall, ConcurrencyMode=ConcurrencyMode.Multiple, UseSynchronizationContext=false)] 
Cuestiones relacionadas