620 likes | 707 Views
2. előadás Szerződések. Készítette: Galán Mihály. Miről lesz szó?. Viselkedés szerződések definiálása Szolgáltatás szerződések és szolgáltatás típusok Hiba szerződések Üzenetcsere minták Szerkezeti szerződések definiálása Adat szerződések Kollekciók Üzenetszerződések.
E N D
2. előadásSzerződések Készítette: Galán Mihály
Miről lesz szó? • Viselkedés szerződések definiálása • Szolgáltatás szerződések és szolgáltatás típusok • Hiba szerződések • Üzenetcsere minták • Szerkezeti szerződések definiálása • Adat szerződések • Kollekciók • Üzenetszerződések
Szolgáltatás viselkedésének megadása • Maga a szolgáltatás hogyan viselkedik és ehhez milyen műveletek szükségesek. • Mikor és milyen hiba léphet fel a szolgáltatásban. • Mik azok a MEP követelmények, amik kölcsönhatásba lépnek a szolgáltatással? (kérés/válasz, egyirányú, duplex)
Szolgáltatás szerződések és szolgáltatás típusok • A szolgáltatás szerződés egy kollektív mechanizmus, melyben a szolgáltatás képességei és követelményei vannak specifikálva a fogyasztó számára. • Ezek a mechanizmusok • .NET interface típus • Operációk a típuson belül • .NET attribútumok • ServiceContractAttribute • OperationContractAttribute • MessageParameterAttribute
Példa szolgáltatás szerződésre (Task Manager) [ServiceContract()] publicinterfaceITaskManagerService { [OperationContract()] int AddTask (StringtaskDescription, stringassignedTo) //stb… }
ServiceContractAttribute I. • A System.ServiceModelnamespace-ben definiált. • Alkalmazható .NET interfésznél és osztálynál. • Az attribútum nem származtatott. • Deklarálható paraméter nélkül is.
ServiceContractAttribute III. [ServiceContract(Name=„TaskManagerService”, Namespace = „http://schemas…”)] publicinterfaceITaskManagerService { //stb… }
OperationContractAttribute I. • Szintén a System.ServiceModelnamespace-ben definiált. • Csak metódusoknál alkalmazható. • A metódust úgy kell deklarálni, hogy a szolgáltatás szerződéshez tartozzon.
OperationContractAttribute III. [ServiceContract()] publicinterfaceSomeCrudContract{ [OperationContract(IsOneWay = true, Action = „urn:crud:insert”)] voidProcessInsertMessage(Messagemessage) [OperationContract(IsOneWay = true, Action =„urn:crud:update”)] voidProcessUpdateMessage(Messagemessage) [OperationContract(IsOneWay = true, Action =„urn:crud:delete”)] voidProcessDeleteMessage(Messagemessage) }
MessageParameterAttribute I. • Szintén a System.ServiceModelnamespace-ben definiált. • Irányítja, hogyan az operációk paramétereinek a neve és a visszatérési értékek hogyan jelenjenek meg a szolgáltatás leírásban. • Egyetlen paramétere van, ez pedig a Name paraméter.
MessageParameterAttribute II. [OperationContract()] [return: MessageParameter(Name=„responseString”)] stringSomeOp([MessageParameter(Name=„string”] string s)
Hiba szerződések • Hiba kontra kivétel • A kivétel egy .NET mechanizmus, mely a futás során felmerülő problémákat kezeli. • Throw, catch, ignore mechanizmusok • Kezelni kell őket, különben a .NET terminálja azt a szálat, amelyikben a hiba történt. • SOAP hiba mechanizmusra hivatkozik. • A hibát vagy a hiba feltételeit a szolgáltatástól a felhasználóig szállítja. • Megvan a bekövetkező hiba üzenetének a struktúrája.
FaultExceptionClass • Standard mechanizmus, mely a .NET kivételek és SOAP hibák között közvetít. • FaultException: típus nélküli hiba adatot küld a felhasználónak. • DaultExcepton <TDetail>: típusos adatot küld a felhasználónak. A TDetail jelenti a hiba információ típusát.
FaultContractAttribute • System.ServiceModel • Megengedi a fejlesztőnek, hogy deklarálja, milyen hiba következhet be a szolgáltatás egyes operációinál. • Tulajdonságok: • Az attribútum csak a műveletnél alkalmazható. • Nem származtatott. • Többször alkalmazható.
Példa [ServiceContract()] publicinterfaceICalculatorService { [OperationContract()] [FaultContract(typeof(string))] doubleDivide(double numerator, doubledenominator); } publicclassCalculatorService : ICalculatorService { publicdoubleDivide(double numerator, doubledenominator){ if(denominator == 0.0d){ StringfaultDetail = „Youcannotdividebyzero”; thrownewFaultException<sring>(faultDetail); } return numerator/denominator; } }
Üzenetváltási lehetőségek • Request/response • OneWay • Duplex
Request/response I. • Legnépszerűbb üzenetváltási módszer. • Egyszerűen beállítható. • OperationContractAttribute: IsOneWay paraméter. • Lehetővé teszi, hogy a szolgáltatás hibákat bocsásson ki vagy tranzakció kontextussal térjen vissza.
Request/response II. [ServiceContract()] publicinterfaceILogisticsService { [OperationContract()] WorkOrderAcknowledgementSubmitWorkOrder(WorkOrderworkOrder); [OperationContract()] voidCancelWorkOrder(int workOderNumber); }
OneWay I. • Ha csak egy üzenetet szeretnék küldeni. • Nem érdekel a válasz. • Beállítása: OperationContractAttributeIsOneWayproperty-jét kell „true”-ra állítani. • Nem használható FaultContract attribútummal együtt. Miért? • Sorbaállított üzenetküldés esetén.
OneWay II. [ServiceContract()] publicinterfaceILogisticsService { [OperationContract(IsOneWay=true)] voidCancelWorkOder(int workOrderNumber); }
Duplex I. • Két helyzetben használatos: • A kliens üzenetet küld a szolgáltatásnak, mert hosszú távú feldolgozást kezdeményezzen és megerősítést kér a szolgáltatástól, hogy a a kért feldolgozás megtörtént. • A kliensnek tudni kell fogadnia kéretlen üzeneteket a szolgáltatástól.
Duplex II. [ServiceContract()] interfaceIGreetingHandler { [OperationContract(IsOneWay=true)] voidGreetingProduced(stringgreeting); } [ServiceContract(CallbackContract = typeof(IGreetingHandler))] interfaceIGreetingService { [OperationContract(IsOneWay = true)] voidRequestGreetng(stringname); }
Duplex III. [ServiceBehavior(InstanceContextMode = InstanceContextMode.PerSession)] classGreetingService : IGreetService { publicvoidRequestGreeting(stringname) { Console.WriteLine(„InService.Greet”); IGreetingHandlercallbackHandler = OperationContext.Current.GerCallbackChannel<IGreetingHandler>(); callbackHandler.GreetingProduced(„Hello ” + name); } }
Adat szerződések I. • Megegyezés a szolgáltatás és a felhasználó között az üzenetváltás során a hasznos adat formájáról és felépítéséről. • Komplex típusok szerializálására. [OperationContract()] ResponseMessageType SomeOp1(RequestMessageTypereqMsg); [OperationContract()] string SomeOp2(string el1, string el2);
Adat szerződések II. • DataContractAttribute használatával deklarálhatók az adat szerződések. • A DataMemberAttribute segítségével lehet bevonni a típusokat a szerződésbe. • Ez opcionális és független a láthatóságtól.
Adat szerződések III. [DataContract(Namespace = „http://schemas.fabrikam.com/customers/”)] publicenumTitleOptions : int { [EnumMember()] Mr = 0, [EnumMember()] Ms = 1, [EnumMember()] Mrs = 2, [EnumMember()] Dr = 3, }
Adat szerződések IV. [DataContract(Namespace = „http://schemas.fabrikam.com/customers/”)] publicclassContactInfo { [DataMember(IsRequired = false)] publicstringPhoneNumber; [DataMember(IsRequired = false)] publicstringEmailAddress; }
DataContractAttribute I. • Enum, struktúra, osztály • Nem származtatott • Összesen két paramétere van.
DataMemberAttribute I. • System.Runtime.Serialization • Azt határozza meg, hogy a tagnak benne kell-e lennie az adatszerkezet szerializációjában.
EnumMemberAttribute • Azt deklarálja, hogy egy megadott enum típus DataContractAttribute-tal deklarálva része legyen az adat szerződésnek. • Egyetlen paramétere a Value, mely a szerializálásnál használható fel. • Az alap érték a valódi érték.
Opt-In vs. Opt-Out I. • DataContractSerializer az új WCF szerializáló. • Opt-In módban működik, ami az elődjének (XMLSerializer) az ellentéte. • DataContractSerializer esetén meg kell jelölni, hogy mely tagok legyenek az adat szerződés részei.
Opt-In vs. Opt-Out II. [Serializable()] publicclassContactInfo { publicstringPhoneNumber; publicstringEmailAddress; [NonSerialized()] publicstringHomeAddress; }
Opt-In vs. Opt-Out III. [DataContract()] publicclassContactInfo { [DataMember()] publicstringPhoneNumber; [DataMember()] publicstringEmailAddress; publicstringHomeAddress; }
Kollekciók I. [ServiceContract()] interfaceITaskManager { [OperationContract()] List<Task> GetTasksByAssignedName (stringname); }
Kollekciók II. [ServiceContract()] InterfaceITaskManager { [OperationContract()] Task[] GetTasksBYAssignedName (stringname); }
Kollekciók III. • Csak akkor automatikus, ha a kollekció egy konkrét kollekció a szerződésben és szerializálható. • Mi történik akkor, ha nem teljesül a feltétel? • Megoldás: CollectionDatacontractAttribute
Kollekciók IV. [CollectonDataContract(Name = „MyCollectionOf{0}”)] publicclassMyCollection<T> : Ienumerable<T> { publicvoid Add(T item) { … } Ienumerator<T> Ienumerable<T>.GetEnumarator() { … } publicIenumeratorGetEnumerator() { … } //… } [ServiceContract()] interfaceITaskManager { [OperationContract()] MyCollection<Task> GetTaskByAssignedName(stringname); }
Kollekciók V. • Miután a kliens oldalon legenerálódott a proxy, a GetTasksByAssigned művelet visszatérési típusa így fog látszódni: [CollectionDataContract()] publicclassMyCollectionOfTask : List<Task> { }
KnownTypeAttribute I. [DataContract()] [KnownType(typeof(LoanApprovalTask))] classTask { //… } [DataContract()] classLoanApprovalTask : Task { //… }
KnownTypeAttribute II. [ServiceContract()] interfaceITaskManager { [OperationContract()] List<Task> GetTasksByAssignedName (stringname); }
Üzenet szerződések • Használat okai: • Hogyan épüljön fel a SOAP test. • Hogyan szerializálódjon. • Szolgáltasson és hozzáférjen a headerökhöz. • Attribútumok: • MessageContractAttribute • MessageHeaderAttribute • MessageBodyMemberAttribute