Fonctionnement du code client généré
L' ServiceModel Metadata Utility Tool (Svcutil.exe) génère du code client et un fichier de configuration d'application cliente à des fins de création d’applications clientes. Cette rubrique présente des exemples de code généré pour des scénarios de contrat de service standard. Pour plus d’informations sur la création d’une application cliente avec du code généré, consultez Vue d’ensemble d’un client WCF.
Vue d’ensemble
Si vous utilisez Visual Studio afin de générer des types de clients Windows Communication Foundation (WCF) pour votre projet, il n'est en général pas nécessaire d'examiner le code client généré. Si vous n'utilisez pas un environnement de développement qui exécute les mêmes services pour vous, vous pouvez utiliser un outil tel que Svcutil.exe pour générer le code client, puis utiliser ce code pour développer votre application cliente.
Svcutil.exe disposant de plusieurs options qui modifient les informations de type générées, cette rubrique ne traite pas de tous les scénarios. Toutefois, les tâches standard suivantes impliquent la localisation de code généré :
Identification d'interfaces de contrat de service.
Identification de la classe de client WCF.
Identification des types de données.
Identification des contrats de rappel pour les services duplex.
Identification de l'interface de canal de contrat de service d'assistance.
Recherche d'interfaces de contrat de service
Pour trouver les interfaces qui modèlent des contrats de service, recherchez les interfaces marquées avec l'attribut System.ServiceModel.ServiceContractAttribute . Cet attribut est souvent difficile à trouver avec une lecture rapide en raison de la présence d'autres attributs et des propriétés explicites définies sur l'attribut lui-même. N'oubliez pas que l'interface de contrat de service et l'interface de contrat client sont deux types différents. L'exemple de code suivant illustre le contrat de service d'origine.
[ServiceContractAttribute(
Namespace = "http://microsoft.wcf.documentation"
)]
public interface ISampleService
{
[OperationContractAttribute]
[FaultContractAttribute(typeof(microsoft.wcf.documentation.SampleFault))]
string SampleMethod(string msg);
}
L'exemple de code suivant illustre le même contrat de service, tel que généré par Svcutil.exe.
[System.ServiceModel.ServiceContractAttribute(
Namespace = "http://microsoft.wcf.documentation"
)]
public interface ISampleService
{
[System.ServiceModel.OperationContractAttribute(
Action = "http://microsoft.wcf.documentation/ISampleService/SampleMethod",
ReplyAction = "http://microsoft.wcf.documentation/ISampleService/SampleMethodResponse"
)]
[System.ServiceModel.FaultContractAttribute(
typeof(microsoft.wcf.documentation.SampleFault),
Action = "http://microsoft.wcf.documentation/ISampleService/SampleMethodSampleFaultFault"
)]
string SampleMethod(string msg);
}
Vous pouvez utiliser l'interface de contrat de service générée avec la classe System.ServiceModel.ChannelFactory pour créer un objet canal WCF avec lequel appeler des opérations de service. Pour plus d’informations, consultez Guide pratique pour utiliser ChannelFactory.
Recherche de classes de client WCF
Pour trouver la classe de client WCF qui implémente le contrat de service que vous souhaitez utiliser, recherchez une extension de System.ServiceModel.ClientBase<TChannel>, où le paramètre de type est l'interface de contrat de service que vous avez trouvée précédemment et qui étend cette interface. L'exemple de code suivant illustre la classe ClientBase<TChannel> de type ISampleService
.
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "3.0.0.0")]
public partial class SampleServiceClient : System.ServiceModel.ClientBase<ISampleService>, ISampleService
{
public SampleServiceClient()
{
}
public SampleServiceClient(string endpointConfigurationName)
:
base(endpointConfigurationName)
{
}
public SampleServiceClient(string endpointConfigurationName, string remoteAddress)
:
base(endpointConfigurationName, remoteAddress)
{
}
public SampleServiceClient(string endpointConfigurationName, System.ServiceModel.EndpointAddress remoteAddress)
:
base(endpointConfigurationName, remoteAddress)
{
}
public SampleServiceClient(System.ServiceModel.Channels.Binding binding, System.ServiceModel.EndpointAddress remoteAddress)
:
base(binding, remoteAddress)
{
}
public string SampleMethod(string msg)
{
return base.Channel.SampleMethod(msg);
}
}
Vous pouvez utiliser cette classe de client WCF en créant une nouvelle instance et en appelant les méthodes qu'elle implémente. Ces méthodes appellent l'opération de service avec laquelle elle est conçue et configurée pour interagir. Pour plus d’informations, consultez Vue d’ensemble d’un client WCF.
Notes
Lorsque SvcUtil.exe génère une classe de client WCF, il ajoute un DebuggerStepThroughAttribute à la classe de client qui empêche les débogueurs de parcourir pas à pas la classe de client WCF.
Recherche de types de données
Pour trouver des types de données dans le code généré, le mécanisme le plus simple consiste à identifier le nom de type spécifié dans un contrat et à rechercher le code pour cette déclaration de type. Par exemple, le contrat suivant spécifie que le SampleMethod
peut retourner une erreur SOAP de type microsoft.wcf.documentation.SampleFault
.
[System.ServiceModel.OperationContractAttribute(
Action = "http://microsoft.wcf.documentation/ISampleService/SampleMethod",
ReplyAction = "http://microsoft.wcf.documentation/ISampleService/SampleMethodResponse"
)]
[System.ServiceModel.FaultContractAttribute(
typeof(microsoft.wcf.documentation.SampleFault),
Action = "http://microsoft.wcf.documentation/ISampleService/SampleMethodSampleFaultFault"
)]
string SampleMethod(string msg);
La recherche de SampleFault
localise la déclaration de type suivante.
[assembly: System.Runtime.Serialization.ContractNamespaceAttribute(
"http://microsoft.wcf.documentation",
ClrNamespace = "microsoft.wcf.documentation"
)]
namespace microsoft.wcf.documentation
{
using System.Runtime.Serialization;
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.Runtime.Serialization", "3.0.0.0")]
[System.Runtime.Serialization.DataContractAttribute()]
public partial class SampleFault : object, System.Runtime.Serialization.IExtensibleDataObject
{
private System.Runtime.Serialization.ExtensionDataObject extensionDataField;
private string FaultMessageField;
public System.Runtime.Serialization.ExtensionDataObject ExtensionData
{
get
{
return this.extensionDataField;
}
set
{
this.extensionDataField = value;
}
}
[System.Runtime.Serialization.DataMemberAttribute()]
public string FaultMessage
{
get
{
return this.FaultMessageField;
}
set
{
this.FaultMessageField = value;
}
}
}
}
Dans ce cas, le type de données est le type de détail levé par une exception spécifique sur le client, un FaultException<TDetail> où le paramètre de type de détail est microsoft.wcf.documentation.SampleFault
. Pour plus d’informations sur les types de données, consultez Spécification du transfert de données dans les contrats de service. Pour plus d’informations sur la gestion des exceptions dans les clients, consultez Envoi et réception des erreurs.
Recherche de contrats de rappel pour les services duplex
Si vous trouvez un contrat de service pour lequel l'interface de contrat spécifie une valeur pour la propriété ServiceContractAttribute.CallbackContract , ce contrat spécifie un contrat duplex. Les contrats duplex requièrent que l'application cliente crée une classe de rappel qui implémente le contrat de rappel et passe une instance de cette classe au System.ServiceModel.DuplexClientBase<TChannel> ou System.ServiceModel.DuplexChannelFactory<TChannel> utilisé pour communiquer avec le service. Pour plus d’informations sur les clients duplex, consultez Guide pratique pour accéder aux services ayant un contrat duplex.
Le contrat suivant spécifie un contrat de rappel de type SampleDuplexHelloCallback
.
[System.ServiceModel.ServiceContractAttribute(
Namespace="http://microsoft.wcf.documentation",
ConfigurationName="SampleDuplexHello",
CallbackContract=typeof(SampleDuplexHelloCallback),
SessionMode=System.ServiceModel.SessionMode.Required
)]
public interface SampleDuplexHello
{
[System.ServiceModel.OperationContractAttribute(
IsOneWay=true,
Action="http://microsoft.wcf.documentation/SampleDuplexHello/Hello"
)]
void Hello(string greeting);
}
<System.ServiceModel.OperationContractAttribute(IsOneWay:=True, _
Action:="http://microsoft.wcf.documentation/SampleDuplexHello/Hello")> _
Sub Hello(ByVal greeting As String)
End Interface 'SampleDuplexHello
La recherche de ce contrat de rappel localise l'interface suivante que l'application cliente doit implémenter.
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "3.0.0.0")]
public interface SampleDuplexHelloCallback
{
[System.ServiceModel.OperationContractAttribute(
IsOneWay=true,
Action="http://microsoft.wcf.documentation/SampleDuplexHello/Reply"
)]
void Reply(string responseToGreeting);
}
<System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "3.0.0.0")> _
Public Interface SampleDuplexHelloCallback
<System.ServiceModel.OperationContractAttribute( _
IsOneWay:=True, _
Action:="http://microsoft.wcf.documentation/SampleDuplexHello/Reply")> _
Sub Reply(ByVal responseToGreeting As String)
End Interface 'SampleDuplexHelloCallback
Recherche d'interfaces de canal de contrat de service
Lorsque vous utilisez la classe ChannelFactory avec une interface de contrat de service, vous devez effectuer une conversion de type dans l'interface System.ServiceModel.IClientChannel pour ouvrir, fermer ou abandonner le canal de manière explicite. Pour faciliter son utilisation, l'outil Svcutil.exe génère également une interface d'assistance qui implémente à la fois l'interface de contrat de service et IClientChannel afin de vous permettre d'interagir avec l'infrastructure de canal client sans devoir convertir de type. Le code suivant illustre la définition d'un canal client d'assistance qui implémente le contrat de service précédent.
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "3.0.0.0")]
public interface ISampleServiceChannel : ISampleService, System.ServiceModel.IClientChannel
{
}