WCF - Guide rapide

WCF signifie Windows Communication Foundation. La caractéristique élémentaire de WCF est l'interopérabilité. C'est l'une des dernières technologies de Microsoft qui est utilisée pour créer des applications orientées services. Basé sur le concept de communication basée sur les messages, dans laquelle une requête HTTP est représentée uniformément, WCF permet d'avoir une API unifiée indépendamment des divers mécanismes de transport.

WCF a été publié pour la première fois en 2006 dans le cadre du framework .NET avec Windows Vista, puis a été mis à jour plusieurs fois. WCF 4.5 est la version la plus récente qui est maintenant largement utilisée.

Une application WCF se compose de trois composants:

  • Service WCF,
  • Hôte de service WCF, et
  • Client de service WCF.

La plate-forme WCF est également connue sous le nom de modèle de service.

Concepts fondamentaux de la WCF

Message

Il s'agit d'une unité de communication qui comprend plusieurs parties en dehors du corps. Les instances de message sont envoyées et reçues pour tous les types de communication entre le client et le service.

Point final

Il définit l'adresse à laquelle un message doit être envoyé ou reçu. Il spécifie également le mécanisme de communication pour décrire comment les messages seront envoyés ainsi que la définition de l'ensemble de messages. Une structure d'un point final comprend les parties suivantes:

Adresse

L'adresse spécifie l'emplacement exact de réception des messages et est spécifiée en tant qu'identificateur de ressource uniforme (URI). Il est exprimé comme schéma: // domaine [: port] / [chemin]. Jetez un œil à l'adresse mentionnée ci-dessous -

net.tcp: // localhost: 9000 / ServiceA

Ici, «net.tcp» est le schéma du protocole TCP. Le domaine est «localhost» qui peut être le nom d'une machine ou d'un domaine Web, et le chemin est «ServiceA».

Contraignant

Il définit la manière dont un point final communique. Il comprend certains éléments contraignants qui constituent l'infrastructure de communication. Par exemple, une liaison indique les protocoles utilisés pour le transport comme TCP, HTTP, etc., le format de codage des messages et les protocoles liés à la sécurité ainsi qu'à la fiabilité.

Contrats

Il s'agit d'un ensemble d'opérations qui spécifie les fonctionnalités que le point de terminaison expose au client. Il se compose généralement d'un nom d'interface.

Hébergement

L'hébergement du point de vue de WCF fait référence à l'hébergement de service WCF qui peut être effectué via de nombreuses options disponibles telles que l'auto-hébergement, l'hébergement IIS et l'hébergement WAS.

Métadonnées

Il s'agit d'un concept important de WCF, car il facilite l'interaction entre une application cliente et un service WCF. Normalement, les métadonnées d'un service WCF sont générées automatiquement lorsqu'elles sont activées, et cela se fait par l'inspection du service et de ses points de terminaison.

Client WCF

Une application cliente créée pour exposer les opérations de service sous la forme de méthodes est connue sous le nom de client WCF. Cela peut être hébergé par n'importe quelle application, même celle qui héberge des services.

Canal

Le canal est un moyen par lequel un client communique avec un service. Différents types de canaux sont empilés et sont connus sous le nom de piles de canaux.

SAVON

Bien que appelé «protocole d'accès aux objets simples», SOAP n'est pas un protocole de transport; il s'agit plutôt d'un document XML comprenant une section d'en-tête et de corps.

Avantages de WCF

  • Il est interopérable par rapport aux autres services. Ceci est en contraste frappant avec .NET Remoting dans lequel le client et le service doivent avoir .Net.

  • Les services WCF offrent une fiabilité et une sécurité améliorées par rapport aux services Web ASMX (Active Server Methods).

  • L'implémentation du modèle de sécurité et la modification de la liaison dans WCF ne nécessitent pas de modification majeure du codage. Quelques modifications de configuration sont nécessaires pour répondre aux contraintes.

  • WCF a un mécanisme de journalisation intégré alors que dans d'autres technologies, il est essentiel de faire le codage requis.

  • WCF a intégré AJAX et la prise en charge de JSON (notation d'objet JavaScript).

  • Il offre une évolutivité et une prise en charge des normes de service Web à venir.

  • Il dispose d'un mécanisme de sécurité par défaut extrêmement robuste.

Il existe des différences majeures entre WCF et un service Web qui sont répertoriées ci-dessous.

  • Attributes - Le service WCF est défini par les attributs ServiceContract et OperationContract, tandis qu'un service Web est défini par les attributs WebService et WebMethod.

  • Protocols - WCF prend en charge une gamme de protocoles, c'est-à-dire HTTP, Named Pipes, TCP et MSMQ, alors qu'un service Web ne prend en charge que le protocole HTTP.

  • Hosting Mechanisms - Différents mécanismes d'activation existent pour l'hébergement WCF, à savoir IIS (Internet Information Service), WAS (Windows Activation Service), l'auto-hébergement et le service Windows, mais un service Web n'est hébergé que par IIS.

  • Services - WCF prend en charge une sécurité robuste, une messagerie, une transaction et une interopérabilité fiables, tandis qu'un service Web ne prend en charge que les services de sécurité.

  • Serializer - WCF prend en charge le sérialiseur DataContract en utilisant System.Runtime.Serialization, tandis qu'un service Web prend en charge le sérialiseur XML en utilisant System.Xml.Serialization.

  • Tools - L'outil ServiceMetadata (svcutil.exe) est utilisé pour la génération de client pour un service WCF, tandis que l'outil WSDL.EXE est utilisé pour générer le même pour un service Web.

  • Exception Handling- Dans WCF, les exceptions non gérées sont mieux gérées en utilisant FaultContract. Ils ne reviennent pas au client comme dans un service Web en tant que défauts SOAP.

  • Hash Table - Il est possible de sérialiser une table de hachage dans WCF, mais ce n'est pas le cas dans un service Web.

  • Bindings - WCF prend en charge plusieurs types de liaisons comme BasicHttpBinding, WSDualHttpBinding, WSHttpBinding, etc., tandis qu'un service Web ne prend en charge que SOAP ou XML.

  • Multithreading - WCF prend en charge le multithreading à l'aide de la classe ServiceBehavior, alors que cela n'est pas pris en charge dans un service Web.

  • Duplex Service Operations - WCF prend en charge les opérations de service duplex en dehors de la prise en charge des opérations de service unidirectionnel et de demande-réponse, alors qu'un service Web ne prend pas en charge les opérations de service duplex.

Pour développer une application de service WCF, il existe principalement deux outils: Microsoft Visual Studio et CodePlex. Microsoft Visual Studio est un ensemble complet d'outils de développement, nécessaires pour développer un grand nombre d'applications diverses telles que les applications Web ASP.NET, les applications de bureau, les applications mobiles et bien d'autres.

Microsoft Visual Studio utilise la fonctionnalité .NET Framework. CodePlex, quant à lui, est un site d'hébergement de projet open source de Microsoft qui propose plusieurs outils gratuits pour le développement d'applications de service WCF.

Microsoft Visual Studio

Il existe de nombreuses éditions de Microsoft Visual Studio et initialement (Visual Studio 2005) n'était pas un fervent partisan du développement WCF. À l'heure actuelle, Visual Studio 2008 est le seul Microsoft IDE disponible pour le développement d'applications de service WCF.

De nos jours, la dernière version de Microsoft Visual Studio 2010 est également un outil préféré pour développer une application de service WCF. Il existe également un modèle prêt à l'emploi dans Visual Studio pour développer une application de service WCF.

La sélection d'un tel modèle conduit à l'ajout de fichiers aux fins suivantes -

  • Contrat de service
  • Mise en œuvre du service
  • Configuration du service

Les attributs requis sont ajoutés automatiquement et un simple service "Hello World" est créé par Microsoft Visual Studio sans même écrire de code.

CodePlex

CodePlex a été lancé par Microsoft en juin 2006 et depuis lors, il a été utilisé par un grand nombre de développeurs à travers le monde pour créer avec succès des projets .NET. Certains des outils proposés par CodePlex pour développer des applications de service WCF sont les suivants:

  • wscf.blue- Il s'agit d'un complément Microsoft Visual Studio, ainsi que d'un ensemble d'outils de développement «contract-first» qui facilite la définition des opérations de service WCF et la génération d'un squelette de code en conséquence. Un lien important pour la même chose est -https://wscfblue.codeplex.com

  • WCFProxyGenerator- Il s'agit également d'un complément Microsoft Visual Studio. L'outil est utilisé pour étendre la génération côté client et offrir une gestion des erreurs supplémentaire. Pour plus d'informations sur cet outil de développement particulier, visitezhttps://wcfproxygenerator.codeplex.com

  • WCFMock- Le test du service WCF peut être une tâche compliquée et cet outil de développement offre une solution pratique pour le test unitaire des services WCF par ses classes utiles. Pour plus d'informations sur cet outil, visitezhttps://wcfmock.codeplex.com

WCFStorm est un autre outil gratuit permettant de développer facilement des applications de service WCF. Sa version LITE offre de nombreuses fonctionnalités frappantes pour appeler et tester dynamiquement les services WCF, modifier la liaison de service, modifier le point de terminaison d'URL WCF, etc.

WCF a une architecture en couches qui offre une prise en charge étendue pour le développement de diverses applications distribuées. L'architecture est expliquée ci-dessous en détail.

Contrats

La couche contrats est juste à côté de la couche application et contient des informations similaires à celles d'un contrat réel qui spécifie le fonctionnement d'un service et le type d'informations accessibles qu'il produira. Les contrats sont essentiellement de quatre types décrits ci-dessous en bref -

  • Service contract - Ce contrat fournit des informations au client ainsi qu'au monde extérieur sur les offres du terminal et les protocoles à utiliser dans le processus de communication.

  • Data contract- Les données échangées par un service sont définies par un contrat de données. Le client et le service doivent être en accord avec le contrat de données.

  • Message contract- Un contrat de données est contrôlé par un contrat de message. Il effectue principalement la personnalisation du formatage de type des paramètres de message SOAP. Ici, il convient de mentionner que WCF utilise le format SOAP à des fins de communication. SOAP signifie Simple Object Access Protocol.

  • Policy and Binding- Il existe certaines conditions préalables pour la communication avec un service, et ces conditions sont définies par une politique et un contrat contraignant. Un client doit suivre ce contrat.

Durée d'exécution du service

La couche d'exécution du service est juste en dessous de la couche des contrats. Il spécifie les divers comportements de service qui se produisent pendant l'exécution. Il existe de nombreux types de comportements qui peuvent subir une configuration et relever de l'exécution du service.

  • Throttling Behavior - Gère le nombre de messages traités.

  • Error Behavior - Définit le résultat de toute occurrence d'erreur de service interne.

  • Metadata Behavior - Spécifie la disponibilité des métadonnées vers le monde extérieur.

  • Instance Behavior - Définit le nombre d'instances à créer pour les rendre disponibles pour le client.

  • Transaction Behavior - Permet un changement d'état de la transaction en cas d'échec.

  • Dispatch Behavior - Contrôle la manière dont un message est traité par l'infrastructure de WCF.

  • Concurrency Behavior - Contrôle les fonctions qui s'exécutent en parallèle lors d'une communication client-serveur.

  • Parameter Filtering - Comprend le processus de validation des paramètres d'une méthode avant qu'elle ne soit appelée.

Messagerie

Cette couche, composée de plusieurs canaux, traite principalement du contenu du message à communiquer entre deux terminaux. Un ensemble de canaux forme une pile de canaux et les deux principaux types de canaux qui composent la pile de canaux sont les suivants -

  • Transport Channels - Ces canaux sont présents au bas d'une pile et sont responsables de l'envoi et de la réception de messages à l'aide de protocoles de transport tels que HTTP, TCP, Peer-to-Peer, Named Pipes et MSMQ.

  • Protocol Channels - Présent en haut d'une pile, ces canaux également appelés canaux en couches, implémentent des protocoles au niveau filaire en modifiant les messages.

Activation et hébergement

La dernière couche de l'architecture WCF est l'endroit où les services sont réellement hébergés ou peuvent être exécutés pour un accès facile par le client. Cela se fait par divers mécanismes décrits ci-dessous en bref.

  • IIS- IIS signifie Internet Information Service. Il offre une myriade d'avantages en utilisant le protocole HTTP par un service. Ici, il n'est pas nécessaire d'avoir le code hôte pour activer le code de service; au lieu de cela, le code de service est activé automatiquement.

  • Windows Activation Service- Ceci est populairement connu sous le nom de WAS et est fourni avec IIS 7.0. La communication basée sur HTTP et non HTTP est possible ici en utilisant les protocoles TCP ou Namedpipe.

  • Self-hosting- Il s'agit d'un mécanisme par lequel un service WCF est auto-hébergé en tant qu'application console. Ce mécanisme offre une flexibilité incroyable en termes de choix des protocoles souhaités et de définition de son propre schéma d'adressage.

  • Windows Service - L'hébergement d'un service WCF avec ce mécanisme est avantageux, car les services restent alors activés et accessibles au client en raison de l'absence d'activation d'exécution.

La création d'un service WCF est une tâche simple à l'aide de Microsoft Visual Studio 2012. Vous trouverez ci-dessous la méthode étape par étape pour créer un service WCF ainsi que tout le codage requis, pour mieux comprendre le concept.

  • Lancez Visual Studio 2012.
  • Cliquez sur nouveau projet, puis dans l'onglet Visual C #, sélectionnez l'option WCF.

Un service WCF est créé qui effectue des opérations arithmétiques de base telles que l'addition, la soustraction, la multiplication et la division. Le code principal est dans deux fichiers différents - une interface et une classe.

Un WCF contient une ou plusieurs interfaces et ses classes implémentées.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.Text;

namespace WcfServiceLibrary1 {
   // NOTE: You can use the "Rename" command on the "Refactor" menu to 
   // change the interface name "IService1" in both code and config file 
   // together.

   [ServiceContract]
   Public interface IService1 {
      [OperationContract]
      int sum(int num1, int num2);

      [OperationContract]
      int Subtract(int num1, int num2);

      [OperationContract]
      int Multiply(int num1, int num2);

      [OperationContract]
      int Divide(int num1, int num2);
   }

   // Use a data contract as illustrated in the sample below to add 
   // composite types to service operations.

   [DataContract]
   Public class CompositeType {
      Bool boolValue = true;
      String stringValue = "Hello ";

      [DataMember]
      Public bool BoolValue {
         get { return boolValue; }
         set { boolValue = value; }
      }

      [DataMember]   
      Public string StringValue {
         get { return stringValue; }
         set { stringValue = value; }
      }
   }
}

Le code derrière sa classe est donné ci-dessous.

using System;
usingSystem.Collections.Generic;
usingSystem.Linq;
usingSystem.Runtime.Serialization;
usingSystem.ServiceModel;
usingSystem.Text;

namespace WcfServiceLibrary1 {
   // NOTE: You can use the "Rename" command on the "Refactor" menu to 
   // change the class name "Service1" in both code and config file 
   // together.

   publicclassService1 :IService1 {
      // This Function Returns summation of two integer numbers
      
      publicint sum(int num1, int num2) {
         return num1 + num2;
      }
      
      // This function returns subtraction of two numbers. 
      // If num1 is smaller than number two then this function returns 0
      
      publicint Subtract(int num1, int num2) {
         if (num1 > num2) {
            return num1 - num2;
         }
         else {
            return 0;
         }
      }
      
      // This function returns multiplication of two integer numbers.
      publicint Multiply(int num1, int num2) {
         return num1 * num2;
      }
      
      // This function returns integer value of two integer number. 
      // If num2 is 0 then this function returns 1.
      publicint Divide(int num1, int num2) {
         if (num2 != 0) {
            return (num1 / num2);
         } else {
            return 1;
         }
      }
   }
}

Pour exécuter ce service, cliquez sur le bouton Démarrer dans Visual Studio.

Pendant que nous exécutons ce service, l'écran suivant apparaît.

En cliquant sur la méthode de somme, la page suivante s'ouvre. Ici, vous pouvez entrer deux nombres entiers quelconques et cliquer sur le bouton Appeler. Le service renverra la somme de ces deux nombres.

Comme la sommation, nous pouvons effectuer toutes les autres opérations arithmétiques répertoriées dans le menu. Et voici les clichés pour eux.

La page suivante apparaît en cliquant sur la méthode Soustraire. Entrez les nombres entiers, cliquez sur le bouton Appeler et obtenez la sortie comme indiqué ici -

La page suivante apparaît en cliquant sur la méthode Multiplier. Entrez les nombres entiers, cliquez sur le bouton Appeler et obtenez la sortie comme indiqué ici -

La page suivante apparaît en cliquant sur la méthode Divide. Entrez les nombres entiers, cliquez sur le bouton Appeler et obtenez la sortie comme indiqué ici -

Une fois le service appelé, vous pouvez basculer entre eux directement à partir d'ici.

Après avoir créé un service WCF, l'étape suivante consiste à l'héberger afin que les applications clientes puissent le consommer. C'est ce qu'on appelle l'hébergement de services WCF. Un service WCF peut être hébergé en utilisant l'une des quatre méthodes ci-dessous:

  • IIS Hosting- IIS signifie Internet Information Services. Son modèle de travail est similaire à celui d'ASP.NET tout en hébergeant un service WCF. La meilleure caractéristique de l'hébergement IIS est que l'activation du service est traitée automatiquement. L'hébergement IIS offre également la surveillance de l'intégrité des processus, l'arrêt au ralenti, le recyclage des processus et de nombreuses autres fonctionnalités pour faciliter l'hébergement d'un service WCF.

  • Self-Hosting- Lorsqu'un service WCF est hébergé dans une application gérée, il est appelé auto-hébergement. Il faut qu'un développeur écrive le codage requis pour l'initialisation de ServiceHost. En auto-hébergement, un service WCF peut être hébergé dans diverses applications telles que l'application console, le formulaire Windows, etc.

  • WAS Hosting - L'hébergement d'un service WCF dans le service d'activation Windows (WAS) est le plus avantageux en raison de ses fonctionnalités telles que le recyclage des processus, la gestion des temps d'inactivité, le système de configuration commun et la prise en charge de HTTP, TCP, etc.

  • Windows Service Hosting- Pour les clients du système local, il est préférable d'héberger le service WCF en tant que service de fenêtre et cela s'appelle l'hébergement de service de fenêtre. Toutes les versions de Windows prennent en charge ce type d'hébergement et ici, le Service Control Manager peut contrôler le cycle de vie des processus du service WCF.

L'hébergement d'un service WCF dans IIS (Internet Information Services) est un processus étape par étape. L'hébergement IIS est illustré ci-dessous en détail avec le codage souhaité ainsi que des captures d'écran pour comprendre le processus.

Step 1- Démarrez Visual Studio 2012 et cliquez sur Fichier → Nouveau → Site Web. Sélectionnez «Service WCF» et l'emplacement comme http. Cela hébergera le service dans IIS. Cliquez sur OK.

Step 2 - Le code derrière l'interface est donné ci-dessous.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Web;
using System.Text;

// NOTE: You can use the "Rename" command on the "Refactor" menu to 
// change the interface name "IService" in both code and config file 
// together.

[ServiceContract]
Public interface IService {
   [OperationContract]
   String GetData(int value);

   [OperationContract]
   CompositeType GetDataUsingDataContract(CompositeType composite);

   // TODO: Add your service operations here
}

// Use a data contract as illustrated in the sample below to add 
// composite types to service operations.

[DataContract]
Public class CompositeType {
   Bool boolValue = true;
   String stringValue = "Hello ";

   [DataMember]
   Public bool BoolValue {
      get { return boolValue; }
      set { boolValue = value; }
   }

   [DataMember]
   Public string StringValue {
      get { return stringValue; }
      set { stringValue = value; }
   }
}

Step 3 - Le code derrière le fichier de classe est donné ci-dessous.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Web;
using System.Text;

// NOTE: You can use the "Rename" command on the "Refactor" menu to 
// change the class name "Service" in code, svc and config file 
// together.

Public class Service : IService {
   Public string GetData(int value) {
      Return string.Format("You entered: {0}", value);
   }

   Public CompositeType GetDataUsingDataContract(CompositeType composite) {
      if(composite == null) {
         thrownewArgumentNullException("composite");
      }
      
      if(composite.BoolValue) {
         composite.StringValue += "Suffix";
      }
      return composite;
   }
}

Step 4- Le fichier de service (.svc) contient le nom du service et le code derrière le nom du fichier. Ce fichier est utilisé pour connaître le service.

<%@ ServiceHost Language = "C#" Debug = "true" Service = "Service" 
   CodeBehind = "~/App_Code/Service.cs" %>

Step 5- Les configurations côté serveur sont mentionnées dans le fichier de configuration. Ici, il y a une mention d'un seul point final qui est configuré à «wsHttpBinding»; nous pouvons également avoir plusieurs points de terminaison avec des liaisons différentes. Puisque nous allons héberger dans IIS, nous devons utiliser uniquement la liaison http.

<?xml version = "1.0"?>
<configuration>
   <!-- 
      Note: As an alternative to hand editing this file you can use the 
         web admin tool to configure settings for your application. Use
         the Website->Asp.Net Configuration option in Visual Studio.
         A full list of settings and comments can be found in 
         machine.config.comments usually located in 
         \Windows\Microsoft.Net\Framework\vx.x\Config 
   -->
   <configSections>
      <sectionGroup name = "system.web.extensions"  
         ype = "System.Web.Configuration.SystemWebExtensionsSectionGroup, 
         System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
         PublicKeyToken = 31BF3856AD364E35">
      
         <sectionGroup name = "scripting" 
            type = "System.Web.Configuration.ScriptingSectionGroup, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral,     
            PublicKeyToken = 31BF3856AD364E35">
      
            <section name = "scriptResourceHandler" 
               type = "System.Web.Configuration.ScriptingScriptResourceHandlerSection, 
               System.Web.Extensions, Version = 3.5.0.0, 
               Culture = neutral, PublicKeyToken = 31BF3856AD364E35" 
               requirePermission = "false" 
               allowDefinition = "MachineToApplication"/>
      
            <sectionGroup name = "webServices" 
               type = "System.Web.Configuration.ScriptingWebServicesSectionGroup, 
               System.Web.Extensions, Version = 3.5.0.0, 
               Culture = neutral, PublicKeyToken = 31BF3856AD364E35">
   
               <section name = "jsonSerialization" 
                  type = "System.Web.Configuration.ScriptingJsonSerializationSection, 
                  System.Web.Extensions, Version = 3.5.0.0, 
                  Culture = neutral, PublicKeyToken = 31BF3856AD364E35" 
                  requirePermission = "false" allowDefinition = "Everywhere"/>

               <section name = "profileService" 
                  type = "System.Web.Configuration.ScriptingProfileServiceSection, 
                  System.Web.Extensions, Version = 3.5.0.0, 
                  Culture = neutral, PublicKeyToken = 31BF3856AD364E35" 
                  requirePermission = "false" 
                  allowDefinition = "MachineToApplication"/>

               <section name = "authenticationService" 
                  type = "System.Web.Configuration.ScriptingAuthenticationServiceSection, 
                  System.Web.Extensions, Version = 3.5.0.0, 
                  Culture = neutral, PublicKeyToken = 31BF3856AD364E35" 
                  requirePermission = "false" 
                  allowDefinition = "MachineToApplication"/>

               <section name = "roleService" 
                  type = "System.Web.Configuration.ScriptingRoleServiceSection, 
                  System.Web.Extensions, Version = 3.5.0.0, 
                  Culture = neutral, PublicKeyToken = 31BF3856AD364E35" 
                  requirePermission = "false" 
                  allowDefinition = "MachineToApplication"/>
      
            </sectionGroup>
         </sectionGroup>
      </sectionGroup>
   </configSections>
   
<appSettings/>
   <connectionStrings/>
   <system.web>
      <!-- 
         Set compilation debug="true" to insert debugging 
         symbols into the compiled page. Because this 
         affects performance, set this value to true only 
         during development.
      -->
      
      <compilation debug = "true">
         <assemblies> 
         
            <add assembly = "System.Core, Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = B77A5C561934E089"/>
            
            <add assembly = "System.Web.Extensions, Version = 3.5.0.0, 
               Culture = neutral, PublicKeyToken = 31BF3856AD364E35"/>
            
            <add assembly = "System.Data.DataSetExtensions, Version = 3.5.0.0, 
               Culture = neutral, PublicKeyToken = B77A5C561934E089"/>
            
            <add assembly = "System.Web.Extensions, Version = 3.5.0.0, 
               Culture = neutral, PublicKeyToken = 31BF3856AD364E35"/>
            
            <add assembly = "System.Xml.Linq, Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = B77A5C561934E089"/>
            
         </assemblies>
      </compilation>
      
         <!--
            The <authentication> section enables configuration 
            of the security authentication mode used by 
            ASP.NET to identify an incoming user. 
         -->
         
      <authentication mode="Windows"/>
         <!--
            The <customErrors> section enables configuration 
            of what to do if/when an unhandled error occurs 
            during the execution of a request. Specifically, 
            it enables developers to configure html error pages 
            to be displayed in place of a error stack trace.

            <customErrors mode = "RemoteOnly" defaultRedirect = "GenericErrorPage.htm">
               <error statusCode = "403" redirect = "NoAccess.htm" />
               <error statusCode = "404" redirect = "FileNotFound.htm" />
            </customErrors>
         -->
         
         <pages>
            <controls>
               <add tagPrefix = "asp" namespace = "System.Web.UI" 
                  assembly = "System.Web.Extensions, Version = 3.5.0.0, 
                  Culture = neutral, PublicKeyToken = 31BF3856AD364E35"/>
               
               <add tagPrefix = "asp" namespace = "System.Web.UI.WebControls" 
                  assembly = "System.Web.Extensions, Version = 3.5.0.0, 
                  Culture = neutral, PublicKeyToken = 31BF3856AD364E35"/>
               
            </controls>
         </pages>
         
         <httpHandlers>
            <remove verb = "*" path = "*.asmx"/>
            
            <add verb = "*" path = "*.asmx" validate = "false" 
               type = "System.Web.Script.Services.ScriptHandlerFactory, 
               System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = 31BF3856AD364E35"/>
            
            <add verb = "*" path = "*_AppService.axd" validate = "false" 
               type = "System.Web.Script.Services.ScriptHandlerFactory, 
               System.Web.Extensions, Version = 3.5.0.0, Culture = neutral,
               PublicKeyToken = 31BF3856AD364E35"/>
            
            <add verb = "GET,HEAD" path = "ScriptResource.axd" 
               type = "System.Web.Handlers.ScriptResourceHandler, 
               System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = 31BF3856AD364E35" validate = "false"/>
         </httpHandlers>
         
         <httpModules>
            <add name = "ScriptModule" 
               type = "System.Web.Handlers.ScriptModule, 
               System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = 31BF3856AD364E35"/>
         </httpModules>
   </system.web>
   
   <system.codedom>
      <compilers>
      
         <compiler language = "c#;cs;csharp" extension = ".cs" 
            warningLevel = "4" type = "Microsoft.CSharp.CSharpCodeProvider, 
            System, Version = 2.0.0.0, Culture = neutral, 
            PublicKeyToken = b77a5c561934e089">
         
            <providerOption name = "CompilerVersion" value = "v3.5"/>
            <providerOption name = "WarnAsError" value = "false"/>

         </compiler>

         <compiler language = "vb;vbs;visualbasic;vbscript" extension = ".vb" 
            warningLevel = "4" type = "Microsoft.VisualBasic.VBCodeProvider, 
            System, Version = 2.0.0.0, Culture = neutral, 
            PublicKeyToken = b77a5c561934e089">

            <providerOption name = "CompilerVersion" value = "v3.5"/>
            <providerOption name = "OptionInfer" value = "true"/>
            <providerOption name = "WarnAsError" value = "false"/>
            
         </compiler>
      </compilers>
      
   </system.codedom>
   <!-- 
      The system.webServer section is required for running ASP.NET AJAX 
      under Internet Information Services 7.0.  
      It is not necessary for previous version of IIS.
   -->
   <system.webServer>
      <validation validateIntegratedModeConfiguration="false"/>
      
      <modules>
         <remove name = "ScriptModule"/>
         <add name = "ScriptModule" preCondition = "managedHandler" 
            type = "System.Web.Handlers.ScriptModule, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
      </modules>
      
      <handlers>
         <remove name = "WebServiceHandlerFactory-Integrated"/>
         <remove name = "ScriptHandlerFactory"/>
         <remove name = "ScriptHandlerFactoryAppServices"/>
         <remove name = "ScriptResource"/>
         
         <add name = "ScriptHandlerFactory" verb = "*" path = "*.asmx" 
            preCondition = "integratedMode" 
            type = "System.Web.Script.Services.ScriptHandlerFactory, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>    
         
         <add name = "ScriptHandlerFactoryAppServices" 
            verb = "*" path = "*_AppService.axd" preCondition = "integratedMode" 
            type = "System.Web.Script.Services.ScriptHandlerFactory, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
         
         <add name = "ScriptResource" preCondition = "integratedMode" 
            verb = "GET,HEAD" path = "ScriptResource.axd" 
            type = "System.Web.Handlers.ScriptResourceHandler, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
      </handlers>
      
      <!--To browse web app root directory during debugging, 
         set the value below to true. Set to false before deployment to 
         avoid disclosing web app folder information.-->
      
      <directoryBrowse enabled = "true"/>
   </system.webServer>
   
   <runtime>
      <assemblyBinding appliesTo = "v2.0.05727" xmlns =" urn:schemas-microsoft-com:asm.v1">
      
         <dependentAssembly>
            <assemblyIdentity name = "System.Web.Extensions" publicKeyToken = "31bf3856ad364e35"/>
            <bindingRedirect oldVersion = "1.0.0.0-1.1.0.0" newVersion = "3.5.0.0"/>
         </dependentAssembly>
         
         <dependentAssembly>
            <assemblyIdentity name = "System.Web.Extensions.Design" publicKeyToken =" 31bf3856ad364e35"/>
            <bindingRedirect oldVersion = "1.0.0.0-1.1.0.0" newVersion = "3.5.0.0"/>
         </dependentAssembly>
         
      </assemblyBinding>
   </runtime>
   
   <system.serviceModel>
      <services>
         <service name = "Service" behaviorConfiguration = "ServiceBehavior">
         <!-- Service Endpoints -->
            <endpoint address = "" binding = "basicHttpBinding" contract = "IService">
               <!-- 
                  Upon deployment, the following identity element should be removed or replaced 
                  to reflect the identity under which the deployed service runs. If removed, 
                  WCF will infer an appropriate identity automatically.
               -->

               <identity>
                  <dns value="localhost"/>
               </identity>

            </endpoint>
            <endpoint address = "mex" binding = "mexHttpBinding" contract = "IMetadataExchange"/>
            
         </service>
      </services>
      
      <behaviors> 
         <serviceBehaviors>
            <behavior name = "ServiceBehavior">
               <!-- To avoid disclosing metadata information, set the value below 
                  to false before deployment -->
               
               <serviceMetadata httpGetEnabled = "true"/>
               
               <!-- To receive exception details in faults for debugging purposes, 
                  set the value below to true. 
                  Set to false before deployment to false avoid 
                  disclosing exception information -->
               
               <serviceDebug includeExceptionDetailInFaults = "false"/>
            </behavior>
         </serviceBehaviors>
      </behaviors>
      
   </system.serviceModel>
</configuration>

Step 6- Vous devez mentionner le nom du fichier de service, ainsi que l'adresse mentionnée dans le fichier de configuration. La capture d'écran d'IIS est donnée ici.

Cliquez sur Démarrer → exécuter → inetmgr qui ouvrira la fenêtre suivante.

Step 7 - Exécutez l'application qui produira l'écran suivant.

Ici, le service WCF est hébergé dans une application console. Ci-dessous est le processus avec des étapes appropriées d'une manière séquentielle qui explique l'ensemble du processus.

Step 1- Commençons par créer le contrat de service et sa mise en œuvre. Créez une application console et nommez-la MyCalculatorService. Il s'agit d'un service simple pour renvoyer l'addition de deux nombres.

Step 2- Maintenant, faites un clic droit sur les références dans l'Explorateur de solutions et cliquez sur Ajouter des références. La fenêtre suivante s'ouvre; ajoutez une référence System.ServiceModel au projet.

Step 3- Créez une interface ISimpleCalculator, ajoutez l'attribut ServiceContract et OperationContract à la classe et fonction comme indiqué ci-dessous. Vous en saurez plus sur ces contrats lors de la prochaine session. Ces contrats exposeront la méthode au monde extérieur pour l'utilisation de ce service.

Step 4 - Le code derrière ce fichier est le suivant -

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;

namespace MyCalculatorWCFService {
   [ServiceContract()]
   Public interface ISimpleCalculator {
      [OperationContract()]
      int Add(int num1, int num2);
   }
}

Step 5 - MyCalculatorService est la classe d'implémentation de l'interface IMyCalculatorService comme indiqué ci-dessous.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace MyCalculatorWCFService {
   Class SimpleCalculator : ISimpleCalculator {
      Public int Add(int num1, int num2) {
         return num1 + num2;
      }
   }
}

Step 6- Maintenant, nous sommes prêts avec le service. C'est parti pour la mise en œuvre du processus d'hébergement. Créez une nouvelle application console et nommez-la "MyCalculatorWCFServiceHost".

Step 7 - Ajoutez la référence de system.servicemodel et le projet MyCalculatorWCFService.

Le code derrière ceci est le suivant -

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using MyCalculatorWCFService;
using System.ServiceModel;
using System.ServiceModel.Description;

namespace MyCalculatorWCFServiceHost {
   class Program {
      static void Main(string[] args) {
         //Create a URI to serve as the base address
         UrihttpUrl = newUri("http://localhost:8090/MyCalculatorWCFService/SimpleCalculator");
         
         //Create ServiceHost
         ServiceHost host = newServiceHost(typeof(MyCalculatorWCFService.ISimpleCalculator), httpUrl);
         
         //Add a service endpoint
         host.AddServiceEndpoint(typeof(MyCalculatorWCFService.ISimpleCal culator), newWSHttpBinding(), "");
         
         //Enable metadata exchange
         ServiceMetadataBehaviorsmb = newServiceMetadataBehavior();
         smb.HttpGetEnabled = true;
         host.Description.Behaviors.Add(smb);

         //Start the Service
         host.Open();
         Console.WriteLine("Service is host at " + DateTime.Now.ToString());
         Console.WriteLine("Host is running... Press  key to stop");
         Console.ReadLine();
      }
   }
}

Pour comprendre le concept d'hébergement WAS, nous devons comprendre comment un système est configuré et comment un contrat de service est créé, permettant une liaison différente au service hébergé.

Tout d'abord, activez WCF pour les non-protocoles. Avant de commencer à créer le service, nous devons configurer le système pour prendre en charge WAS. Voici les étapes pour configurer WAS -

  • Cliquez sur Menu Démarrer → Panneau de configuration → Programmes et fonctionnalités, puis cliquez sur «Activer ou désactiver les composants Windows» dans le volet gauche.

  • Développez «Microsoft .Net Framework 3.0» et activez «Windows Communication Foundation HTTP Activation» et «Windows Communication Foundation Non-HTTP Activation».

  • Ensuite, nous devons ajouter la liaison au site Web par défaut. À titre d'exemple, nous lierons le site Web par défaut au protocole TCP. Accédez au menu Démarrer → Programmes → Accessoires. Faites un clic droit sur "Invite de commandes" et sélectionnez "Exécuter en tant qu'administrateur" dans le menu contextuel.

  • Exécutez la commande suivante -

C:\Windows\system32\inetsrv> appcmd.exe set site "Default Web Site" -+bindings.[protocol='net.tcp',bindingInformation='808:*']

Cette commande ajoute la liaison de site net.tcp au site Web par défaut en modifiant le fichier applicationHost.config situé dans le répertoire "C: \ Windows \ system32 \ inetsrv \ config". De même, nous pouvons ajouter différents protocoles au site Web par défaut.

Créer un service hébergé WAS

Step-1 - Ouvrez Visual Studio 2008 et cliquez sur Nouveau → Site Web et sélectionnez Service WCF à partir du modèle et Emplacement comme HTTP, comme indiqué ci-dessous -

Step-2- Créez le contrat en créant une interface IMathService. Ajoutez l'attribut ServiceContract à l'interface et l'attribut OperationContract à la déclaration de méthode.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.Text;

// NOTE: You can use the "Rename" command on the "Refactor" menu to 
// change the interface name "IService" in both code and config file 
// together.

[ServiceContract]

Public interface IMathService {
   [OperationContract]
   int Add(int num1, int num2);

   [OperationContract]
   int Subtract(int num1, int num2);
}

Step-3 - L'implémentation de l'interface IMathService est illustrée ci-dessous -

using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Web;
using System.Text;

// NOTE: You can use the "Rename" command on the "Refactor" menu to 
// change the class name "Service" in code, svc and config file 
// together.

Public class MathService : IMathService {
   Public int Add(int num1, int num2) {
      return num1 + num2;
   }
   Public int Subtract(int num1, int num2) {
      return num1 - num2;
   }
}

Step-4 - Le fichier de service est illustré ci-dessous.

<%@ServiceHostLanguage="C#"Debug="true"Service="MathService"CodeBehind="~/App_Code/MathService.cs"%>

Step-5- Dans le fichier web.Config, créez un point de terminaison avec la liaison «netTcpBinding» et les métadonnées du service seront publiées à l'aide du point d'échange de métadonnées. Créez donc le point de terminaison d'échange de métadonnées avec l'adresse comme «mex» et la liaison comme «mexTcpBinding». Sans publier les métadonnées du service, nous ne pouvons pas créer le proxy en utilisant l'adresse net.tcp, par exemple -

svcutil.exe net.tcp://localhost/WASHostedService/MathService.svc).
<?xml version = "1.0" ?>
<configuration>
   <!--
      Note: As an alternative to hand editing this file you can use the 
         web admin tool to configure settings for your application. Use
         the Website->Asp.Net Configuration option in Visual Studio.
         A full list of settings and comments can be found in 
         machine.config.comments usually located in 
         \Windows\Microsoft.Net\Framework\vx.x\Config 
   -->
   <configSections>
      <sectionGroup name = "system.web.extensions" 
         type = "System.Web.Configuration.SystemWebExtensionsSectionGroup, 
         System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
         PublicKeyToken = 31BF3856AD364E35">
		
         <sectionGroup name = "scripting" 
            type = "System.Web.Configuration.ScriptingSectionGroup, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken =3 1BF3856AD364E35">

            <section name = "scriptResourceHandler" 
               type = "System.Web.Configuration.ScriptingScriptResourceHandlerSection, 
               System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = 31BF3856AD364E35" 
               requirePermission = "false" 
               allowDefinition = "MachineToApplication"/>

            <sectionGroup name = "webServices" 
               type = "System.Web.Configuration.ScriptingWebServicesSectionGroup, 
               System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = 31BF3856AD364E35">

               <section name = "jsonSerialization" 
                  type = "System.Web.Configuration.ScriptingJsonSerializationSection, 
                  System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
                  PublicKeyToken = 31BF3856AD364E35" requirePermission = "false" 
                  allowDefinition = "Everywhere"/>

               <section name = "profileService" 		     
                  type = "System.Web.Configuration.ScriptingProfileServiceSection, 
                  System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
                  PublicKeyToken = 31BF3856AD364E35" requirePermission = "false" 
                  allowDefinition = "MachineToApplication"/>

               <section name = "authenticationService" 			     
                  type = "System.Web.Configuration.ScriptingAuthenticationServiceSection, 
                  System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
                  PublicKeyToken = 31BF3856AD364E35" requirePermission = "false" 
                  allowDefinition = "MachineToApplication"/>

               <section name = "roleService"	
                  type = "System.Web.Configuration.ScriptingRoleServiceSection, 
                  System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
                  PublicKeyToken = 31BF3856AD364E35" requirePermission = "false"
                  allowDefinition = "MachineToApplication"/>

            </sectionGroup>
         </sectionGroup>
      </sectionGroup>
   </configSections>
   
   <appSettings/>
   <connectionStrings/>
   
   <system.web>
      <!--
         Set compilation debug="true" to insert debugging 
         symbols into the compiled page. Because this 
         affects performance, set this value to true only 
         during development.
      -->
      <compilation debug = "true">
         <assemblies>
            <add assembly = "System.Core, Version = 3.5.0.0, 
               Culture = neutral, PublicKeyToken = B77A5C561934E089"/>
            
            <add assembly = "System.Web.Extensions, Version = 3.5.0.0, 
               Culture = neutral, PublicKeyToken = 31BF3856AD364E35"/>
            
            <add assembly = "System.Data.DataSetExtensions, 
               Version = 3.5.0.0, Culture = neutral,                  
               PublicKeyToken = B77A5C561934E089"/>
            
            <add assembly = "System.Web.Extensions, Version = 3.5.0.0, 
               Culture = neutral, PublicKeyToken = 31BF3856AD364E35"/>
            
            <add assembly = "System.Xml.Linq, 
               Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = B77A5C561934E089"/>
         </assemblies>
      </compilation>
      
      <!--
         The <authentication> section enables configuration          
         of the security authentication mode used by 
         ASP.NET to identify an incoming user. 
      -->
      
      <authentication mode="Windows"/>
      
      <!--
         The <customErrors> section enables configuration 
         of what to do if/when an unhandled error occurs 
         during the execution of a request. Specifically, 
         it enables developers to configure html error pages 
         to be displayed in place of a error stack trace.
         <customErrors mode = "RemoteOnly" defaultRedirect = "GenericErrorPage.htm">
         <error statusCode = "403" redirect = "NoAccess.htm" />
         <error statusCode = "404" redirect = "FileNotFound.htm" />
         </customErrors>
      -->
      
      <pages>
         <controls>
            <add tagPrefix = "asp" namespace = "System.Web.UI" 
               assembly = "System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = 31BF3856AD364E35"/>
            
            <add tagPrefix = "asp" namespace = "System.Web.UI.WebControls"
               assembly = "System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
               PublicKeyToken = 31BF3856AD364E35"/>
         </controls>
      </pages>
      
      <httpHandlers>
         <remove verb = "*" path = "*.asmx"/>
         
         <add verb =" *" path =" *.asmx" validate="false"         
            type = "System.Web.Script.Services.ScriptHandlerFactory, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
         
         <add verb = "*" path = "*_AppService.axd" validate = "false" 
            type = "System.Web.Script.Services.ScriptHandlerFactory,System.Web.Extensions, 
            Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
         
         <add verb = "GET,HEAD" path = "ScriptResource.axd"        
            type = "System.Web.Handlers.ScriptResourceHandler, System.Web.Extensions, 
            Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35" validate = "false"/>
      </httpHandlers>
      
      <httpModules>
         <add name = "ScriptModule" 
            type = "System.Web.Handlers.ScriptModule, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
      </httpModules>
      
   </system.web>
   
   <system.codedom>
      <compilers>
         
         <compiler language = "c#;cs;csharp" extension = ".cs" warningLevel = "4" 
            type = "Microsoft.CSharp.CSharpCodeProvider, System, 
            Version = 2.0.0.0, Culture = neutral,                 
            PublicKeyToken = b77a5c561934e089">
         
            <providerOption name = "CompilerVersion" value = "v3.5"/>
            <providerOption name = "WarnAsError" value = "false"/>
         </compiler>
         
         <compiler language = "vb;vbs;visualbasic;vbscript" 
            extension = ".vb" warningLevel = "4" 
            type = "Microsoft.VisualBasic.VBCodeProvider, System, 
            Version = 2.0.0.0, Culture = neutral,                  
            PublicKeyToken = b77a5c561934e089">
         
            <providerOption name = "CompilerVersion" value = "v3.5"/>
            <providerOption name = "OptionInfer" value = "true"/>
            <providerOption name = "WarnAsError" value = "false"/>
         </compiler>
      
      </compilers>
   </system.codedom>
   
   <!--
      The system.webServer section is required for running ASP.NET AJAX under 
      Internet Information Services 7.0. It is not necessary for previous version of IIS.
   -->
   
   <system.webServer>
      <validation validateIntegratedModeConfiguration = "false"/>
      
      <modules>
         <remove name = "ScriptModule"/>
         <add name = "ScriptModule" preCondition = "managedHandler"         
            type = "System.Web.Handlers.ScriptModule, System.Web.Extensions, 
            Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
      </modules>
      
      <handlers>
         <remove name = "WebServiceHandlerFactory-Integrated"/>
         <remove name = "ScriptHandlerFactory"/>
         <remove name = "ScriptHandlerFactoryAppServices"/>
         <remove name = "ScriptResource"/>
         
         <add name = "ScriptHandlerFactory" 
            verb = "*" path = "*.asmx" preCondition = "integratedMode"              
            type = "System.Web.Script.Services.ScriptHandlerFactory, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
         
         <add name = "ScriptHandlerFactoryAppServices" 
            verb = "*" path = "*_AppService.axd" preCondition = "integratedMode" 
            type = "System.Web.Script.Services.ScriptHandlerFactory, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
         
         <add name = "ScriptResource" preCondition = "integratedMode" 
            verb = "GET,HEAD" path = "ScriptResource.axd" 
            type = "System.Web.Handlers.ScriptResourceHandler, 
            System.Web.Extensions, Version = 3.5.0.0, Culture = neutral, 
            PublicKeyToken = 31BF3856AD364E35"/>
         
      </handlers>
      <!--
         To browse web app root directory during debugging, set the value below to true. 
         Set to false before deployment to avoid disclosing web app folder information.
      -->
      <directoryBrowse enabled="true"/>
   </system.webServer>
   
   <runtime>
      <assemblyBinding appliesTo = "v2.0.05727" xmlns = "urn:schemas-microsoft-com:asm.v1">
      
         <dependentAssembly>
            <assemblyIdentity name = "System.Web.Extensions" publicKeyToken = "31bf3856ad364e35"/>
            <bindingRedirect oldVersion = "1.0.0.0-1.1.0.0" newVersion = "3.5.0.0"/>
         </dependentAssembly>
         
         <dependentAssembly>
            <assemblyIdentity name = "System.Web.Extensions.Design" publicKeyToken = "31bf3856ad364e35"/>
            <bindingRedirect oldVersion = "1.0.0.0-1.1.0.0" newVersion = "3.5.0.0"/>
         </dependentAssembly>
         
      </assemblyBinding>
   </runtime>
   
   <system.serviceModel>
      <services>
         <service behaviorConfiguration = "ServiceBehavior" name = "Service">
            <endpoint address = "" binding = "basicHttpBinding" contract = "IMathService">
            
            <identity>
               <dns value = "localhost" />
            </identity>
            
            </endpoint>
            <endpoint address = "mex" binding = "mexHttpBinding" contract = "IMetadataExchange"/>
         </service>
      </services>
      
      <behaviors>
         <serviceBehaviors>
            <behavior name = "ServiceBehavior">
               <!-- 
                  To avoid disclosing metadata information, set the value below 
                  to false before deployment. 
               -->
               <serviceMetadata httpGetEnabled="true"/>
               
               <!-- 
                  To receive exception details in faults for debugging purposes, 
                  set the value below to true. Set to false before deployment to avoid 
                  disclosing exception information 
               -->
               <serviceDebug includeExceptionDetailInFaults="false"/>
            </behavior>
         </serviceBehaviors>
      </behaviors>
      
   </system.serviceModel>
</configuration>

Activer différentes liaisons au service hébergé

  • Allez dans le menu Démarrer → Programmes → Accessoires. Faites un clic droit sur "Invite de commandes" et sélectionnez "Exécuter en tant qu'administrateur" dans le menu contextuel.

  • Exécutez la commande suivante -

C:\Windows\system32\inetsrv>appcmd set app "Default Web Site/WASHostedService" /enabledProtocols:http,net.tcp

Il produira la sortie suivante -

Le fonctionnement de l'hébergement de services Windows est simple. Vous trouverez ci-dessous les étapes avec le codage requis et les captures d'écran qui expliquent le processus de manière simple.

Step 1- Créons maintenant un service WCF. Ouvrez Visual Studio 2008 et cliquez sur Nouveau → Projet et sélectionnez Bibliothèque de classes dans le modèle.

Step 2- Ajoutez la référence System.ServiceModel au projet. Il s'agit de l'assembly principal utilisé pour créer le service WCF.

Step 3- Ensuite, nous pouvons créer l'interface ISimpleCalulator. Ajoutez l'attribut de contrat de service et d'exploitation comme indiqué ci-dessous -

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;

namespace WindowsServiceHostedService{
   [ServiceContract]
   public interfaceISimpleCalculator {
      [OperationContract]
      int Add(int num1, int num2);

      [OperationContract]
      int Subtract(int num1, int num2);

      [OperationContract]
      int Multiply(int num1, int num2);

      [OperationContract]
      double Divide(int num1, int num2);
   }
}

Step 4 - Implémentez l'interface ISimpleCalculator comme indiqué ci-dessous -

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace WindowsServiceHostedService {
   Class SimpleCalulator : ISimpleCalculator {
      Public int Add(int num1, int num2) {
         return num1 + num2;
      }
      Public int Subtract(int num1, int num2) {
         return num1 - num2;
      }
      Public int Multiply(int num1, int num2) {
         return num1 * num2;
      }
      Public double Divide(int num1, int num2) {
         if (num2 != 0)
            return num1 / num2;
         else
            return 0;
      }
   }
}

Step 5- Construisez le projet et récupérez la dll. Maintenant, nous sommes prêts avec le service WCF. Nous allons voir comment héberger le service WCF dans le service Windows.

Note- Dans ce projet, il est mentionné que nous créons à la fois un contrat et un service (mise en œuvre) dans le même projet. Cependant, c'est toujours une bonne pratique si vous avez les deux dans des projets différents.

Step 6 - Ouvrez Visual Studio 2008 et cliquez sur Nouveau → Projet et sélectionnez Service Windows.

Step 7- Ajoutez «WindowsServiceHostedService.dll» comme référence au projet. Cette assemblée va servir de service.

Step 8- La méthode OnStart du service peut être utilisée pour écrire le code d'hébergement pour WCF. Nous devons nous assurer que nous n'utilisons qu'un seul objet hôte de service. La méthode OnStop est utilisée pour fermer l'hôte de service. Le code suivant montre comment héberger le service WCF dans le service Windows.

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Linq;
using System.ServiceProcess;
using System.Text;
using System.ServiceModel;
using System.ServiceModel.Description;

namespace WCFHostedWindowsService {
   Partial class WCFHostedWindowsService : ServiceBase {
      ServiceHostm_Host;

      Public WCFHostedWindowsService() {
         InitializeComponent();
      }
      Private void InitializeComponent() {
         thrownewNotImplementedException();
      }
      protectedoverridevoidOnStart(string[] args) {
         if (m_Host != null) {
            m_Host.Close();
         }
        
         //Create a URI to serve as the base address
         UrihttpUrl = newUri("http://localhost:8090/WindowsServiceHostedService/SimpleCalculator");
        
         //Create ServiceHost
         m_Host = newServiceHost typeof(WindowsServiceHostedService.SimpleCalulator), httpUrl);
        
         //Add a service endpoint
         m_Host.AddServiceEndpoint (typeof(WindowsServiceHostedService.ISimpleCalculator), newWSHttpBinding(), "");
        
         //Enable metadata exchange
         ServiceMetadataBehaviorsmb = newServiceMetadataBehavior();
         smb.HttpGetEnabled = true;
         m_Host.Description.Behaviors.Add(smb);
        
         //Start the Service
         m_Host.Open();
      }
      protectedoverridevoidOnStop() {
         if (m_Host != null) {
            m_Host.Close();
            m_Host = null;
         }
      }
      staticvoid Main() {
         ServiceBase[] ServicesToRun;
         ServicesToRun = newServiceBase[] { 
            newWCFHostedWindowsService();
         }   
         ServiceBase.Run(ServicesToRun);
      }
   }
}

Step 9- Pour installer le service, nous avons besoin de la classe Installer pour le service Windows. Ajoutez donc une nouvelle classe Installer au projet, qui est héritée de la classe Installer. Le code ci-dessous indique le nom du service, le type de démarrage, etc. du service.

using System;
using System.Collections.Generic;
using System.Text;
using System.ServiceProcess;
using System.Configuration.Install;
using System.ComponentModel;
using System.Configuration;

namespace WCFHostedWindowsService {
   [RunInstaller(true)]
   Public class WinServiceInstaller : Installer {
      Private ServiceProcessInstaller process;
      Private ServiceInstaller service;

      Public WinServiceInstaller() {
         process = newServiceProcessInstaller();
         process.Account = ServiceAccount.NetworkService;
         service = newServiceInstaller();
         
         service.ServiceName = "WCFHostedWindowsService";
         service.DisplayName = "WCFHostedWindowsService";
         service.Description = "WCF Service Hosted";
         service.StartType = ServiceStartMode.Automatic;
         
         Installers.Add(process);
         Installers.Add(service);
      }
   }
}

Step 10- Générez le projet pour obtenir le fichier exécutable WCFHostedWindowsService.exe. Ensuite, nous devons installer le service à l'aide de l'invite de commande Visual Studio. Ouvrez donc l'invite de commande en cliquant sur Démarrer → Tous les programmes → Microsoft Visual Studio 2008 → Visual Studio Tools → Invite de commandes Visual Studio. À l'aide de l'application utilitaire d'installation, vous pouvez installer le service comme indiqué ci-dessous.

Les services WCF permettent à d'autres applications d'y accéder ou de les utiliser. Un service WCF peut être utilisé de plusieurs manières selon le type d'hébergement. Ici, nous expliquons la méthode étape par étape pour consommer un service WCF pour chacune des options d'hébergement populaires suivantes -

  • Consommer le service WCF hébergé dans IIS 5/6
  • Consommer un service WCF auto-hébergé
  • Consommation du service WCF hébergé dans le service d'activation Windows
  • Consommation du service WCF hébergé dans le service Windows

Consommation du service WCF hébergé dans IIS 5/6

Le processus de consommation d'un service WCF hébergé dans IIS 5/6 est décrit ci-dessous en détail. En outre, la discussion comprend comment créer des applications proxy et console.

Step 1- Une fois qu'un service est hébergé dans IIS, nous devons le consommer dans les applications clientes. Avant de créer l'application client, nous devons créer un proxy pour le service. Ce proxy est utilisé par l'application cliente pour interagir avec le service. Pour créer un proxy, exécutez l'invite de commandes Visual Studio 2008. À l'aide de l'utilitaire de service, nous pouvons créer la classe proxy et ses informations de configuration.

svcutilhttp: //localhost/IISHostedService/Service.svc

Après avoir exécuté cette commande, nous obtiendrons deux fichiers générés à l'emplacement par défaut.

  • MyService.cs - Classe proxy pour le service WCF

  • output.config - Informations de configuration sur le service

Step 2 - Nous allons maintenant commencer à créer l'application Console à l'aide de Visual Studio 2008 (application client).

Step 3- Ajoutez la référence 'System.ServiceModel'; il s'agit de la DLL principale de WCF.

Step 4 - Créez une classe Proxy.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace MyServiceClient {
   Class Program {
      Static void Main(string[] args) {
         // Creating Proxy for the MyService
         ServiceClient Client = newServiceClient();
         Console.WriteLine("Client calling the service...");
         Console.WriteLine("Hello Ram");
         Console.Read();
      }
   }
}

La sortie apparaît comme suit -

Consommation du service WCF auto-hébergé

Ici, l'ensemble du processus de consommation d'un service WCF auto-hébergé est expliqué étape par étape avec un codage et des captures d'écran suffisants, le cas échéant.

Step 1- Le service est hébergé, nous devons maintenant implémenter la classe proxy pour le client. Il existe différentes manières de créer le proxy.

  • En utilisant SvcUtil.exe, nous pouvons créer la classe proxy et son fichier de configuration avec des points de terminaison.

  • Ajout d'une référence de service à l'application cliente.

  • Implémentation de la classe ClientBase <T>

Parmi ces trois méthodes, la mise en œuvre de ClientBase <T> est la meilleure pratique. Si vous utilisez les deux autres méthodes, nous devons créer une classe proxy à chaque fois que nous apportons des modifications à l'implémentation du service. Mais ce n'est pas le cas pour ClientBase <T>. Il ne créera le proxy qu'au moment de l'exécution et s'occupera donc de tout.

À cette fin, créez une classe proxy, qui inclut les références de System.ServiceModel et MyCalculatorService.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
using MyCalculatorService;

namespace MyCalculatorServiceProxy {
   // WCF create proxy for ISimpleCalculator using ClientBase
   Public class MyCalculatorServiceProxy : 
   ClientBase<ISimpleCalculator>,
   
   ISimpleCalculator {
      Public int Add(int num1, int num2) {
         //Call base to do funtion
         returnbase.Channel.Add(num1, num2);
      }
   }
}

Maintenant, créez une application console, qui inclut les références de System.ServiceModel et MyCalculatorServiceProxy.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ServiceModel;
using MyCalculatorServiceProxy;

namespace MyCalculatorServiceClient {
   classProgram {
      Static void Main(string[] args) {
         MyCalculatorServiceProxy.MyCalculatorServiceProxy proxy = newMyCalculatorServiceProxy.MyCalculatorServiceProxy();
         
         Console.WriteLine("Client is running at " + DateTime.Now.ToString());
         Console.WriteLine("Sum of two numbers. 5 + 5 =" + proxy.Add(5,5));
         Console.ReadLine();
      }
   }
}

Step 2 - Les informations de point final (identiques au service) doivent être ajoutées au fichier de configuration de l'application cliente.

<?xmlversion = "1.0"encoding = "utf-8" ?>
<configuration>
   <system.serviceModel>
      <client>
         <endpoint address 
            ="http://localhost:8090/MyCalculatorServiceProxy/ISimpleCalculator"
            binding = "wsHttpBinding" contract "MyCalculatorServiceProxy.ISimpleCalculator">
            </endpoint>
      </client>
   </system.serviceModel>
</configuration>

Step 3- Avant d'exécuter l'application client, vous devez exécuter le service. Ci-dessous, la sortie de l'application cliente.

Consommation du service WCF hébergé dans WAS

La consommation d'un service WCF hébergé dans WAS est un processus simple impliquant seulement quelques étapes. Les étapes sont les suivantes -

  • Ajoutez la classe proxy et le fichier de configuration à l'application cliente.
  • Créez l'objet pour MathServiceClient et appelez la méthode.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespaceWASHostedClient {
   classProgram {
      staticvoid Main(string[] args) {
         MathServiceClient client = newMathServiceClient();
         Console.WriteLine("Sum of two number 5,6");
         Console.WriteLine(client.Add(5, 6));
         Console.ReadLine();
      }
   }
}

La sortie apparaît comme indiqué ci-dessous.

Consommation du service WCF hébergé dans le service Windows

Le processus étape par étape de la consommation d'un service WCF hébergé dans le service Windows est décrit ci-dessous en détail avec un codage et des instructions.

Une fois qu'il est hébergé avec succès, nous pouvons créer une classe proxy pour le service et commencer à l'utiliser dans l'application cliente. Ici, il est affiché avec le type d'hébergement IIS consommant.

Ajoutez la référence de ServiceModel.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespaceWindowServiceClient {
   classProgram {
      staticvoid Main(string[] args) {
         //Creating Proxy for the MyService
         MyServiceClient client = newMyServiceClient();
         Console.WriteLine("Client calling the service...");
         Console.WriteLine("Sum of two numbers 5,6");
         Console.WriteLine(client.Add(5, 6));
        
         Console.WriteLine("Subtraction of two numbers 6,5");
         Console.WriteLine(client.Sub(6, 5));
        
         Console.WriteLine("Multiplication of two numbers 6,5");
         Console.WriteLine(client.Mul(6, 5));
        
         Console.WriteLine("Division of two numbers 6,3");
         Console.WriteLine(client.Div(6, 3));
         Console.Read();
      }
   }
}

La sortie apparaît comme suit -

La liaison de service WCF est un ensemble de plusieurs éléments dans lesquels chaque élément définit la façon dont le service communique avec le client. Un élément de transport et un élément de codage de message sont les deux composants les plus vitaux de chaque liaison. Dans ce chapitre, nous aborderons diverses liaisons de service WCF couramment utilisées.

Reliure de base

La liaison de base est offerte par la classe BasicHttpBinding. Il utilise le protocole HTTP pour transporter et représenter un service WCF en tant que service Web ASP.NET (service Web ASMX), afin que les anciens clients qui utilisent les services Web ASMX puissent utiliser les nouveaux services de manière pratique.

La liaison de base est définie comme liaison par défaut dans un service Web WCF activé par Silverlight et est une liaison standard pour les communications dans le style de service Web. Il ne prend pas en charge la messagerie fiable.

Vous trouverez ci-dessous un extrait de code décrivant les paramètres par défaut pour la liaison de base.

<basicHttpBinding>
   <binding name = "basicHttpBindingDefaults" allowCookies = "false" 
      bypassProxyOnLocal = "false" hostNameComparisonMode = "StrongWildcard" 
      maxBufferPoolSize = "524288" maxBufferSize = "65536" 
      maxReceivedMessageSize = "65536" messageEncoding = "Text" proxyAddress = "" 
      textEncoding = "utf-8" transferMode = "Buffer" useDefaultWebProxy = "true" 
      closeTimeout = "00:01:00" openTimeout = "00:01:00" receiveTimeout = "00:10:00" 
      sendTimeout = "00:01:00">
   
      <readerQuotas maxArrayLength = "16384" maxBytesPerRead = "4096" 
         maxDepth = "32"
         maxNameTableCharCount = "16384" maxStringContentLength = "8192"/>

      <security mode = "None">
         <transport clientCredentialType = "None" proxyCredentialType = "None" realm = ""/>
         <message algorithmSuite = "Basic256" clientCredentialType = "UserName" />
      </security>       
   </binding>

</basicHttpBinding>

Les paramètres par défaut ci-dessus ont leurs limites évidentes, car la taille du message est limitée et il n'y a pas de mode de sécurité. Cependant, la personnalisation de la liaison de base résout ce problème comme celui ci-dessous.

<basicHttpBinding>
   <binding name = "basicHttpSecure" maxBufferSize = "100000" maxReceivedMessageSize = "100000">
   
      <readerQuotas maxArrayLength = "100000" maxStringContentLength = "100000"/>
      <security mode = "TransportWithMessageCredential" />
     
   </binding>
</basicHttpBinding>

Liaison de service Web

La liaison de service Web (WS) est fournie par la classe WSHttpBinding. Il est assez similaire à la liaison de base et utilise les mêmes protocoles pour le transport, mais offre plusieurs spécifications WS– * telles que WS – Reliable Messaging, WS – Transactions, WS – Security et bien d'autres. En un mot, WSHttpBinding est égal à la somme des spécifications basicHttpBinding et WS– *. Vous trouverez ci-dessous un extrait de code représentant les paramètres par défaut de WS Binding -

<wsHttpBinding>
   <binding name = "wsHttpBindingDefaults" allowCookies = "false" 
      bypassProxyOnLocal = "false" closeTimeout = "00:01:00" 
      hostNameComparisonMode = "StrongWildcard" 
      maxBufferPoolSize = "524288" maxReceivedMessageSize = "65536" 
      messageEncoding = "Text" openTimeout = "00:01:00" 
      receiveTimeout = "00:10:00" proxyAddress = "" sendTimeout = "00:01:00" 
      textEncoding = "utf-8" transactionFlow = "false" 
      useDefaultWebProxy = "true" > 
   
      <readerQuotas maxArrayLength = "16384" maxBytesPerRead = ."4096" 
         maxDepth = "32" maxNameTableCharCount = "16384" 
         maxStringContentLength = "8192"/>

      <reliableSession enabled = "false" ordered = "true" 
         inactivityTimeout = "oo:10:00" /> 

      <security mode = "Message">
         <message algorithmSuite = "Basic256" clientCredentialType = "Windows" 
            esatalishSecurityContext = "true" 
            negotiateServiceCredential = "true" />

         <transport clientCredentialType = "Windows"
            proxyCredentialType = "None" realm = ""/>        	
      </security>
      
   </binding>
</wsHttpBinding>

Liaison IPC

La liaison IPC utilise le canal nommé et est proposée par la classe netNamedPipeBinding. Il s'agit de la liaison la plus rapide et la plus sécurisée parmi toutes les liaisons disponibles. Bien que la sécurité au niveau des messages ne soit pas prise en charge ici, les messages sont sécurisés par défaut en raison d'une sécurité de transport robuste. Vous trouverez ci-dessous l'extrait de code représentant les paramètres par défaut pour la liaison IPC -

<netNamedPipeBinding>
   
   <binding name = "netPipeDefaults" closeTimeout = "00:01:00" 
      hostNameComparisonMode = "StrongWildcard" maxBufferPoolSize = "524288" 
      maxBufferSize = "65536" maxConnections = "10" 
      maxReceivedMessageSize = "65536" openTimeout = "00:01:00" 
      receiveTimeout = "00:10:00" sendTimeout = "00:01:00" transactionFlow = "false" 
      transactionProtocol = "OleTransactions" transferMode = "Buffered">  

      <readerQuotas maxArrayLength = "16384" maxBytesPerRead = "4096" 
         maxDepth = "32" maxNameTableCharCount = "16384" 
         maxStringContentLength = "8192"/>
   
      <security mode = "Transport">        	
      </security>
      
   </binding>
</netNamedPipeBinding>

Autres types de liaisons de service

  • TCP Binding- Fournie par la classe NetTCPBinding, cette liaison utilise le protocole TCP pour la communication au sein du même réseau et effectue le codage des messages au format binaire. Cette liaison est considérée comme la plus fiable contrairement aux autres.

  • WS Dual Binding- Ce type de liaison ressemble plus à WSHttpBinding à la seule exception qu'il facilite la communication bidirectionnelle, c'est-à-dire que les messages peuvent être envoyés et reçus à la fois par les clients et les services. Il est proposé par la classe WSDualHttpBinding.

  • Web binding - La liaison Web est conçue pour représenter les services WCF sous forme de requêtes HTTP par l'utilisation de HTTP-GET, HTTP-POST, etc. Elle est proposée par la classe WebHttpBinding et est couramment utilisée avec les réseaux sociaux.

  • MSMQ Binding- Il est proposé par la classe NetMsmqBinding et est utilisé pour fournir des solutions au cas où le service traite un message à un moment différent de celui envoyé par le client. La liaison MSMQ utilise MSMQ pour le transport et prend en charge les messages détachés en file d'attente. MSMQ est une implémentation de la mise en file d'attente des messages proposée par Microsoft.

  • Federated WS Binding- Il s'agit d'une forme spécifique de liaison WS et offre une prise en charge de la sécurité fédérée. Il est proposé par la classe WSFederationHttpBinding.

  • Peer Network Binding- Offert par la classe NetPeerTCPBinding, il est principalement utilisé dans les systèmes de partage de fichiers. Il utilise le protocole TCP mais utilise la mise en réseau des pairs comme transport. Dans ce réseau, chaque machine (nœud) agit comme un client et un serveur pour les autres nœuds. La liaison de réseau homologue est utilisée dans les systèmes de partage de fichiers tels que torrent.

  • MSMQ Integration Binding - Offert par la classe MsmqIntegrationBinding, il permet de communiquer avec les systèmes existants qui communiquent via MSMQ (Microsoft Message Queuing).

En dehors de ceux-ci, il est également possible de créer des liaisons personnalisées. Toutefois, comme il est possible de modifier les propriétés de configuration de chaque liaison WCF, la nécessité de créer des liaisons personnalisées se pose rarement.

L'ensemble des techniques employées par WCF pour lier un ensemble de messages (demandes client) aux instances de service est appelé Gestion d'instances. WCF prend en charge trois types d'activation d'instance et ils sont traités dans ce chapitre.

Service par appel

Le service par appel est le mode d'activation d'instance par défaut de WCF. Lorsqu'un service WCF est configuré pour un service par appel, un objet CLR est créé pour la durée pendant laquelle un appel ou une demande client est en cours. CLR signifie Common Language Runtime et inclut des instances de service dans WCF.

Dans le service par appel, chaque demande client obtient une nouvelle instance de service dédiée et sa consommation de mémoire est inférieure à celle d'autres types d'activation d'instance.

La propriété InstanceContextMode doit être définie sur InstanceContextMode.PerCall, afin d'indiquer qu'un service WCF agira en tant que service par appel. La propriété InstanceContextMode appartient à l'attribut ServiceBehavior. Par conséquent, un service par appel peut être configuré comme suit -

[ServiceContract]
interface IMyContract
{...}
[ServiceBehavior (InstanceContextMode = InstanceContextMode.PerCall)]
class MyService : IMyContract
{...}

Un service est ici exprimé en IMyContract. La figure suivante montre le processus d'activation de l'instance de service par appel.

Implémentation d'un service par appel

[DataContract]
class Param {....}

[ServiceContract]
interface IMyContract {
   [OperationContract]
   void MyMethod(Param objectIdentifier);
}
class MyPerCallService : IMyContract, IDisposable {
   public void MyMethod(Param objectIdentifier) {
      GetState(objectIdentifier); 
      DoWork();
      SaveState(objectIdentifier);
   }
   
   void GetState(Param objectIdentifier) {....}
   void DoWork() {....}
   void SaveState(Param objectIdentifier) {....}
   public void Dispose() {....}
}

Ici, Param est le paramètre de pseudo type inventé pour l'exemple ci-dessus.

Service par session

Dans ce mode d'activation de WCF, une session privée ou on peut dire confidentielle est maintenue entre les deux entités, c'est-à-dire le client et une instance de service particulière. Aussi connu sous le nom de service de session privée, le service par session offre une nouvelle instance de service qui reste dédiée à chaque demande client et autonome de toutes les autres instances appartenant à ce service sensible à la session.

Pour lancer un service par session, la propriété InstanceContextMode doit être définie sur PerSession. Ici, l'instance de service reste en mémoire pendant toute la durée de la session.

Le mode d'activation souffre de l'évolutivité car le service configuré est incapable de prendre en charge des clients en attente supplémentaires autres que quelques-uns (ou peut-être jusqu'à une centaine) en raison du coût impliqué dans chacune de cette instance de service dédiée.

Un service par session peut être configuré comme -

[ServiceBehavior (InstanceContextMode = InstanceContextMode.PerSession)]
class MyService : IMyContract
{...}

Le processus du service par session peut être décrit comme illustré dans la figure suivante -

Le code suivant montre un contrat et un service configurés pour l'utilisation d'une session privée. La sortie indique que le client a effectivement obtenu une instance de service dédiée.

Code de service

[ServiceContract(Session = true)]
interface IMyContract {
   [OperationContract]
   void MyMethod();
}

[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerSession)]
class MyService : IMyContract, IDisposable {
   int m_Counter = 0; MyService() {Console.WriteLine("MyService.MyService()"); }
   
   public void MyMethod() {
      m_Counter++;
      Console.WriteLine("Counter = " + m_Counter);
   }
   public void Dispose() { 
      Console.WriteLine("MyService.Dispose()"); 
   }
}

Code client

MyContractProxy proxy = new MyContractProxy(); proxy.MyMethod(); proxy.MyMethod(); 
proxy.Close();

Production

MyService.MyService() Counter = 1 Counter = 2 MyService.Dispose()

Service Singleton

Dans ce mode d'activation de WCF, toutes les demandes client indépendantes les unes des autres sont connectées à la même instance unique bien connue, indépendamment de leur connexion aux points de terminaison de service. Le service singleton est supprimé uniquement lorsque l'hôte se ferme.

Ce service est créé une seule fois lors de la création de l'hôte. Dans le cas où l'hôte ne dispose d'aucune instance de singleton, le service renvoie la valeur NULL. Le mode d'activation est à son meilleur lorsque la quantité de travail dans chaque appel de méthode est faible et qu'aucune opération en attente n'est là en arrière-plan.

La propriété InstanceContextMode doit être définie sur InstanceContextMode.Single pour lancer ce service Singleton.

Par conséquent, un service Singleton peut être configuré comme -

[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single)]
class MySingleton : ...
{...}

Le processus du service Singleton est illustré dans la figure suivante -

Le code suivant est utilisé pour initialiser et héberger une instance singleton.

Code de service

[ServiceContract]
interface IMyContract {
   [OperationContract]
   void MyMethod( );
}
[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single)]
class MySingleton : IMyContract {
   int m_Counter = 0;
   
   public int Counter {
      get {
         return m_Counter;
      }
      set {
         m_Counter = value;
      }
   }
   public void MyMethod( ) {
      m_Counter++;
      Trace.WriteLine("Counter = " + Counter);
   }
}

Code hôte

MySingleton singleton = new MySingleton( );
singleton.Counter = 42;
ServiceHost host = new ServiceHost(singleton);
host.Open( );

//Do some blocking calls then
host.Close( );

Code client

MyContractClient proxy = new MyContractClient( );
proxy.MyMethod( );
proxy.Close( );

Production

Counter = 43

Une transaction dans WCF est un ensemble d'opérations qui suivent certaines propriétés, collectivement appelées ACID. Ici, si une seule opération échoue, tout le système échoue automatiquement. Lorsqu'une commande est passée en ligne, une transaction a lieu. L'exemple suivant peut être utile pour comprendre le processus de transaction en termes plus simples.

Exemple

Supposons que vous ayez commandé un téléviseur LCD dans une boutique en ligne et que vous allez payer le montant par carte de crédit. Lorsque vous saisissez les informations requises pour passer la commande, deux opérations se produisent simultanément.

Premièrement, le montant spécifié est débité de votre compte bancaire et deuxièmement, le compte fournisseur est crédité du même montant. Les deux opérations doivent s'exécuter avec succès pour avoir une transaction réussie.

Propriétés de transaction WCF

Les quatre propriétés suivies d'une transaction WCF sont les suivantes:

  • Atomic - Toutes les opérations doivent agir comme une seule opération indivisible à l'issue d'une transaction.

  • Consistency - Quel que soit le jeu d'opérations, le système est toujours dans un état de cohérence, c'est-à-dire que le résultat de la transaction est toujours conforme à l'attente.

  • Isolation - L'état intermédiaire du système n'est visible par aucune entité du monde extérieur tant que la transaction n'est pas terminée.

  • Durability - L'état engagé est maintenu quel que soit le type de panne (matériel, panne de courant, etc.)

Lors de la configuration d'une transaction WCF, certains facteurs doivent être pris en compte. Il s'agit du comportement de liaison et de fonctionnement.

Binding- Les liaisons qui prennent en charge la transaction dans WCF ne sont que quelques-unes et il est essentiel de faire un choix parmi ces liaisons uniquement, qui restent désactivées par défaut et doivent être activées pour obtenir le support requis pour la transaction. Ces liaisons sont les suivantes -

  • NetTcpBinding
  • NetNamedPipeBinding
  • WSHttpBinding
  • WSDualHttpBinding
  • WSFederationHttpBinding

Operation behavior- Alors qu'une liaison facilite le chemin de propagation des transactions, une opération prend en charge le traitement des transactions ainsi que la configuration des opérations. Le comportement des opérations utilise principalement deux attributs: TransactionFlow et TransactionScopeRequired. Ici, il convient de noter que TransactionFlow a principalement trois valeurs, à savoir: Autorisé, Obligatoire et Non autorisé.

Le code suivant montre si la modification de la configuration de la liaison et du contrat d'opération facilite la propagation du client.

<bindings> 
   <wsHttpBinding> 
      <binding name = "MandatoryTransBinding" transactionFlow = "true"> 
         <reliableSession enabled ="true"/>
      </binding>
   </wsHttpBinding> 
</bindings>

Protocole de transaction

WCF utilise trois types de protocoles pour les transactions -

  • Lightweight
  • Transaction Ole
  • Transaction WS-atomique (WS-AT)

De tous les trois, WS-AT est un protocole interopérable et permet le flux de transactions distribuées à travers les pare-feu. Cependant, ce protocole ne doit pas être utilisé lorsque la transaction est strictement basée sur la technologie Microsoft.

Phases de la transaction WCF

Il existe deux phases dans une transaction WCF, comme illustré dans la figure suivante.

  • Prepare Phase - Dans cette phase, le gestionnaire de transaction vérifie si toutes les entités sont prêtes à s'engager pour la transaction ou non.

  • Commit Phase - Dans cette phase, l'engagement des entités démarre dans la réalité.

La figure suivante illustre les fonctions des deux phases d'une transaction WCF.

Activation d'une transaction WCF

Pour activer une transaction WCF avec succès, il faut suivre une série de six étapes de manière séquentielle. Les étapes requises sont décrites ci-dessous.

Step 1 − Creation of two WCF Services

La première étape à cet égard consiste à créer deux projets de service dans WCF pour participer à une seule transaction. Les transactions de base de données seront effectuées sur ces deux services et on comprendra comment elles sont unifiées par une transaction WCF. Une application Web de WCFTransactions a également été créée pour consommer les deux services créés dans une seule étendue de transaction.

Step 2 − Method creation and its attribution with TransactionFlow attribute

Ici, une méthode UpdateData sera créée pour les deux services WCF à insérer dans la base de données avec l'attribut OperationContract. Pour accomplir cette tâche, une classe d'interface est d'abord créée à l'aide de l'attribut ServiceContract. Pour activer la transaction dans la méthode nouvellement créée, elle est attribuée avec TransactionFlow et les transactions sont autorisées à l'aide de la valeur autorisée.

[ServiceContract]
public interface IService1 {
   [OperationContract]
   [TransactionFlow(TransactionFlowOption.Allowed)]
   void UpdateData();
}

Step 3− Implementation of WCF service with TransactionScopeRequired attribute

Cela se fait en utilisant le code ci-dessous -

[OperationBehavior(TransactionScopeRequired = true)]
public void UpdateData() {
   try {
      SqlConnection objConnection = new SqlConnection(strConnection);
      objConnection.Open();
      
      using(SqlTransaction transaction = Program.dbConnection.BeginTransaction()) {
     	   Boolean doRollback = false;
     	   using(SqlCommand cmd = new SqlCommand(
            "insert into Customer (Customer name, Customer code) values ('sss', 'sss')"objConnection))
         
     	   try {
            cmd.ExecuteNonQuery();
     	   } catch(SqlException) {
            doRollback = true;
            break;
     	   }
      }
      
      if(doRollback)
         transaction.Rollback();
      else
         transaction.Commit();  
   }
   finally {
      objConection.Close();
   }
}

Step 4 − Enabling Transaction Flow by WCF Service Config File

Son codage se fait comme suit -

<bindings>
   <wsHttpBinding>
      <binding name = "TransactionalBind" transactionFlow = "true"/>
   </wsHttpBinding>
</bindings>

Il est essentiel d'attacher la liaison autorisée de transaction avec le point de terminaison pour exposer le service WCF.

<endpoint address = "" binding = "wsHttpBinding" bindingConfiguration = "TransactionalBind" contract = "WcfService1.IService1">

Step 5 − Calling both the services in a single transaction

Ici, les deux services ci-dessus sont appelés en une seule transaction et à cette fin, l'objet TransactionScope est utilisé pour regrouper les deux services. La méthode Complete de l'objet ci-dessus est appelée pour valider une transaction WCF. Pour annuler, la méthode Dispose doit être appelée.

using (TransactionScope ts = new TransactionScope(TransactionScopeOption.RequiresNew)) {
   try {
      // Call your webservice transactions here
      ts.Complete();
   } catch (Exception ex) {
      ts.Dispose();
   }
}

Le petit morceau du code complet dans lequel les transactions WCF ont été regroupées dans une seule étendue est illustré ci-dessous:

using (TransactionScope ts = new TransactionScope(TransactionScopeOption.RequiresNew)) {
   try {
      ServiceReference1.Service1Client obj = newServiceReference1.Service1Client();
      obj.UpdateData();
      ServiceReference2.Service1Client obj1 = new ServiceReference2.Service1Client();
      obj1.UpdateData();
      ts.Complete();
   } catch (Exception ex) {
      ts.Dispose();
   }
}

Step 6 − Testing WCF transaction

Le test est effectué à la 6ème et dernière étape et après avoir appelé le 1er service WCF, une exception est forcée.

Le service WCF RIA est une infrastructure de niveau supérieur et un nouveau composant de frameworks comme .NET 4 et Silverlight 4 qui facilite la procédure de création d'une application métier complexe dans Silverlight en offrant une validation côté client. RIA signifie Rich Internet Applications.

Il faut noter ici que Silverlight est un framework proposé par Microsoft, idéal pour les applications Internet riches et est disponible pour une utilisation en tant que plug-in de navigateur, tout comme Adobe Flash.

Le service WCF RIA est principalement basé sur la version standard du service WCF. La figure suivante illustre une partie de l'architecture WCF, dans laquelle les services WCF RIA se concentrent en général.

La création d'un service WCF RIA est la prochaine étape pour mieux comprendre le concept. La procédure étape par étape est donnée ci-dessous.

Step 1 - Créez un nouveau projet Web du nom SLWCFRiaServices.Web à l'aide de Silverlight 5, puis ajoutez un nouvel élément en sélectionnant ADO.NET Entity Data Model au même.

Step 2 - Choisissez maintenant le contenu du modèle dans l'assistant de modèle de données d'entité en générant le modèle à partir de la base de données.

Step 3 - Dans le même assistant, choisissez votre connexion de données et vos objets de base de données.

Step 4 - Construisez la solution de sorte qu'à l'avenir, la reconnaissance du modèle de données ne pose pas de problème pour le service de domaine que vous allez créer.

Step 5 - Créez maintenant un service de domaine dans le projet Web en ajoutant un nouvel élément et assurez-vous d'activer l'accès client.

Step 6 - Dans la toute prochaine étape, certaines classes seront générées et il est essentiel de les reconstruire.

Step 7 - Dans cette étape, DataDomainContext est affiché par le panneau Sources de données.

Step 8 - Dans cette étape, l'article sous le DataDomainContext doit être sélectionné et personnalisé.

Step 9- Attacher le contrôle DataGrid à la source de données est l'étape engagée ici, ainsi que la sélection des thèmes. Ici, le thème BureauBlue a été sélectionné.

Step 10- La dernière et dernière étape consiste à accéder à l'écran de conception et à ajouter une entité dans la zone de mise en page de MainPage par simple glisser-déposer. Il est également vital de s'assurer que AutoGenerateColumns = "True" et de l'exécuter pour afficher la sortie.

Conditions préalables

Il existe certaines conditions préalables pour profiter du plein potentiel des services WCF RIA -

  • Visual Studio 2010 / Visual Studio 2012
  • Silverlight Developer Runtime
  • Dernière version de la boîte à outils des services RIA
  • SDK (Kit de développement logiciel)

Service de domaine WCF RIA

Un service de domaine comprend un ensemble d'opérations de données liées aux affaires. Ce n'est rien d'autre qu'un service WCF qui expose la logique métier de toute application de service WCF RIA.

Un service de domaine WCF RIA a la classe d'hébergement DomainServiceHost en interne, qui à son tour utilise la classe WCF ServiceHost pour héberger l'application. Pour rendre le service de domaine accessible pour le projet client, il doit avoir l'attribut EnableClientAccessAttribute. L'attribut est appliqué automatiquement chaque fois qu'une nouvelle classe de service de domaine est ajoutée.

La figure suivante montre l'architecture d'un service de domaine WCF RIA -

Services WCF RIA - Interrogation de données

La figure suivante montre comment une requête est créée côté client et exécutée côté serveur pour renvoyer des résultats interrogeables. DAL signifie Data Access Layer.

Services WCF RIA - Mise à jour des données

La figure suivante montre comment les données sont mises à jour en exécutant l'opération CUD (Create Update Delete) côté serveur. Il convient de noter ici que le service WCF RIA est toujours sans état du côté serveur.

Un service WCF se vante d'un système de sécurité robuste avec deux modes ou niveaux de sécurité afin que seul un client prévu puisse accéder aux services. Les menaces de sécurité courantes dans une transaction distribuée sont modérées dans une large mesure par WCF.

Principales caractéristiques de sécurité

Le service WCF possède quatre fonctionnalités de sécurité clés, comme illustré dans la figure ci-dessous.

  • Authentication - Ici, l'authentification ne se limite pas à l'identification de l'expéditeur du message, mais est mutuelle, c'est-à-dire que l'authentification du destinataire du message est nécessaire pour exclure toute possibilité d'attaque intermédiaire.

  • Authorization- Il s'agit de la prochaine étape prise par un service WCF pour assurer la sécurité et il est ici déterminé si le service doit autoriser l'appelant à continuer ou non. Bien que l'autorisation ne dépende pas de l'authentification, elle suit normalement l'authentification.

  • Confidentiality- L'échange d'informations entre un appelant et un service est gardé confidentiel pour restreindre son interprétation par des tiers auxquels le message n'est pas destiné. Pour rendre cela possible, le cryptage est utilisé avec une grande variété d'autres mécanismes.

  • Integrity - Le dernier concept clé est le maintien de l'intégrité, c'est-à-dire l'assurance que le message n'a pas été falsifié par quiconque au cours de son trajet de l'expéditeur au destinataire.

Transfert du mode de sécurité

WCF propose les modes de sécurité de transfert suivants pour garantir une communication sécurisée entre un client et un serveur. Les divers modes de sécurité de transfert sont mentionnés ci-dessous.

  • None- Ce mode ne garantit aucun type de sécurité des messages et le service n'obtient aucune information d'identification sur le client. Ce mode est très risqué, car il peut permettre la falsification des messages et n'est donc pas recommandé.

<wsHttpBinding>
   <binding name = "WCFSecurityExample">
      <security mode = "None"/>
   </binding>
</wsHttpBinding>
  • Transport- Ce mode est le moyen le plus simple de réaliser un transfert sécurisé de message via l'utilisation de protocoles de communication tels que TCP, IPC, Https et MSMQ. Ce mode est plus efficace lorsque le transfert est point à point et est principalement utilisé dans un environnement contrôlé, c'est-à-dire des applications intranet.

<wsHttpBinding>
   <binding name = "WCFSecurityExample">
      <security mode = "Transport"/>
   </binding>
</wsHttpBinding>
  • Message- Le mode de sécurité permet une authentification mutuelle et offre une grande confidentialité car les messages sont cryptés et peuvent être transportés via http, qui n'est pas considéré comme un protocole sécurisé. Ici, la sécurité est fournie de bout en bout sans tenir compte du nombre d'intermédiaires impliqués dans un transfert de message et s'il existe un transport sécurisé ou non. Le mode est généralement utilisé par les applications Internet.

<wsHttpBinding>
   <binding name = "WCFSecurityExample">
      <security mode = "Message"/>
   </binding>
</wsHttpBinding>
  • Mixed - Ce mode de sécurité n'est pas utilisé fréquemment et l'authentification client n'est proposée qu'au niveau client.

<wsHttpBinding>
   <binding name = "WCFSecurityExample">
      <security mode = "TransportWithMessageCredential"/>
   </binding>
</wsHttpBinding>
  • Both- Ce mode de sécurité comprend à la fois la sécurité du transport et la sécurité des messages pour offrir une couverture de sécurité robuste, mais entraîne souvent une surcharge des performances globales. Celui-ci est pris en charge uniquement par MSMQ.

<netMsmqBinding>
   <binding name = "WCFSecurityExample">
      <security mode = "Both"/>
   </binding>
</netMsmqBinding>

Toutes les liaisons WCF, à l'exception de BasicHttpBinding, ont une certaine sécurité de transfert par défaut.

Niveau de sécurité des messages

La sécurité au niveau des messages ne dépend pas des protocoles WCF. Il est utilisé avec les données de message elles-mêmes en chiffrant les données à l'aide d'un algorithme standard. Un certain nombre d'informations d'identification client sont disponibles pour différentes liaisons pour le niveau de sécurité des messages et elles sont décrites ci-dessous.

Client credentials for message level security in WCF

None- Ici, le cryptage est utilisé pour sécuriser le message, alors qu'aucune authentification client n'est effectuée, ce qui signifie que le service est accessible par un client anonyme. À l'exception de BasicHttpBinding, toutes les liaisons WCF prennent en charge ces informations d'identification client. Cependant, il convient de noter que pour NetNamedPipeBinding, ces informations d'identification client ne sont pas du tout disponibles.

  • Windows- Ici, le cryptage des messages et l'authentification client ont lieu pour un utilisateur connecté en temps réel. Dans ce cas également, contrairement à toutes les autres liaisons WCF, NetNamedPipeBinding n'est pas disponible et BasicHttpBinding ne prête pas sa prise en charge.

  • UserName- Ici, les messages sont cryptés et sécurisés en offrant un nom d'utilisateur, et les clients sont authentifiés car ils doivent offrir un mot de passe. BasicHttpBinding, tout comme les deux informations d'identification client ci-dessus, ne prend pas en charge UserName et n'est pas disponible pour NetNamedPipeBinding.

  • Certificate- Outre le cryptage des messages, le client et le service obtiennent une authentification avec certificat. Ces informations d'identification client sont disponibles et sont prises en charge par toutes les liaisons WCF à l'exception de NetNamedPipeBinding.

  • IssuedToken- Les jetons émis par une autorité comme Cardspace sont utilisés pour authentifier les messages. Le cryptage des messages est également effectué ici.

Le code suivant montre comment les informations d'identification du client sont configurées dans le niveau / mode de sécurité des messages WCF.

<netTcpBinding>
   <binding name = "WCFMessageSecurityExample">
      <security mode = "Message">
         <message clientCredentialType = "None"/>
      </security>   
   </binding>
</netTcpBinding>

<netMsmqBinding>...</netMsmqBinding>
</bindings>
<behaviors>...</behaviors>

Ici, il faut noter que le mode de sécurité de transport a un avantage sur le niveau de sécurité des messages, car le premier est plus rapide. Il ne nécessite aucun codage supplémentaire et offre une prise en charge de l'interopérabilité, et ne réduit donc pas les performances globales.

Cependant, du point de vue de la sécurité, le mode de sécurité des messages est plus robuste et indépendant des protocoles et offre une sécurité de bout en bout.

Un développeur de services WCF peut rencontrer des erreurs imprévues qui nécessitent un rapport au client de manière appropriée. Ces erreurs, appeléesexceptions, sont normalement gérés à l'aide de blocs try / catch, mais encore une fois, c'est très spécifique à la technologie.

Étant donné que la zone de préoccupation d'un client ne concerne pas la façon dont une erreur s'est produite ou les facteurs contribuant à une erreur, le contrat SOAP Fault est utilisé pour communiquer le message d'erreur du service au client dans WCF.

Un contrat Fault permet au client d'avoir une vue documentée des erreurs survenues dans un service. L'exemple suivant donne une meilleure compréhension.

Step 1 - Un service de calcul simple est créé avec une opération de division qui générera des exceptions générales.

using System;
usingSystem.Collections.Generic;
usingSystem.Linq;
usingSystem.Runtime.Serialization;
usingSystem.ServiceModel;
usingSystem.Text;

namespace Calculator {
   // NOTE: You can use the "Rename" command on the "Refactor" menu to change 
   // the interface name "IService1" in both code and config file together.
   
   [ServiceContract]
   
   public interface IService1 {
      [OperationContract]
      int divide(int num1, int num2);
      // TODO: Add your service operations here
   }
}

Le codage du fichier de classe est indiqué ci-dessous -

Maintenant, lorsque nous essayons de diviser le nombre 10 par zéro, le service de calcul lèvera une exception.

L'exception peut être gérée par le bloc try / catch.

Maintenant, lorsque nous essayons de diviser un nombre entier par 0, il retournera la valeur 10 car nous l'avons traité dans le bloc catch.

Step 2 - FaultException est utilisé dans cette étape pour communiquer les informations d'exception au client à partir du service.

public int Divide(int num1, int num2) { 
   //Do something 
   throw new FaultException("Error while dividing number"); 
}

Step 3- Il est également possible de créer un type personnalisé pour envoyer le message d'erreur à l'aide de FaultContract. Les étapes essentielles pour créer un type personnalisé sont mentionnées ci-dessous -

Un type est défini par l'utilisation d'un contrat de données et les champs destinés à être renvoyés sont spécifiés.

L'opération de service est décorée par l'attribut FaultContract. Le nom du type est également spécifié.

Une instance de service est créée pour déclencher des exceptions et des propriétés d'exception personnalisées sont attribuées.