2009-06-17 3 views
4

J'ai un service WCF que j'utilise pour remplacer un ancien service Web ASP.NET. Le service semble fonctionner correctement mais il est incapable de gérer des demandes simultanées pour une raison quelconque. Ma mise en œuvre du service a les propriétés suivantes:Pourquoi mon service WCF hébergé par Winforms est-il mono-threadé?

[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall, ConcurrencyMode = ConcurrencyMode.Multiple)] 
public class HHService : IHHService 

Ma déclaration d'accueil ressemble à ceci:

baseAddress = new Uri("http://0.0.0.0:8888/HandHeld/"); 
host = new ServiceHost(typeof(HHService), baseAddress); 

ServiceMetadataBehavior behavior; 
behavior = host.Description.Behaviors.Find<ServiceMetadataBehavior>(); 
if (behavior == null) 
{ 
    behavior = new ServiceMetadataBehavior(); 
    behavior.HttpGetEnabled = true; 
    behavior.MetadataExporter.PolicyVersion = PolicyVersion.Policy15; 
    host.Description.Behaviors.Add(behavior); 
} 
host.AddServiceEndpoint(ServiceMetadataBehavior.MexContractName,MetadataExchangeBindings.CreateMexHttpBinding(), "mex"); 
host.AddServiceEndpoint(typeof(IHHService), new BasicHttpBinding(), "HHService.asmx"); 
HHService.LogMessage += new EventHandler<HHService.LogMessageEventArgs>(HHService_LogMessage); 
host.Open(); 

Le service fonctionne et renvoie les résultats corrects, mais si deux clients tentent de faire un appel à la en même temps, un client bloquera jusqu'à ce que l'autre soit terminé plutôt que les appels s'exécutant ensemble. Je n'utilise aucun fichier de configuration. J'essaye de faire tout par programme. Est-ce que j'ai quelque chose d'installation incorrecte qui provoque ce comportement? J'ai exécuté d'autres services en utilisant le NetTCPBinding sans ce problème.

EDIT: En réponse à John Saunders: Je ne suis pas familier avec tout mode de compatibilité ASP.NET. Je n'utilise aucun état de session, le service est sans état, il ne traite que les demandes. Mis à part l'implémentation des méthodes actuelles tout ce que j'ai fait est dans le code listé ici.

Solution possible:

j'appelle la fonction host.Open() de l'événement Form_Load du formulaire principal. J'ai déplacé l'appel à un fil séparé. Tout ce fil a été appelez host.Open() mais maintenant le service semble se comporter comme je m'y attendais.

Répondre

4

Si votre mode de contexte d'instance est PerCall, votre serveur est toujours mono-thread, car par définition, chaque appel obtient une nouvelle instance de serveur.

Cela fonctionne correctement dans un environnement IIS, où IIS peut générer plusieurs instances de serveur pour gérer n appelants simultanés, un en tant que serveur monothread pour chaque requête entrante. Dans un de vos commentaires, vous mentionnez que vous hébergez votre WCF dans une application de formulaires. Cela peut être une décision de conception que vous devez reconsidérer. Ce n'est pas vraiment optimal, car l'application Winforms ne peut pas gérer plusieurs appelants. instances du code de service.

Marc

+0

S'il vous plaît jeter un oeil à mon édition parce que je l'ai fait fonctionner correctement sans faire d'autres changements que ceux que j'ai mentionnés. Je ne suis pas sûr pourquoi cela a fonctionné bien. – Mykroft

+0

OK, excellent.Oui, l'hébergement d'un service WCF dans une application Winforms sur le thread principal de l'interface utilisateur n'est pas vraiment une bonne idée. –

+0

C'est bizarre parce que j'ai une autre application qui fait à peu près la même chose avec un NetTCPBinding et cela fonctionne sans ces problèmes. – Mykroft

0

Y at-il un verrou quelque part dans votre fonction de service?

+0

Non, il n'y a pas de blocage. – Mykroft

0

Utilisez-vous le mode de compatibilité ASP.NET? Etat de la session? Ma question suivante serait: qu'est-ce qui vous fait penser que c'est un seul thread? Comment avez-vous déterminé cela, et quel test utilisez-vous pour prouver que vous n'avez pas résolu le problème? Pourrait être un faux positif.

Questions connexes