You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
1995 lines
147 KiB
1995 lines
147 KiB
<?xml version="1.0" encoding="UTF-8"?>
|
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
|
<html xmlns="http://www.w3.org/1999/xhtml" lang="en-US" xml:lang="en-US"><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /><title>Web Services Choreography Description Language: Primer </title><style type="text/css">
|
|
code { font-family: monospace; }
|
|
|
|
div.constraint,
|
|
div.issue,
|
|
div.note,
|
|
div.notice { margin-left: 2em; }
|
|
|
|
ol.enumar { list-style-type: decimal; }
|
|
ol.enumla { list-style-type: lower-alpha; }
|
|
ol.enumlr { list-style-type: lower-roman; }
|
|
ol.enumua { list-style-type: upper-alpha; }
|
|
ol.enumur { list-style-type: upper-roman; }
|
|
|
|
|
|
div.exampleInner pre { margin-left: 1em;
|
|
margin-top: 0em; margin-bottom: 0em}
|
|
div.exampleOuter {border: 4px double gray;
|
|
margin: 0em; padding: 0em}
|
|
div.exampleInner { background-color: #d5dee3;
|
|
border-top-width: 4px;
|
|
border-top-style: double;
|
|
border-top-color: #d3d3d3;
|
|
border-bottom-width: 4px;
|
|
border-bottom-style: double;
|
|
border-bottom-color: #d3d3d3;
|
|
padding: 4px; margin: 0em }
|
|
div.exampleWrapper { margin: 4px }
|
|
div.exampleHeader { font-weight: bold;
|
|
margin: 4px}
|
|
</style><link rel="stylesheet" type="text/css" href="http://www.w3.org/StyleSheets/TR/W3C-WD.css" /></head><body><div class="head"><p><a href="http://www.w3.org/"><img src="http://www.w3.org/Icons/w3c_home" alt="W3C" height="48" width="72" /></a></p>
|
|
<h1><a name="title" id="title"></a>Web Services Choreography Description Language: Primer </h1>
|
|
<h2><a name="w3c-doctype" id="w3c-doctype"></a>W3C Working Draft 19 June 2006</h2><dl><dt>This version:</dt><dd>
|
|
<a href="http://www.w3.org/TR/2006/WD-ws-cdl-10-primer-20060619/">http://www.w3.org/TR/2006/WD-ws-cdl-10-primer-20060619/</a>
|
|
</dd><dt>Latest version:</dt><dd>
|
|
<a href="http://www.w3.org/TR/ws-cdl-10-primer/">http://www.w3.org/TR/ws-cdl-10-primer/</a>
|
|
</dd><dt>Editors:</dt><dd>Steve Ross-Talbot, Pi4 Technologies Ltd.</dd><dd>Tony Fletcher, Choreology</dd></dl><p class="copyright"><a href="http://www.w3.org/Consortium/Legal/ipr-notice#Copyright">Copyright</a> © 2006 <a href="http://www.w3.org/"><acronym title="World Wide Web Consortium">W3C</acronym></a><sup>®</sup> (<a href="http://www.csail.mit.edu/"><acronym title="Massachusetts Institute of Technology">MIT</acronym></a>, <a href="http://www.ercim.org/"><acronym title="European Research Consortium for Informatics and Mathematics">ERCIM</acronym></a>, <a href="http://www.keio.ac.jp/">Keio</a>), All Rights Reserved. W3C <a href="http://www.w3.org/Consortium/Legal/ipr-notice#Legal_Disclaimer">liability</a>, <a href="http://www.w3.org/Consortium/Legal/ipr-notice#W3C_Trademarks">trademark</a> and <a href="http://www.w3.org/Consortium/Legal/copyright-documents">document use</a> rules apply.</p></div><hr /><div>
|
|
<h2><a name="abstract" id="abstract"></a>Abstract</h2><p>Web Services Choreography Description Language: Primer is a non-normative document intended to provide an easy to understand tutorial on the uses and the features of the <a href="http://www.w3.org/TR/ws-cdl-10">Web Services Choreography Description Language specification</a>.</p></div><div>
|
|
<h2><a name="status" id="status"></a>Status of this Document</h2><p><em>This section describes the status of this document at the time of its publication. Other documents may supersede this document. A list of current W3C publications and the latest revision of this technical report can be found in the <a href="http://www.w3.org/TR/">W3C technical reports index</a> at http://www.w3.org/TR/.</em></p><p>This document is a First Public Working Draft and has been produced by the <a href="http://www.w3.org/2002/ws/chor/">Web Services Choreography Working Group</a>, part of the <a href="http://www.w3.org/2002/ws/Activity">Web Services Activity</a> in the W3C <a href="http://www.w3.org/Architecture/">Architecture Domain</a>. </p><p>The document is in its early stage, readers should expect lots of changes and additions. A public editors' copy, demonstrating progress on this document is available from the <a href="http://www.w3.org/2002/ws/chor/">Web Services Choreography Working Group</a> home page.</p><p>
|
|
Please send comments about this document to <a href="mailto:public-ws-chor-comments@w3.org">public-ws-chor-comments@w3.org</a> (with <a href="http://lists.w3.org/Archives/Public/public-ws-chor-comments/">public archive</a>). Discussions on this specification should take place on the <a href="mailto:public-ws-chor@w3.org">public-ws-chor@w3.org</a> (with <a href="http://lists.w3.org/Archives/Public/public-ws-chor/">public archive</a>)</p><p> This document was produced by a group operating under the <a href="http://www.w3.org/TR/2002/NOTE-patent-practice-20020124">24 January 2002 CPP</a> as amended by the <a href="http://www.w3.org/2004/02/05-pp-transition">W3C Patent Policy Transition Procedure</a>. W3C maintains a <a rel="disclosure" href="http://www.w3.org/2002/ws/chor/3/01/17-IPR-statements.html">public list of any patent disclosures</a> made in connection with the deliverables of the group; that page also includes instructions for disclosing a patent. An individual who has actual knowledge of a patent which the individual believes contains <a href="http://www.w3.org/Consortium/Patent-Policy-20040205/#def-essential">Essential Claim(s)</a> must disclose the information in accordance with <a href="http://www.w3.org/Consortium/Patent-Policy-20040205/#sec-Disclosure">section 6 of the W3C Patent Policy</a>. </p><p>Publication as a Working Draft does not imply endorsement by the W3C Membership. This is a draft document and may be updated, replaced or obsoleted by other documents at any time. It is inappropriate to cite this document as other than work in progress.</p></div><div class="toc">
|
|
<h2><a name="contents" id="contents"></a>Table of Contents</h2><p class="toc">1 <a href="#Introduction">Introduction</a><br />
|
|
1.1 <a href="#structprimer">Structure of the primer</a><br />
|
|
2 <a href="#overview">An Overview of WS-CDL</a><br />
|
|
2.1 <a href="#usingcdl">Using WS-CDL</a><br />
|
|
2.2 <a href="#whyusecdl">Why use WS-CDL?</a><br />
|
|
2.3 <a href="#structcdl">The Structure of WS-CDL</a><br />
|
|
3 <a href="#gettingstarted">Getting Started</a><br />
|
|
3.1 <a href="#degenerateexample"> Degenerate Example </a><br />
|
|
3.2 <a href="#interactionorienteddesign">Interaction Oriented Design</a><br />
|
|
3.2.1 <a href="#interactions">Interactions</a><br />
|
|
3.2.2 <a href="#roles">Roles</a><br />
|
|
3.2.3 <a href="#participants">Participants</a><br />
|
|
3.2.4 <a href="#relationships">Relationships </a><br />
|
|
3.2.5 <a href="#informationtypes">Information Types</a><br />
|
|
3.2.6 <a href="#tokens">Tokens and locators</a><br />
|
|
3.2.7 <a href="#channels">Channels</a><br />
|
|
3.2.8 <a href="#choreographies">Choreographies</a><br />
|
|
3.2.9 <a href="#completeexample">Complete Example</a><br />
|
|
4 <a href="#intermediate">Intermediate Topics</a><br />
|
|
4.1 <a href="#intermediateexample"> The Intermediate Example </a><br />
|
|
4.1.1 <a href="#variables">Variables</a><br />
|
|
4.1.2 <a href="#workunits">Non Blocking Workunits</a><br />
|
|
4.1.2.1 <a href="#repeatingworkunits">Repetition</a><br />
|
|
4.1.3 <a href="#time">Time</a><br />
|
|
4.1.4 <a href="#records"> Recording information </a><br />
|
|
4.1.5 <a href="#conditional"> Conditional Workunits</a><br />
|
|
4.1.6 <a href="#choices"> Choices </a><br />
|
|
4.1.7 <a href="#parallel"> Parallelization </a><br />
|
|
4.1.8 <a href="#modularization">Modularization</a><br />
|
|
4.1.8.1 <a href="#choreographiesandsubchoreographies">Choreographies and sub-choreographies</a><br />
|
|
4.1.9 <a href="#performing"> Performing a sub choreography </a><br />
|
|
4.1.10 <a href="#channelpassing"> Channel Passing </a><br />
|
|
4.1.11 <a href="#exchanges"> Exchanges </a><br />
|
|
4.2 <a href="#intermediate-extra">Extending the example</a><br />
|
|
4.2.1 <a href="#exceptionsandfaults">Exceptions and Faults</a><br />
|
|
4.2.2 <a href="#Finalization">Finalization</a><br />
|
|
4.2.2.1 <a href="#finalizers"> Finalizers and Finalization </a><br />
|
|
4.2.3 <a href="#silentactionsandconditions">Silent Actions and Conditions</a><br />
|
|
4.2.4 <a href="#noactions">NoActions</a><br />
|
|
4.2.5 <a href="#completeexample2">Complete Example</a><br />
|
|
5 <a href="#advanced">Advanced Topics</a><br />
|
|
5.1 <a href="#dependentworkunits">Dependent Workunits</a><br />
|
|
5.2 <a href="#concurrentperforms">Concurrent Performs</a><br />
|
|
5.2.1 <a href="#managingjoinconditions">Managing join conditions</a><br />
|
|
5.3 <a href="#isolationlevels"> Isolation Levels </a><br />
|
|
5.4 <a href="#advancedchannels">Advanced Channels</a><br />
|
|
5.4.1 <a href="#usage">Usage</a><br />
|
|
5.4.2 <a href="#channelpassingmodes">Channel Passing Modes</a><br />
|
|
5.5 <a href="#id2272704">Pitfalls</a><br />
|
|
5.5.1 <a href="#distributedchoice">Distributed choice and race conditions</a><br />
|
|
5.6 <a href="#alignmentandcoordination"> Alignment and Coordination </a><br />
|
|
6 <a href="#implementation">Implementation Considerations</a><br />
|
|
6.1 <a href="#endpointprojections">End Point Projections</a><br />
|
|
6.1.1 <a href="#Java">Java</a><br />
|
|
6.1.2 <a href="#WS-BPEL"> WS-BPEL </a><br />
|
|
6.1.3 <a href="#monitoring"> Runtime Monitoring </a><br />
|
|
6.1.4 <a href="#wsdl1.1"> WSDL1.1 </a><br />
|
|
6.1.5 <a href="#WSDL2.0"> WSDL2.0 </a><br />
|
|
6.2 <a href="#wdaddressing"> WS-Addressing </a><br />
|
|
6.2.1 <a href="#channelrep"> Channel Representation </a><br />
|
|
</p></div><hr /><div class="body"><div class="div1">
|
|
<h2><a name="Introduction" id="Introduction"></a>1 Introduction</h2><div class="div2">
|
|
<h3><a name="structprimer" id="structprimer"></a>1.1 Structure of the primer</h3><p>This primer is intended to give an overview of WS-CDL and can be read by WS-CDL
|
|
users (e.g. a software professional wishing to write choreography descriptions)
|
|
and WS-CDL implementers (e.g software professionals wishing to create WS-CDL compliant
|
|
tools) alike. The first 5 sections are intended for both audiences while the
|
|
last is intended primarily for implementors.</p><p>Section 2 provides an overview of WS-CDL. The first half of Section 3 describes
|
|
a degenerate example using UML sequence diagrams. The second half of Section 3 walks
|
|
through building the WS-CDL description of the example. Section 4 examines
|
|
WS-CDL at a deeper level, extending the previous example and describing how more
|
|
advanced features can be employed. Section 5 describes the use of WS-CDL
|
|
within an organization. Section 6 describes some of the implementation
|
|
considerations for implementers.</p></div></div><div class="div1">
|
|
<h2><a name="overview" id="overview"></a>2 An Overview of WS-CDL</h2><p>WS-CDL is a
|
|
language for specifying peer-to-peer protocols where each party wishes to remain
|
|
autonomous and in which no party is master over any other – i.e. no centralization
|
|
point. The description of a peer-to-peer protocol is grounded in what we term an
|
|
ordered set of <code>interactions</code>, where an <code>interaction</code> is defined
|
|
loosely as an <code>exchange</code> of messages between parties.</p><p>It is essential in understanding Web Services Choreography Description Language
|
|
(WS-CDL) to realize that there is no single point of control. There are no global
|
|
variables, conditions or workunits. To have them would require centralised storage and
|
|
orchestration.
|
|
WS-CDL does permit a shorthand notation to enable variables and conditions to
|
|
exist in multiple places, but this is syntactic sugar to avoid repetitive
|
|
definitions. There is also an ability for variables residing in one service to be
|
|
aligned (synchronized) with the variables residing in another service, giving the
|
|
illusion of global or shared state.</p><p>It is also important to understand that WS-CDL does not distinguish between
|
|
observable messages from applications, that might be considered as application or
|
|
business messages, from the infrastructure upon which an application is based,
|
|
that might be considered as some form of signal. In WS-CDL all messages are
|
|
described as information types and have no special significance over each other. All
|
|
that WS-CDL describes is the ordering rules for the messages which dictate the order
|
|
in which they should be observed. When these ordering rules are broken WS-CDL
|
|
considers them to be out-of-sequence messages and this can be viewed as an error in
|
|
conformance of the services that gave rise to them against the WS-CDL description.</p><p>WS-CDL is an XML-based language that can be used to describe the common and
|
|
collaborative observable behavior of multiple services that need to interact in
|
|
order to achieve some goal. WS-CDL describes this behavior from a global or neutral
|
|
perspective rather than from the perspective of any one party and we call a complete
|
|
WS-CDL description a global model.</p><p>Services are any form of computational process with which one may interact, examples
|
|
are a buying process and a selling process that are implemented as computational
|
|
services in a Service Oriented Architecture (SOA) or indeed as a Web Services
|
|
implementation of an SOA. Because
|
|
WS-CDL is not explicitly bound to WSDL it can play the same global model role for
|
|
both SOA services and Web Services, that is it is possible to use WS-CDL to describe
|
|
a global model for services with no WSDL descriptions (perhaps they just have Java interfaces)
|
|
as easily as it is to describe services that do have or will have WSDL descriptions. The
|
|
way in which WS-CDL can be used without WSDL descriptions is however implementation dependent.</p><p>Common collaborative observable behavior is the phrase we use to describe
|
|
the behavior of a system of services, for example buyer and seller services, from a
|
|
global perspective. Each service has an observable behavior that can be described
|
|
today using WSDL or some other interface description language (e.g. Java). Such
|
|
observable behavior is described as a set of functions, possibly with parameters,
|
|
that a service offers coupled with error messages or codes that indicate failure
|
|
along with the return types for the functions offered. If we used abstract BPEL
|
|
along with WSDL we can also describe the valid sequences of functions from a single
|
|
services perspective (i.e. the service we are describing), which is not
|
|
possible with WSDL or Java alone [NOTE: NEEDS TO BE QUALIFIED WITH WHICH BPEL AND PROFILE].
|
|
We refer to this set as the “observable behavior” for
|
|
a service. This level, the service level, of “observable behavior” does not describe
|
|
behavior of a system of services because it only deals with a single service. The
|
|
composition of a set of "observable behaviors" at a service level is what we call
|
|
the common collaborative observable behavior. The composition is not simply the set of
|
|
observable behaviors at the service level operating together because such a composition
|
|
requires further description of the dependencies that the set of services exhibit in order
|
|
to interoperate correctly. If we captured the ordering rules for a set of service
|
|
then we would have the common collaborative observable behavior fully specified. This is
|
|
what WS-CDL is for.</p><p>Individual service behaviors can be used in the composition of wider collaboration in
|
|
which a set of services with their own behaviors could be effectively used. In order
|
|
to do so a global model that described the peer to peer
|
|
observable interactions of such a set of services is required to ensure that the
|
|
services will in-fact cooperate to a commonly understood script. That script is the
|
|
global model and that script is what WS-CDL is used to describe.</p><p>A global model, ensures that the common collaborative observable behavior is not
|
|
biased towards the view of any one of the services. Instead it describes as peers
|
|
the entire collaborative observable behavior of all of the services such that no one
|
|
service can be said to exert any control over any other service. In effect it
|
|
described the services as a complete distributed application in which each service
|
|
plays a distinct role and has distinct relationships with its peer services.</p><p>One may think of WS-CDL as a language for describing the observable activities of a
|
|
set of services some of which are synchronized through some common understanding
|
|
realized by a specific business interaction between the services or by a declaration
|
|
of interest in the progress of one service by another (e.g. has the buyer accepted
|
|
the price offered by the seller). The least interesting scenario is one in which
|
|
WS-CDL can be used to describe a set of services that never synchronize at all; that
|
|
is there is no observable relationships and no statement of an unobservable
|
|
relationship that exists between the services. In this case the services perform a
|
|
choreography, but effectively on different stages and thus need no form of
|
|
coordination (e.g. a buyer and seller choreography for WallMart versus a Bloomberg
|
|
Reuters choreography for the exchange of news items). In all other cases the
|
|
synchronization is what makes life interesting (e.g. a buyer seller choreography
|
|
coupled with a seller credit check choreography or indeed a seller shipper
|
|
choreography). </p><p>In WS-CDL the mechanisms for describing the common observable behavior range from
|
|
specific information alignment (e.g. when a buyer and seller record the fact that an
|
|
order has been accepted in variables that reside at the buyer and at the seller),
|
|
interaction (e.g. when a buyer requests a price from a seller and receives a price
|
|
as a response from the seller) and a declaration of interest in the progress of a
|
|
choreography (e.g. has the bartering choreography between buyer and seller “started”
|
|
or has it “finished”). In the first two cases synchronization is explicit and
|
|
visible as a business related activity (e.g. the observable recording of information
|
|
and it’s alignment and the description of an information exchange between a buyer
|
|
and seller) and in the last case (e.g. choreography has “started” or “finished”) it
|
|
is implicit based on the progress of a choreography and not any business
|
|
relationships.</p><div class="div2">
|
|
<h3><a name="usingcdl" id="usingcdl"></a>2.1 Using WS-CDL</h3><p>WS-CDL is a description and not an executable language, hence the term
|
|
“Description” in it’s name. It is a language that can be used to unambiguously
|
|
describe observable service collaborations, we might also refer to this as
|
|
a business protocol. </p><p>When WS-CDL is focused on describing collaboration within a domain of control
|
|
(e.g. a single company or enterprise) WS-CDL is used to describe the internal
|
|
workflows that involves multiple services (also called end-points) that
|
|
constitute observable collaborative behavior. The value in so doing is to
|
|
encourage conformance of services to a negotiated choreography description and
|
|
to improve interoperability of services through an agreed choreography
|
|
description. This is no more than describing a business protocol that defines an
|
|
observable collaboration between services. You can think of it as a way of
|
|
ensuring services are well behaved with respect to the goals you wish to achieve
|
|
within your domain.</p><p>When the focus of WS-CDL is across domains of control, WS-CDL is used to describe
|
|
the ordering of observable message exchanges across domains such as the those
|
|
that govern vertical protocols such as fpML, FIX, TWIST and SWIFT. These
|
|
protocols have some form of XML data format definition and then proceed to
|
|
describe the ordering of message exchanges using a combination of prose and UML
|
|
sequence diagrams.</p></div><div class="div2">
|
|
<h3><a name="whyusecdl" id="whyusecdl"></a>2.2 Why use WS-CDL?</h3><p>WS-CDL can be used to ensure interoperability within and across domains of
|
|
control to lower interoperability issues, and create solutions
|
|
within and across domains of control. </p><p>WS-CDL can be used to ensure that the total cost of software systems in a
|
|
distributed environment, within a domain of control and across the
|
|
world-wide-web is lowered by guaranteeing that the services that participate in
|
|
a choreography are well behaved on a continuous basis.</p><p>Both of these benefits translate into greater up-time and so increase top line
|
|
profits. At the same time they translate into less testing time and so reduce
|
|
cost of delivery which decreases bottom line costs.</p></div><div class="div2">
|
|
<h3><a name="structcdl" id="structcdl"></a>2.3 The Structure of WS-CDL</h3><p> WS-CDL is a layered language that provides different levels of expressibility to
|
|
describe a choreography. Not all of the features of WS-CDL are needed to describe a
|
|
choreography. The array of features are included in the language to provide a complete
|
|
and accurate reflection of what is needed to model a particular choreography and depending
|
|
on what is needed some features of the language will be needed whereas others will not.
|
|
In this document we shall lead by example and show what the features can be used for and
|
|
also provide some guidance as to when to use certain features and when not.
|
|
The high level features of WS-CDL are shown diagrammatically in Figure 1.</p><p> At the top most level for any WS-CDL there is a package that contains all other
|
|
things. All choreographies described in WS-CDL will include a number of types that need
|
|
to be defined. Among these types we have <code>informationTypes</code> that describe
|
|
general messages in interaction and variables,
|
|
<code>roleTypes</code> that define behavior (i.e. a WSDL description),
|
|
<code>participantTypes</code> that group <code>roleTypes</code>into a physical
|
|
representation of a service (e.g. multiple WSDL descriptions at a single location,
|
|
<code>relationshipTypes</code> that describe how roles are connected - they define
|
|
the static linkage between roles, <code>channelTypes</code> that describe communication
|
|
links and their constraints between <code>roleTypes</code> -
|
|
instances of <code>channelType</code> are used to interact between <code>roleTypes</code>,
|
|
<code>tokens</code> which are aliases to <code>informationTypes</code> and <code>tokenLocators</code>
|
|
that describe how attributes may be derived from their carrying <code>informationType</code>.
|
|
Once the types are defined then <code>choreographies</code> can be defined using them. A
|
|
<code>choreography</code> has attributes such as a <code>name</code> and a <code>root</code>
|
|
the latter being the entry point for a choreography as well as comprising a structured set of
|
|
activities which can include any combination of
|
|
<code>sequences, parallelisation, choices, workunits, interactions, assignments</code>
|
|
to variables,
|
|
<code>silentActions, noAction</code> and the <code>performing</code> of a sub-choreography. A
|
|
<code>choreography</code>
|
|
may also include an <code>exceptionBlock</code> that indicated what to do when an exception is
|
|
raised and a <code>finalizerBlock</code>. All of these parts of a choreography will be further
|
|
explained
|
|
and illustrated by means of example.</p><img src="pictures/Figure1.png" alt="Layered structure of WS-CDL" /><p> When we model a choreography we may use <code>silentActions</code> to hide certain
|
|
values or conditions that give rise to one path being taken over another. We call this
|
|
notion non-observable conditionals and it makes it possible to model branching based
|
|
on observing changes in the interactions that occur (e.g. one might observe an
|
|
exchange between a buyer and a seller which is said to be terminated when a
|
|
“completed” interaction is observed) instead of having to make the condition itself
|
|
visible.</p><p>If we have no observable conditionals then it is not necessary to perform any
|
|
explicit state management at the roles that are interacting because we have not
|
|
needed to express any explicit computation (e.g. totalOrderValue EQUALS
|
|
expectedOrderValue) required of an observable condition. None of roles used in
|
|
choreographies of this type have the need for any state variables to control a
|
|
choreography, rather the progression of a choreography is expressed purely in
|
|
terms of observable interactions and use observation to determine their state
|
|
with respect to the other roles. </p><p>Some business protocols are defined exposing specific business rules. These
|
|
constitute shared knowledge between the concerned roles. For example we may
|
|
terminate an order completion between a buyer and a seller when we calculate
|
|
that the items delivered match the original order. The business rule in this
|
|
example is the shared constraint that buyer_quantity equals completion_quantity.
|
|
At some level the roles must have some shared knowledge of both variables and
|
|
their values. When business rules of this nature become part of the business
|
|
protocol such Observable Conditionals can be added into a choreography and which
|
|
implies state management is needed.</p><p>WS-CDL provides some basic interfaces for state management defining it’s
|
|
requirements as a coordination protocol. The specifics of state management is
|
|
left as an implementation detail for the community.</p></div></div><div class="div1">
|
|
<h2><a name="gettingstarted" id="gettingstarted"></a>3 Getting Started</h2><p>In order to understand WS-CDL is best to illustrate it through the use of an example.
|
|
In this section we shall introduce a simple example and build upon it throughout the
|
|
rest of document to illustrate different parts of WS-CDL. The Appendices have the
|
|
full listing of the various WS-CDL encodings of the example as well as a url to the
|
|
WS-CDL descriptions. In all cases the WS-CDL descriptions have been tested against
|
|
at least one implementation of WS-CDL having been constructed in a validating
|
|
editor.</p><div class="div2">
|
|
<h3><a name="degenerateexample" id="degenerateexample"></a>3.1 Degenerate Example </h3><p> The degenerate example involves just the buyer and the seller from the previous
|
|
example. The buyer simply requests a price from the seller and the seller
|
|
responds with a price or a fault if the goods are not known or not available.
|
|
This is illustrated in the sequence diagram in Figure 6 below. </p><img src="pictures/Figure2.png" alt="Sequence Diagram For the Degenerate Usecase" /></div><div class="div2">
|
|
<h3><a name="interactionorienteddesign" id="interactionorienteddesign"></a>3.2 Interaction Oriented Design</h3><p> In this section we introduce the fundamental concept of an interaction, which
|
|
underpins WS-CDL. We shall use our degenerate example that we have described
|
|
above and go through the necessary steps to define it as a choreography
|
|
description in WS_CDL. We shall define the roles, tokens, channels,
|
|
relationships, participants and variables necessary to properly describe it. </p><div class="div3">
|
|
<h4><a name="interactions" id="interactions"></a>3.2.1 Interactions</h4><p> An interaction is the realization of a collaboration between roles. Roles are grouped
|
|
into participants. Roles are analogous to the entities at the top of our UML sequence
|
|
diagrams and participants group these roles into domains of control which can be said to
|
|
be the location the behaviors defined by the roles.</p><p> With respect to our degenerate usecase a collaboration is a message exchange
|
|
between the swim lanes in the sequence diagram in Figure 6. In the example
|
|
when the buyer requests a quote a message is sent from the buyer to the
|
|
seller with the details of the product included in the quote. The
|
|
seller can either respond with a quote back to the buyer or can respond with
|
|
a fault which indicates that the product is invalid. The WS-CDL fragment for
|
|
this interaction is illustrated below: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment1" id="wscdlfragment1"></a>Example: WS-CDL fragment</div><div class="exampleInner"><pre>
|
|
<interaction name="QuoteElicitation" operation="getQuote" channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">
|
|
Quote Elicitation
|
|
</description>
|
|
<participate relationshipType="tns:Buyer2Seller" fromRoleTypeRef="tns:BuyerRole" toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="QuoteRequest" informationType="tns:QuoteRequestType" action="request">
|
|
<description type="documentation">
|
|
Quote Request Message Exchange
|
|
</description>
|
|
<send variable="cdl:getVariable('quoteRequest','','')"/>
|
|
<receive variable="cdl:getVariable('quoteRequest','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponse" informationType="tns:QuoteResponseType" action="respond">
|
|
<description type="documentation">
|
|
Quote Response Message Exchange
|
|
</description>
|
|
<send variable="cdl:getVariable('quoteResponse','','')"/>
|
|
<receive variable="cdl:getVariable('quoteResponse','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponseFault" informationType="tns:QuoteResponseFaultType" action="respond" faultName="InvalidProductFault">
|
|
<description type="documentation">
|
|
Quote Response Fault Exchange
|
|
</description>
|
|
<send variable="cdl:getVariable('faultResponse','','')"/>
|
|
<receive variable="cdl:getVariable('faultResponse','','')"/>
|
|
</exchange>
|
|
</interaction>
|
|
</pre></div></div><p> Interactions are descriptions of one or more exchanges between a sender and
|
|
a receiver. Interactions are labeled with an operation name that can be
|
|
mapped to a WSDL operation, a topic in a publish-and-subscribe environment
|
|
or a message queue in a point-to-point messaging environment. Interactions
|
|
take place over a channel, as indicated by a channelVariable, the variable
|
|
itself will have been declared to be of a particular channelType. The
|
|
participating relationship further restricts the interaction to the roles
|
|
that are valid for that relationship. </p><p> Each exchange names the type of the thing to be exchanged and the
|
|
direction of the exchange (e.g. a request, a response, or a fault). </p><p> In our degenerate example we have one interaction called <code>"Buyer
|
|
requests a quote from the seller"</code> which occurs over a channel
|
|
variables called <code>"Buyer2SellerC"</code> with an operation name
|
|
<code>"quoteRequest"</code>. The interaction has three exchanges, one
|
|
for the request called <code>"Request Quote"</code>, one for the valid
|
|
response called <code>"Quote Response"</code> and one for the fault called
|
|
<code>"Invalid Product"</code>. </p><p> In order to describe this more fully we have to define the channelType
|
|
for the <code>channelVariable</code> called <code>"Buyer2SellerC"</code>, in
|
|
the <code>interaction</code>, and then define the information types
|
|
<code>"tns:QuoteRequestType"</code>,
|
|
<code>"tns:QuoteResponseType"</code> and
|
|
<code>"tns:QuoteResponseFaultType"</code> for the variables <code>-</code>, <code>-</code>
|
|
and <code>-</code> respectively. We also need to define the relationships, roles
|
|
and participants that are needed to support this interaction, such as
|
|
<code>"tns:Buyer2Seller"</code>, <code>"tns:BuyerRole"</code> and
|
|
<code>"tns:SellerRole"</code>. </p><p> Thus we shall do it in the following order: </p><ol><li>Define our roleTypes, </li><li>Define our relationshipTypes, </li><li>Define our informationTypes, </li><li>Define our tokenType,</li><li>Define our channelTypes</li></ol></div><div class="div3">
|
|
<h4><a name="roles" id="roles"></a>3.2.2 Roles</h4><p> There are 2 roles that are played out in the example. These are the “buyer”
|
|
and the “seller”, they represent the same entities described in the sequence
|
|
diagram in Figure 6. We define them as <code>BuyerRole</code> and
|
|
<code>SellerRole</code> as follows: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment2" id="wscdlfragment2"></a>Example: WS-CDL fragment</div><div class="exampleInner"><pre>
|
|
<roleType name="BuyerRole">
|
|
<description type="documentation">
|
|
Role for Buyer
|
|
</description>
|
|
<behavior name="BuyerBehavior" interface="BuyerBehaviorInterface">
|
|
<description type="documentation">
|
|
Behavior for Buyer Role
|
|
</description>
|
|
</behavior>
|
|
</roleType>
|
|
<roleType name="SellerRole">
|
|
<description type="documentation">
|
|
Role for Seller
|
|
</description>
|
|
<behavior name="SellerBehavior" interface="SellerBehaviorInterface">
|
|
<description type="documentation">
|
|
Behavior for Seller
|
|
</description>
|
|
</behavior>
|
|
</roleType>
|
|
</pre></div></div><p> In WS-CDL each role defined has a <code>behavior</code>. A
|
|
<code>behavior</code> in this sense is the binding point for a WSDL
|
|
description (either WSDL1.1 or WSDL2.0). The binding point is the
|
|
<code>interface</code> which normally references a WSDL description but
|
|
this is optional in WS-CDL. Because it is optional we can use this as a
|
|
binding point to different service descriptions. In our example the
|
|
respective <code>interfaces</code> for the roles <code>BuyerRole</code> and
|
|
<code>SellerRole</code> are <code>BuyerBehaviorInterface</code> and
|
|
<code>SellerBehaviorInterface</code> which do not refer to any WSDL
|
|
description and so can be used by implementors to derive WSDL descriptions.
|
|
For example one might well derive the WSDL descriptions and generate
|
|
BuyerBehaviorInterface.wsdl and SellerBehaviorInterface.wsdl. </p><p> We shall look at how we would bind to an existing WSDL description in the
|
|
Intermediate section. </p><p> The abstract syntax for roles is illustrated below: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlsyntax1" id="wscdlsyntax1"></a>Example: WS-CDL roleType definition</div><div class="exampleInner"><pre>
|
|
roleType ::=
|
|
<roleType name="ncname">
|
|
<description type=" documentation" </description>?
|
|
<behavior name="ncname" interface="qname"? />+
|
|
</roleType>
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="participants" id="participants"></a>3.2.3 Participants</h4><p> In WS-CDL a "Participant" is a set of distinct roles that are implemented as
|
|
a service. That is the behaviors that relate to the roles are all
|
|
implemented by the same service. In a sense a "Participant" is akin to a Web
|
|
Service in which the WSDL that describes that service fulfills the
|
|
functional description needed to implement the collection of behaviors that
|
|
the roles require to meet their obligations and in which the Web Service is
|
|
implemented by the same logical entity albeit a organisation or line of
|
|
business within an organisation. </p><p> "Participants" turn out to be very important in a WS-CDL description, which is
|
|
why they are mandatory, because they represent the grounding of behaviors
|
|
into a process - the Web Service that implements them. This is important
|
|
because it governs our need to ground where things happen for the purpose of
|
|
behavioral type checking and in understanding who may share what
|
|
information. Normally roles do not share information, rather information is
|
|
explicitly exchanged to gain a common understanding in a landscape of peer
|
|
services. In the case of a "Participant" the information within a
|
|
"Participant" may be shared in the same sense of information existing in
|
|
some shared memory between different threads in a process. From a WS-CDL perspective
|
|
this sharing is based on the roles within the participant. Thus the roles may
|
|
share information within the boundary of the participant.</p><p> From a WS-CDL modeling perspective we might simply consider a "Participant"
|
|
to be a collection of roles that are represented physically as a single
|
|
service. In our example the roles would be members of their own
|
|
<code>participant</code> so there would be a one-to-one mapping. Thus
|
|
the roles <code>BuyerRole</code> and <code>SellerRole</code> would be in the
|
|
participants <code>Buyer</code> and <code>Seller</code> respectively. </p><p> In WS-CDL the participants for our example would be written as follows: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment2_1" id="wscdlfragment2_1"></a>Example: WS-CDL fragment</div><div class="exampleInner"><pre>
|
|
<participantType name="Seller">
|
|
<description type="documentation">
|
|
Seller Participant
|
|
</description>
|
|
<roleType typeRef="tns:SellerRole"/>
|
|
</participantType>
|
|
<participantType name="Buyer">
|
|
<description type="documentation">
|
|
Buyer Participant
|
|
</description>
|
|
<roleType typeRef="tns:BuyerRole"/>
|
|
</participantType>
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="relationships" id="relationships"></a>3.2.4 Relationships </h4><p> Once we have some roles defined we can define the relationships. In WS-CDL a
|
|
relationship declares an intention to interact between two roles. In a
|
|
sequence diagram this is akin to any two of the actors in a sequence diagram
|
|
that have connecting arrows in any direction. In our example we have
|
|
relationships between the <code>BuyerRole</code> and the
|
|
<code>SellerRole</code> and we would define it as the <code>relationship</code>
|
|
<code>Buyer2Seller</code> as follows: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment3" id="wscdlfragment3"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>
|
|
<relationshipType name="Buyer2Seller">
|
|
<description type="documentation">
|
|
Buyer Seller Relationship
|
|
</description>
|
|
<roleType typeRef="tns:BuyerRole"/>
|
|
<roleType typeRef="tns:SellerRole"/>
|
|
</relationshipType>
|
|
</pre></div></div><p> A relationship comprises a name and two role types. We use the convention in
|
|
this document that the first role type defines the “from” role and the
|
|
second the “to” role and connect them with the number 2, thus all of our
|
|
relationships are of the form <code>from2to</code>. WS-CDL does not distinguish
|
|
between the "to" and "from" roles in a relationship. We simple use this convention
|
|
as a convenience. It does not imply any directionality with respect to the
|
|
<code>relationship</code> and is only a naming convention for the primer.</p><p> The abstract syntax for relationships is defined as follows: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlsyntax2" id="wscdlsyntax2"></a>Example: WS-CDL relationshipType definition</div><div class="exampleInner"><pre>
|
|
relationshipType ::=
|
|
<relationshipType name="ncname">
|
|
<role type="qname" behavior="list of ncname"? />
|
|
<role type="qname" behavior="list of ncname"? />
|
|
</relationshipType>
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="informationtypes" id="informationtypes"></a>3.2.5 Information Types</h4><p> The informationTypes in a choreography are used to describe the types for
|
|
many of the variables that we might use in a choreography. They are used to
|
|
describe the types of messages that we might send between roles in an
|
|
interaction. In our example we have information types we need to declare for
|
|
the "request", "response" and "faultResponse". We shall call these
|
|
<code>QuoteRequestType</code>, <code>QuoteResponseType</code> and
|
|
<code>QuoteResponseFaultType</code> respectively. </p><p> We shall need a few other information types for our tokens, token locators
|
|
and channel types. We shall explain why they are needed in the section that
|
|
deals with tokens locators and channel types. For the purpose of
|
|
completeness we shall define them here and they are called
|
|
<code>IdentityType</code> and <code>URI</code>. </p><p> In WS-CDL the full description is as follows: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment4" id="wscdlfragment4"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>
|
|
<informationType name="QuoteRequestType" type="primer:QuoteRequestMsg">
|
|
<description type="documentation">
|
|
Quote Request Message
|
|
</description>
|
|
</informationType>
|
|
<informationType name="QuoteResponseType" type="primer:QuoteResponseMsg">
|
|
<description type="documentation">
|
|
Quote Response Message
|
|
</description>
|
|
</informationType>
|
|
<informationType name="QuoteResponseFaultType" type="primer:QuoteResponseFaultMsg">
|
|
<description type="documentation">
|
|
Quote Response Fault Message
|
|
</description>
|
|
</informationType>
|
|
<informationType name="IdentityType" type="xsd:string">
|
|
<description type="documentation">
|
|
Identity Attribute
|
|
</description>
|
|
</informationType>
|
|
<informationType name="URI" type="xsd:uri">
|
|
<description type="documentation">
|
|
Reference Token For Channels
|
|
</description>
|
|
</informationType>
|
|
</pre></div></div><p> The abstract syntax for defining information types is as follows: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlsyntax3" id="wscdlsyntax3"></a>Example: WS-CDL informationType definition</div><div class="exampleInner"><pre>
|
|
informationType ::=
|
|
<informationType name="ncname"
|
|
type="qname"?|element="qname"?
|
|
exceptionType="true"|"false"? />
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="tokens" id="tokens"></a>3.2.6 Tokens and locators</h4><p> A token provides a mechanism for defining an alias for an information type.
|
|
Token locators can then be defined to locate a particular token from
|
|
within a message type. We define some tokens and token locators here because
|
|
they are needed when defining channel types.</p><p> The key uses of tokens and locators are as follows:</p><ul><li><p>Tokens and their locators are used to define the identity attributes
|
|
that ensure channel communication can be correlated. A token provides a
|
|
mechanism for defining
|
|
an alias for an information type. Token locators can then be defined to
|
|
locate this particular token from within a message type. Tokens and
|
|
token locators are shown here to define channel types</p></li><li><p>The tokens we define will also be used to refer to a service reference, that
|
|
is a url, for a web service. In this context a token defines an alias to
|
|
the web service so that we can refer to it by a shorter name. In our
|
|
degenerate example we do not reference any web service url but for the sake
|
|
of completeness we define a URL token here. From an implementation perspective
|
|
as opposed to a pure usage perspective the channel type reference is needed to
|
|
understand what data type will be used to transfer an endpoint reference between
|
|
services when channel passing is enacted. We shall visit channel passing later on
|
|
in the intermediate section.</p>
|
|
<p> The two <code>informationTypes</code> included earlier are used as references in the token
|
|
and token locator definitions.</p></li><li><p>Tokens and their locators are a mechanism to make the
|
|
choreography description more readable and more maintainable through the indirection
|
|
that they afford. Thus tokens and locators can be used as a simple alias mechanism to refer to
|
|
informationTypes that have been previously defined and to refer to information
|
|
within instances of informationTypes such as the purchase order number or the
|
|
amount or value of an order and even the time to live of a quote which itself
|
|
may timeout at some point.</p></li></ul><p> We define the tokens <code>id</code>, which represents the information type
|
|
<code>IdentityType</code>, and <code>URI</code>, which represents the
|
|
information type <code>URI</code>.
|
|
|
|
We define locators for <code>QuoteRequestType</code>,
|
|
<code>QuoteResponseType</code> and <code>QuoteResponseFaultType</code> that will
|
|
cause the identity information, associated with token <code>id</code>, for
|
|
the <code>informationTypes</code> to be obtained
|
|
from the contents of these messages when exchanged on the channel.
|
|
The full description of the tokens
|
|
and the locators is given below: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment5" id="wscdlfragment5"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>
|
|
<token name="id" informationType="tns:IdentityType">
|
|
<description type="documentation">
|
|
Identity token
|
|
</description>
|
|
</token>
|
|
<token name="URI" informationType="tns:URI">
|
|
<description type="documentation">
|
|
Reference Token for Channels
|
|
</description>
|
|
</token>
|
|
|
|
<tokenLocator tokenName="tns:id" informationType="tns:QuoteRequestType" query="/quote/@id">
|
|
<description type="documentation">
|
|
Identity for Quote Request
|
|
</description>
|
|
</tokenLocator>
|
|
<tokenLocator tokenName="tns:id" informationType="tns:QuoteResponseType" query="/quote/@key">
|
|
<description type="documentation">
|
|
Identity for Quote Response
|
|
</description>
|
|
</tokenLocator>
|
|
<tokenLocator tokenName="tns:id" informationType="tns:QuoteResponseFaultType" query="/quote/@key">
|
|
<description type="documentation">
|
|
Identity for Quote Response Fault
|
|
</description>
|
|
</tokenLocator>
|
|
</pre></div></div><p>The abstract syntax for defining a tokens and token locators are as follows:</p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlsyntax4" id="wscdlsyntax4"></a>Example: WS-CDL token definition</div><div class="exampleInner"><pre>
|
|
<token name="ncname"
|
|
informationType="qname" />
|
|
|
|
<tokenLocator tokenName="QName"
|
|
informationType="QName"
|
|
part="NCName"?
|
|
query="XPath-expression" />
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="channels" id="channels"></a>3.2.7 Channels</h4><p> Finally, having defined our roles, information types, tokens and locators we
|
|
are in a position to define our channel. Channels are the principle
|
|
mechanism used to realize an interaction. </p><p> In our <code>interaction</code> we have a channel variables called <code>Buyer2SellerC</code>
|
|
that has a type. A channel is named, described, and then related to the roles
|
|
that realize its behavioral interface. A reference is provided to a
|
|
service. The channel type will have the capability to derive its
|
|
identity when in use.</p><p> The channel type we shall define is called <code>Buyer2SellerChannel</code>
|
|
and it is defined as follows: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment6" id="wscdlfragment6"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>
|
|
<channelType name="Buyer2SellerChannel">
|
|
<description type="documentation">
|
|
Buyer to Seller Channel Type
|
|
</description>
|
|
<roleType typeRef="tns:SellerRole"/>
|
|
<reference>
|
|
<token name="tns:URI"/>
|
|
</reference>
|
|
<identity type="primary">
|
|
<token name="tns:id"/>
|
|
</identity>
|
|
</channelType>
|
|
</pre></div></div><p> Our channel type, named <code>Buyer2SellerChannel</code> connects us from
|
|
the <code>BuyerRole</code> to the <code>SellerRole</code>. The latter
|
|
implements the service at the end of the channel. The <code>reference</code>
|
|
simply refers to a service, in this case it does nothing for us because we
|
|
have no specific service to refer to. The <code>identity</code> is marked as
|
|
<code>primary</code> which means that the token <code>id</code> is
|
|
interpreted as a primary key for correlation. The token locators we defined
|
|
earlier are used together with the information type being sent or received
|
|
on a channel to determine the actual key which can be a composite key if
|
|
needed. In our example the identity is a single attribute. </p><p> The abstract syntax of a channel definition is provided below. We shall look
|
|
at the other part of a channel type definition in later sections: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlsyntax5" id="wscdlsyntax5"></a>Example: WS-CDL Channel definition</div><div class="exampleInner"><pre>
|
|
channelType::=
|
|
<channelType name="ncname"
|
|
usage="once"|"unlimited"?
|
|
action="request-respond"|"request"|"respond"? >
|
|
|
|
<passing channel="qname"
|
|
action="request-respond"|"request"|"respond"?
|
|
new="true"|"false"? />*
|
|
<role type="qname" behavior="ncname"? />
|
|
|
|
<reference>
|
|
<token name="qname"/>
|
|
</reference>
|
|
|
|
<identity>
|
|
<token name="qname"/>+
|
|
</identity>?
|
|
|
|
</channelType>
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="choreographies" id="choreographies"></a>3.2.8 Choreographies</h4><p> We can now consider describing the choreography itself. To do this we shall:</p><ul><li>Declare the relationships, which act as an additional type check on the
|
|
channels.</li><li>Declare variables, for instances of the channel and the information types.</li><li>Define the interactions and their ordering constraints.</li></ul><p>The only <code>relationship</code> we have is <code>Buyer2Seller</code> and we prefix
|
|
this with the name space (tns).</p><p>Then we add the <code>variable declaration</code> based
|
|
on the channel and information types that we have already defined for each
|
|
of <code>Buyer2SellerC</code>, <code>quoteRequest</code>,
|
|
<code>quoteResponse</code> and <code>faultResponse</code> which
|
|
respectively are of types <code>Buyer2SellerChannel</code>,
|
|
<code>QuoteRequestType</code>, <code>QuoteResponseType</code> and
|
|
<code>QuoteReponseFaultType</code>. The variables are declared in a
|
|
<code>variableDefinitions</code> block. In WS-CDL it is important to
|
|
note that variables are always situated. That is variables are declared to
|
|
reside at one or more roles independently of each other. This is why the
|
|
variable declarations have a <code>roleTypes</code> attribute. In our
|
|
degenerate example we declare our variables to be situated at both the buyer
|
|
and the seller roles. The fact that two roles may have the same variable name
|
|
does not have any meaning in WS-CDL. Using the <code>roleTypes</code>
|
|
attribute in a variable declaration is simply for convenience. The same
|
|
variable name could be declared twice at two different roles and this is the
|
|
same as adding the two roles to the <code>roleTypes</code>. If you omit the
|
|
<code>roleTypes</code> the default behavior is to declare the variable
|
|
at all roles within this choreography where the roles are inferred from the
|
|
declared relationships that participate in it. </p><p> The WS-CDL fragment below shows how the <code>relationship</code> and <code>variable
|
|
declarations</code> are put together. We have named
|
|
the choreography as <code>DegenerateChoreography</code>. We have also set
|
|
the <code>root</code> attribute to be <code>true</code> because this
|
|
choreography is the root of the interactions that will take place. When
|
|
<code>root</code> is set to <code>false</code> the choreography is
|
|
deemed not to start the interactions. </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment8" id="wscdlfragment8"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>
|
|
<choreography name="DegenerateChoreography" root="true">
|
|
<description type="documentation">
|
|
The Choreography for the degenerate use case
|
|
</description>
|
|
<relationship type="tns:Buyer2Seller"/>
|
|
<variableDefinitions>
|
|
<variable name="Buyer2SellerC"
|
|
channelType="tns:Buyer2SellerChannel"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">
|
|
Channel Variable
|
|
</description>
|
|
</variable>
|
|
<variable name="quoteRequest"
|
|
informationType="tns:QuoteRequestType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">
|
|
Request Message
|
|
</description>
|
|
</variable>
|
|
<variable name="quoteResponse"
|
|
informationType="tns:QuoteResponseType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">
|
|
Response Message
|
|
</description>
|
|
</variable>
|
|
<variable name="faultResponse"
|
|
informationType="tns:QuoteResponseFaultType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">
|
|
Fault Message
|
|
</description>
|
|
</variable>
|
|
</variableDefinitions>
|
|
</pre></div></div><p> To recap, we have</p><ul><li>defined all of our types,</li><li> and declared our
|
|
variables</li></ul><p>What remains is to define the interactions and their ordering
|
|
based on all that has preceded it. </p><p> We shall define our single interaction that we presented earlier within a
|
|
sequence. We don't have to do this but it is good practice to start with a
|
|
sequence and then add things to it. If you don't an explicit sequence then it is
|
|
implied. </p><p> Thus our example now looks like the following: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment9" id="wscdlfragment9"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>
|
|
<?xml version="1.0" encoding="UTF-8"?>
|
|
<package
|
|
name="DegenerateExample"
|
|
author="Stephen Ross-Talbot"
|
|
version="1.0"
|
|
targetNamespace="http://www.w3.org/2002/ws/chor/primer"
|
|
xmlns:tns="http://www.w3.org/2002/ws/chor/primer"
|
|
xmlns="http://www.w3.org/2005/10/cdl"
|
|
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
|
|
xmlns:primer="http://www.w3.org/2002/ws/chor/primer">
|
|
<description type="documentation">
|
|
Degenerate Example for Primer
|
|
</description>
|
|
|
|
…
|
|
|
|
<choreography name="DegenerateChoreography" root="true">
|
|
<description type="documentation">
|
|
The Choreography for the degenerate use case
|
|
</description>
|
|
…
|
|
|
|
<sequence>
|
|
<interaction name="QuoteElicitation" operation="getQuote" channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">
|
|
Quote Elicitation
|
|
</description>
|
|
<participate relationshipType="tns:Buyer2Seller" fromRoleTypeRef="tns:BuyerRole" toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="QuoteRequest" informationType="tns:QuoteRequestType" action="request">
|
|
<description type="documentation">
|
|
Quote Request Message Exchange
|
|
</description>
|
|
<send variable="cdl:getVariable('quoteRequest','','')"/>
|
|
<receive variable="cdl:getVariable('quoteRequest','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponse" informationType="tns:QuoteResponseType" action="respond">
|
|
<description type="documentation">
|
|
Quote Response Message Exchange
|
|
</description>
|
|
<send variable="cdl:getVariable('quoteResponse','','')"/>
|
|
<receive variable="cdl:getVariable('quoteResponse','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponseFault" informationType="tns:QuoteResponseFaultType" action="respond" faultName="InvalidProductFault">
|
|
<description type="documentation">
|
|
Quote Response Fault Exchange
|
|
</description>
|
|
<send variable="cdl:getVariable('faultResponse','','')"/>
|
|
<receive variable="cdl:getVariable('faultResponse','','')"/>
|
|
</exchange>
|
|
</interaction>
|
|
</sequence>
|
|
</choreography>
|
|
</package>
|
|
</pre></div></div><p> In our example above there are three exchanges within a single interaction
|
|
which is within a sequence. The first exchange is called
|
|
<code>QuoteRequest</code> is based on a operation defined in the
|
|
interaction called <code>getQuote</code> and this occurs over a channel
|
|
variable called <code>BuyerSellerC</code>. This exchange is based on a
|
|
message being sent from the buyer to seller which is of type
|
|
<code>tns:QuoteRequestType</code> and it is marked as a
|
|
<code>request</code>. The exchange also defines the variables that will be
|
|
used to send and to receive the content of the message of type
|
|
<code>tns:QuoteResponseType</code>, in each case the variable is called
|
|
<code>quoteRequest</code> and appears inside a cdl function which
|
|
understands how to get a variable called <code>cdl:getVariable(...)</code>.
|
|
The first parameter to this function is the name of the variable in the
|
|
choreography, the second and third parameters in this case are left blank.
|
|
The roles for these variables are inferred from the direction of the
|
|
exchange and so we can infer ourselves that <code>quoteRequest</code> was
|
|
populated before the interaction at the buyer and then when the exchange
|
|
completes the seller's <code>quoteRequest</code> variable is populated with
|
|
the same values. The variables are not shared but after the exchange they
|
|
hold common knowledge between the roles that participate in the exchange. </p><p> The second exchange is similar to the first except that it is marked as a
|
|
<code>respond</code>. As such we can infer the direction is from the
|
|
seller back to the buyer. </p><p> The third and final exchange occurs if the seller finds a fault with the
|
|
request and as a result decides to send a response, which is why it is
|
|
marked as a <code>respond</code>. Because this is a fault, we also declare
|
|
that the exchange has a <code>faultName</code>, in this case we have called
|
|
the faultName <code>InvalidProduct</code> to denote that the product which
|
|
is the subject of the quote request is invalid in some way. It could be
|
|
because it does not exist or indeed because no stock exists at present and
|
|
so no quote can be provided. The decision as to which one it really is, is
|
|
obscured. </p><p> The abstract syntax for a choreography, thus far, is as follows: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlsyntax6" id="wscdlsyntax6"></a>Example: WS-CDL Choreography definition</div><div class="exampleInner"><pre>
|
|
choreography ::=
|
|
<choreography name="ncname"
|
|
complete="xsd:boolean XPath-expression"?
|
|
isolation="true"|"false"?
|
|
root="true"|"false"?
|
|
coordination="true"|"false"? >
|
|
<relationship type="qname" />+
|
|
variableDefinitions?
|
|
|
|
Activity-Notation*
|
|
|
|
</choreography>
|
|
|
|
variableDefintions ::=
|
|
<variableDefinitions>
|
|
<variable name="ncname"
|
|
informationType="qname"?|channelType="qname"?
|
|
roleTypes="list of qname"? />+
|
|
</variableDefinitions>
|
|
|
|
Activity-Notation ::=
|
|
<sequence<
|
|
<interaction name="NCName"
|
|
channelVariable="QName"
|
|
operation="NCName">
|
|
<description;></descriptions>
|
|
|
|
<participate relationshipType="QName"
|
|
fromRoleTypeRef="QName" toRoleTypeRef="QName" />
|
|
|
|
<exchange name="NCName"
|
|
faultName="QName"?
|
|
informationType="QName"?|channelType="QName"?
|
|
action="request"|"respond" >
|
|
<send variable="XPath-expression"?/>
|
|
<receive variable="XPath-expression"?/>
|
|
</exchange>*
|
|
</interaction>*
|
|
</sequence<
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="completeexample" id="completeexample"></a>3.2.9 Complete Example</h4><p> Having described all of the necessary types and having described the salient
|
|
aspects of the Choreography we present the complete example. </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment10" id="wscdlfragment10"></a>Example: WS-CDL Complete Example</div><div class="exampleInner"><pre>
|
|
<?xml version="1.0" encoding="UTF-8"?>
|
|
<package
|
|
name="DegenerateExample"
|
|
author="Stephen Ross-Talbot"
|
|
version="1.0"
|
|
targetNamespace="http://www.w3.org/2002/ws/chor/primer"
|
|
xmlns:tns="http://www.w3.org/2002/ws/chor/primer"
|
|
xmlns="http://www.w3.org/2005/10/cdl"
|
|
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
|
|
xmlns:primer="http://www.w3.org/2002/ws/chor/primer">
|
|
<description type="documentation">
|
|
Degenerate Example for Primer
|
|
</description>
|
|
|
|
<informationType name="QuoteRequestType" type="primer:QuoteRequestMsg">
|
|
<description type="documentation">
|
|
Quote Request Message
|
|
</description>
|
|
</informationType>
|
|
<informationType name="QuoteResponseType" type="primer:QuoteResponseMsg">
|
|
<description type="documentation">
|
|
Quote Response Message
|
|
</description>
|
|
</informationType>
|
|
<informationType name="QuoteResponseFaultType" type="primer:QuoteResponseFaultMsg">
|
|
<description type="documentation">
|
|
Quote Response Fault Message
|
|
</description>
|
|
</informationType>
|
|
<informationType name="IdentityType" type="xsd:string">
|
|
<description type="documentation">
|
|
Identity Attribute
|
|
</description>
|
|
</informationType>
|
|
<informationType name="URI" type="xsd:uri">
|
|
<description type="documentation">
|
|
Reference Token For Channels
|
|
</description>
|
|
</informationType>
|
|
|
|
<token name="id" informationType="tns:IdentityType">
|
|
<description type="documentation">
|
|
Identity token
|
|
</description>
|
|
</token>
|
|
<token name="URI" informationType="tns:URI">
|
|
<description type="documentation">
|
|
Reference Token for Channels
|
|
</description>
|
|
</token>
|
|
<tokenLocator tokenName="tns:id" informationType="tns:QuoteRequestType" query="/quote/@id">
|
|
<description type="documentation">
|
|
Identity for Quote Request
|
|
</description>
|
|
</tokenLocator>
|
|
<tokenLocator tokenName="tns:id" informationType="tns:QuoteResponseType" query="/quote/@key">
|
|
<description type="documentation">
|
|
Identity for Quote Response
|
|
</description>
|
|
</tokenLocator>
|
|
<tokenLocator tokenName="tns:id" informationType="tns:QuoteResponseFaultType" query="/quote/@key">
|
|
<description type="documentation">
|
|
Identity for Quote Response Fault
|
|
</description>
|
|
</tokenLocator>
|
|
|
|
<roleType name="BuyerRole">
|
|
<description type="documentation">
|
|
Role for Buyer
|
|
</description>
|
|
<behavior name="BuyerBehavior" interface="BuyerBehaviorInterface">
|
|
<description type="documentation">
|
|
Behavior for Buyer Role
|
|
</description>
|
|
</behavior>
|
|
</roleType>
|
|
<roleType name="SellerRole">
|
|
<description type="documentation">
|
|
Role for Seller
|
|
</description>
|
|
<behavior name="SellerBehavior" interface="SellerBehaviorInterface">
|
|
<description type="documentation">
|
|
Behavior for Seller
|
|
</description>
|
|
</behavior>
|
|
</roleType>
|
|
|
|
<relationshipType name="Buyer2Seller">
|
|
<description type="documentation">
|
|
Buyer Seller Relationship
|
|
</description>
|
|
<roleType typeRef="tns:BuyerRole"/>
|
|
<roleType typeRef="tns:SellerRole"/>
|
|
</relationshipType>
|
|
|
|
<participantType name="Seller">
|
|
<description type="documentation">
|
|
Seller Participant
|
|
</description>
|
|
<roleType typeRef="tns:SellerRole"/>
|
|
</participantType>
|
|
<participantType name="Buyer">
|
|
<description type="documentation">
|
|
Buyer Participant
|
|
</description>
|
|
<roleType typeRef="tns:BuyerRole"/>
|
|
</participantType>
|
|
|
|
<channelType name="Buyer2SellerChannel">
|
|
<description type="documentation">
|
|
Buyer to Seller Channel Type
|
|
</description>
|
|
<roleType typeRef="tns:SellerRole"/>
|
|
<reference>
|
|
<token name="tns:URI"/>
|
|
</reference>
|
|
<identity type="primary">
|
|
<token name="tns:id"/>
|
|
</identity>
|
|
</channelType>
|
|
|
|
<choreography name="DegenerateChoreography" root="true">
|
|
<description type="documentation">
|
|
The Choreography for the degenerate use case
|
|
</description><relationship type="tns:Buyer2Seller"/>
|
|
<variableDefinitions>
|
|
<variable name="Buyer2SellerC"
|
|
channelType="tns:Buyer2SellerChannel"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">
|
|
Channel Variable
|
|
</description>
|
|
</variable>
|
|
<variable name="quoteRequest"
|
|
informationType="tns:QuoteRequestType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">
|
|
Request Message
|
|
</description>
|
|
</variable>
|
|
<variable name="quoteResponse"
|
|
informationType="tns:QuoteResponseType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">
|
|
Response Message
|
|
</description>
|
|
</variable>
|
|
<variable name="faultResponse"
|
|
informationType="tns:QuoteResponseFaultType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">
|
|
Fault Message
|
|
</description>
|
|
</variable>
|
|
</variableDefinitions>
|
|
|
|
<sequence>
|
|
<interaction name="QuoteElicitation" operation="getQuote" channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">
|
|
Quote Elicitation
|
|
</description>
|
|
<participate relationshipType="tns:Buyer2Seller" fromRoleTypeRef="tns:BuyerRole" toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="QuoteRequest" informationType="tns:QuoteRequestType" action="request">
|
|
<description type="documentation">
|
|
Quote Request Message Exchange
|
|
</description>
|
|
<send variable="cdl:getVariable('quoteRequest','','')"/>
|
|
<receive variable="cdl:getVariable('quoteRequest','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponse" informationType="tns:QuoteResponseType" action="respond">
|
|
<description type="documentation">
|
|
Quote Response Message Exchange
|
|
</description>
|
|
<send variable="cdl:getVariable('quoteResponse','','')"/>
|
|
<receive variable="cdl:getVariable('quoteResponse','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponseFault" informationType="tns:QuoteResponseFaultType" action="respond" faultName="InvalidProductFault">
|
|
<description type="documentation">
|
|
Quote Response Fault Exchange
|
|
</description>
|
|
<send variable="cdl:getVariable('faultResponse','','')"/>
|
|
<receive variable="cdl:getVariable('faultResponse','','')"/>
|
|
</exchange>
|
|
</interaction>
|
|
</sequence>
|
|
</choreography>
|
|
</package>
|
|
</pre></div></div></div></div></div><div class="div1">
|
|
<h2><a name="intermediate" id="intermediate"></a>4 Intermediate Topics</h2><p>In the previous section we introduced the most basic of features of WS-CDL using a degenerate
|
|
example to illustrate how to write down a choreography description. In this section we shall
|
|
describe how to add further structure to a choreography. In this section we provide the reader
|
|
with all of the facilities that one would need to write down a choreography that could actually
|
|
be used in practice. It provides what we consider to be the basic features for real systems
|
|
described in WS-CDL.</p><p>We shall describe how to use variables, loops, conditionals, we shall describe how to modularize
|
|
a choreography description, how to describe exceptions and what to do about them and how they
|
|
relate to WSDL faults.</p><p>In order to best illustrate all of this we shall revisit our degenerate example and
|
|
some further complexity to it and then we shall describe it using WS-CDL. Throughout
|
|
the course of this section we shall continue to add more to our example as a means
|
|
of illustrating WS-CDL.</p><div class="div2">
|
|
<h3><a name="intermediateexample" id="intermediateexample"></a>4.1 The Intermediate Example </h3><p>We go back to our degenerate example which had a single interaction which we wrote down as a single
|
|
UML sequence diagram. We now add a little more to the example to make it more real. We shall concentrate
|
|
on the process of bartering whereby the buyer requests a price from the seller and enters some sort of
|
|
repetitive behavior in which the buyer requests an updated price from the seller and continues until the
|
|
buyer decides to order the goods at the prevailing price. This example is shown in the UML sequence
|
|
diagram below:</p><img src="pictures/Figure3.png" alt="Diagram of the simple bartering process" /><p>In the example we can see that we need to understand when a fault has occurred on the initial request
|
|
for quote, the <code>getQuote</code> operation. We can see that this has three message exchanges which
|
|
are <code>quoteRequest</code>, <code>quoteResponse</code> and <code>quoteFault</code> respectively.
|
|
They are exactly the same as the degenerate example we looked at earlier.</p><p>We shall need to determine which response we got back. If the response was not a fault then we can
|
|
continue a process in which the buyer sends an <code>updateQuote</code> operation that includes the
|
|
last price to see if a better price can be gleaned from the seller.</p><p>When the buyer decides to act on a price the buyer simply invokes an <code>order</code> operation at
|
|
the seller role and we terminate the bartering process by setting a variable to terminate the process.
|
|
Because variables are situated we shall need to place the variable at a specific role to handle this.
|
|
In our model we shall place this variable, <code>barteringDone</code> which is a <code>Boolean</code>
|
|
at the <code>SellerRole</code>.</p><p>To model this is WS-CDL we shall need to define a some repetitive behavior that is controlled by
|
|
our <code>barteringDone</code> variable.
|
|
There are other ways of doing this which are counter intuitive but for now we shall use
|
|
just use our variable to control the repetition.</p><p>Having set out an the intermediate example we shall now look at extending it. In many systems
|
|
quotes have a duration associated with them. In technology terms this has given rise to the notion
|
|
of a duration on a message in standards such as JMS and WS-RM. The durations in most if not all
|
|
cases are set as part of a business policy rather than being driven by technology and in this
|
|
extended example we add the notion of a duration to a quote. This is presented in the sequence
|
|
diagram below. We shall set our duration at <code>30 seconds</code> and show how we do this in
|
|
a choreographic description using WS-CDL.</p><img src="pictures/Figure4.png" alt="Diagram of the simple bartering process with a quote duration" /><p>The most important decisions we shall make when we model this are who sets the duration and
|
|
who owns the clock by which we measure the duration, in effect at what role do we situate the
|
|
duration.</p><p>When we model this we shall situate the duration at the <code>SellerRole</code> and see what effect
|
|
this has on our WS-CDL model and then situate it at the <code>BuyerRole</code> and see what the
|
|
difference is between the two models. It is our opinion that a duration of this nature really belongs
|
|
at the <code>SellerRole</code></p><p>In our final additions to our intermediate example we shall add some further roles to describe
|
|
the additional collaborations between a <code>SellerRole</code>, a <code>CreditAgencyRole</code> -
|
|
this role will be responsible for providing credit checking facilities, a <code>ShippingRole</code> -
|
|
this role will be responsible for providing onward shipping of the good bought and shipping details
|
|
which need to be delivered back to the <code>BuyerRole</code>.</p><img src="pictures/Figure5.png" alt="Diagram of the basic buyer, seller, credit agency and shipper" /><p>We shall have some key decision to make how we model this example too. We shall model it first as
|
|
a set of <code>workunits</code> that simply follow one another, a sequence.</p><p>We shall also model it
|
|
as a set of dependent <code>workunits</code> which are running concurrently and in which the act
|
|
of credit checking will depend on the completion of the bartering process and so will be dependent
|
|
on a variables value that denotes the completion of the bartering process and similarly between the
|
|
act of credit checking and shipping.</p><img src="pictures/Figure6.png" alt="Diagram of the dependent processes" /><p>Finally shall model the delivery of the necessary delivery details
|
|
in two ways. In the first instance we shall simply have the <code>SellerRole</code> receive the details
|
|
from the <code>ShipperRole</code> and pass them back to the <code>BuyerRole</code> and in the second
|
|
instance we shall model it as a callback from the <code>ShipperRole</code> directly back to the
|
|
<code>BuyerRole</code>. The former would require a-priori knowledge of the buyer whereas the latter
|
|
does not and so would be a better model.</p><p>It should be noted that while the sequence diagrams are instructive at an abstract level they do not
|
|
record the level of detail
|
|
needed to document the external observable behavior to fully describe
|
|
these examples. In order to convey enough information to enable developers to construct the necessary
|
|
services further annotation and textual explanation is needed. The benefit of doing this in
|
|
WS-CDL is that we can describe all that is needed from an externally observable behavior perspective,
|
|
akin to a high level design, and so facilitate service construction and onward testing
|
|
of services guaranteeing interoperability throughout.</p><img src="pictures/Figure7.png" alt="Diagram of the callback solution" /><div class="div3">
|
|
<h4><a name="variables" id="variables"></a>4.1.1 Variables</h4><p>To continue with our example above we need to declare a variable that can be used to
|
|
control the bartering process. We shall call this variable <code>barteringDone</code> and
|
|
we shall give it a type of <code>xsd:boolean</code> which we shall declare as an information
|
|
type in WS-CDL called <code>Boolean</code>. In WS-CDL variables are always situated (or
|
|
located). That is they are defined at one or more roles. We have seen this already when we
|
|
defined the channels and messages for the degenerate example. For our <code>barteringDone</code>
|
|
we need to consider where the control for the value of the variable will be located. We need
|
|
decide on the master for this process and the slaves. We shall select the <code>SellerrRole</code>
|
|
as the master and so situate our variable at this role.</p><p> It is important to remember that when variables are manipulated in some way
|
|
the manipulation is also situated. If a variable is situated at one role then it becomes
|
|
clear that manipulation of that variable is also situation at the same place. When a variable
|
|
is situated at more than one role we need to be clear about where manipulation takes place because
|
|
the value of a variable after manipulation is scoped to that role and where it is situated.</p><p>
|
|
Variables are not shared. Rather they exist at
|
|
the roles they are defined at and only have the same value if some explicit
|
|
exchange occurs that describes how they become the same value. The fact that
|
|
they have they may have the same name has no bearing on the semantics of a
|
|
variable as is no guarantee that they will ever hold the same content, but of
|
|
course it would be normal to think that they might simply because they bear the
|
|
same name. So it is good practice in describing choreographies to name variables
|
|
well so that clarity can be preserved. </p><p> The scope of a situated variable, we say <code>quoteRequest@buyer</code>, is at
|
|
it's role. So in this case it is at the <code>buyer</code>. The use of the
|
|
<code>@</code> sign has no significance in WS-CDL. We only use it here as a
|
|
short hand to indicate where the variable is located. The same short hand is
|
|
used in the formal description of WS-CDL which can be found at <code>SOME URL TO
|
|
MARCO'S WORK</code>. </p><p> If we tried to copy <code>quoteRequest@buyer</code> to
|
|
<code>quoteRequest@seller</code> we would exceed the scoping contract. It would
|
|
not be allowed. If we tried to copy <code>quoteRequest@buyer</code>, in whole or
|
|
in part, to <code>x@buyer</code>, where x is some variable declared at buyer,
|
|
then it would succeed. The variable <code>x@buyer</code> after the copy was
|
|
completed, would indeed have the same value as <code>quoteRequest@buyer</code>.
|
|
If we wanted to ensure that <code>quoteRequest@seller</code> was populated with
|
|
the same values as <code>quoteRequest@buyer</code> we would use an interaction
|
|
in which the variables <code>quoteRequest@buyer</code> and
|
|
<code>quoteRequest@seller</code> are in the appropriate send and receive
|
|
parts of the exchange within the interaction, much as we did in our degenerate
|
|
example in the previous section. </p><p> Our <code>barteringDone</code> variable will be situated at the <code>SellerRole</code>
|
|
which we shall deem to be in control of the loop. The WS-CDL fragments for the information type
|
|
and the variable declaration are shown below: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment4f" id="wscdlfragment4f"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>
|
|
<informationType name="BooleanType" type="xsd:boolean">
|
|
<description type="documentation">
|
|
Useful boolean type
|
|
</description>
|
|
</informationType>
|
|
.....
|
|
<choreography name="IntermediateChoreography" root="true">
|
|
<description type="documentation">
|
|
The Choreography for the intermediate use case
|
|
</description><relationship type="tns:Buyer2Seller"/>
|
|
<variableDefinitions>
|
|
<variable name="barteringDone"
|
|
informationType="tns:Boolean"
|
|
roleTypes="tns:SellerRole">
|
|
<description type="documentation">
|
|
Used to control a loop for bartering between buyer and seller
|
|
</description>
|
|
</variable>
|
|
.......
|
|
</variableDefinitions>
|
|
.......
|
|
</choreography>
|
|
</pre></div></div><p> We may define other variables throughout the course of this section and we shall
|
|
indicate where they are situated and what type they are as narrative. </p></div><div class="div3">
|
|
<h4><a name="workunits" id="workunits"></a>4.1.2 Non Blocking Workunits</h4><p> In this section we look at repetitive workunits and come back to conditional workunits.
|
|
A workunit provides repetition based on
|
|
some predicate and provides a way of adding conditionality. Workunits
|
|
in general have a Body that includes the other choreography structuring
|
|
constructs. In the specification these structuring constructs are called
|
|
<code>ActionNotation</code>. The <code>ActionNotation</code> is only performed
|
|
if the workunits attributes
|
|
enable it to be performed. In the case of a simple conditional the guard condition (G) is
|
|
evaluated and if true the Body is performed. In the case of a simple
|
|
repetition the guard condition (G) is omitted and so will
|
|
always evaluate to true, the Body is therefore
|
|
performed and if the repetition condition (R) evaluates to true it is performed
|
|
again and again until the repetition condition evaluates to false. The more complex
|
|
scenario is when a guard condition (G) and a repetition condition (R) are both present.
|
|
In this case the workunit is dependent on the guard condition first and then the
|
|
repetition condition afterwards. We present the general structure of, non-blocking (B is False),
|
|
workunits as follows:
|
|
</p><div class="exampleInner"><pre>
|
|
Workunit (G) (R) (B is False)
|
|
Body
|
|
</pre></div><p>
|
|
|
|
Where G and R are of type <code>xsd:boolean</code> Xpath expressions and B is an
|
|
<code>xsd:boolean</code> constrained to be
|
|
<code>true</code> or <code>false</code>. A typical order of evaluation is as follows:
|
|
</p><div class="exampleInner"><pre>
|
|
(G) Body (R G) Body (R G) Body
|
|
</pre></div><p>Which equates to (in pseudo code):</p><div class="exampleInner"><pre>
|
|
while (G)
|
|
{
|
|
Body
|
|
} until (!R)
|
|
</pre></div><p>IF G is always True THEN it equates to:</p><div class="exampleInner"><pre>
|
|
repeat
|
|
{
|
|
Body
|
|
} until (!R)
|
|
</pre></div><p>IF R is always False THEN it equates to:</p><div class="exampleInner"><pre>
|
|
if (G)
|
|
{
|
|
Body
|
|
}
|
|
</pre></div><div class="div4">
|
|
<h5><a name="repeatingworkunits" id="repeatingworkunits"></a>4.1.2.1 Repetition</h5><p> In order to model our repetitive behavior in which, once the buyer has a quote, the
|
|
buyer engages in a repetitive bartering process in order to get an acceptable price, we
|
|
need to use a workunit that has some repetition condition. The example below used a
|
|
workunit that we have named "Repeat until bartering has been
|
|
completed" that is our repeating workunit for this bartering process.
|
|
In it we have a condition that governs the repetition, namely
|
|
<code>barteringDone = false</code>. This
|
|
condition evaluates the declared variable "barteringDone" to see if it is
|
|
false. If false the workunit proceeds and repeats until such time as the
|
|
condition ("barteringDone = false") evaluates to true. Within the workunit
|
|
we have a number of things that can happen, our choice. Either a
|
|
<code>silentAction</code> occurs - more of what this actually means
|
|
later - that models the timeout of a quote and we situate this at the
|
|
<code>BuyerRole</code>, or a <code>sequence</code> occurs in which the
|
|
Buyer accepts the quote and engages in the act of buying, or a different
|
|
<code>sequence</code> that models the Buyer updating the quote - in
|
|
effect requesting a new price. Only one of these can occur within the choice
|
|
at any one time. The second sequence includes setting our control variable
|
|
<code>barteringDone</code> to <code>true</code> and it is this that
|
|
causes the repetition to terminate.</p><p> Note that the repetition is situated at the <code>SellerRole</code> as is the
|
|
assignment to the variable <code>barteringDone</code>. </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment10f" id="wscdlfragment10f"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>
|
|
<?xml version="1.0" encoding="UTF-8"?>
|
|
<package name="IntermediateExample" author="Stephen Ross-Talbot" version="1.0"
|
|
targetNamespace="http://www.w3.org/2002/ws/chor/primer"
|
|
xmlns:tns="http://www.w3.org/2002/ws/chor/primer" xmlns="http://www.w3.org/2005/10/cdl"
|
|
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
|
|
xmlns:primer="http://www.w3.org/2002/ws/chor/primer">
|
|
<description type="documentation">Intermediate Example: Simple Bartering Process</description>
|
|
|
|
<informationType name="QuoteRequestType" type="primer:QuoteRequestMsg">
|
|
<description type="documentation">Quote Request Message</description>
|
|
</informationType>
|
|
<informationType name="QuoteResponseType" type="primer:QuoteResponseMsg">
|
|
<description type="documentation">Quote Response Message</description>
|
|
</informationType>
|
|
<informationType name="QuoteResponseFaultType" type="primer:QuoteResponseFaultMsg">
|
|
<description type="documentation">Quote Response Fault Message</description>
|
|
</informationType>
|
|
<informationType name="IdentityType" type="xsd:string">
|
|
<description type="documentation">Identity Attribute</description>
|
|
</informationType>
|
|
<informationType name="URI" type="xsd:uri">
|
|
<description type="documentation">Reference Token For Channels</description>
|
|
</informationType>
|
|
<informationType name="OrderRequestType" type="primer:OrderRequestMessage">
|
|
<description type="documentation">Order Request Message</description>
|
|
</informationType>
|
|
<informationType name="OrderResponseType" type="primer:OrderResponseMessage">
|
|
<description type="documentation">Order Response Message</description>
|
|
</informationType>
|
|
<informationType name="Boolean" type="xsd:boolean">
|
|
<description type="documentation">Boolean type for use in loop control</description>
|
|
</informationType>
|
|
|
|
<token name="id" informationType="tns:IdentityType">
|
|
<description type="documentation">Identity token</description>
|
|
</token>
|
|
<token name="URI" informationType="tns:URI">
|
|
<description type="documentation">Reference Token for Channels</description>
|
|
</token>
|
|
|
|
<tokenLocator tokenName="tns:id" informationType="tns:QuoteRequestType" query="/quote/@id">
|
|
<description type="documentation">Identity for QuoteRequestType</description>
|
|
</tokenLocator>
|
|
<tokenLocator tokenName="tns:id" informationType="tns:QuoteResponseType" query="/quote/@key">
|
|
<description type="documentation">Identity for QuoteResponseType</description>
|
|
</tokenLocator>
|
|
<tokenLocator tokenName="tns:id" informationType="tns:QuoteResponseFaultType"
|
|
query="/quote/@key">
|
|
<description type="documentation">Identity for QuoteResponseFaultType</description>
|
|
</tokenLocator>
|
|
<tokenLocator tokenName="tns:id" informationType="tns:OrderRequestType" query="/order/@orderId">
|
|
<description type="documentation">Identity for OrderRequestType</description>
|
|
</tokenLocator>
|
|
<tokenLocator tokenName="tns:id" informationType="tns:OrderResponseType" query="/order/@orderId">
|
|
<description type="documentation">Id for OrderResponseType</description>
|
|
</tokenLocator>
|
|
|
|
<roleType name="BuyerRole">
|
|
<description type="documentation">Role for Buyer</description>
|
|
<behavior name="BuyerBehavior" interface="BuyerBehaviorInterface">
|
|
<description type="documentation">Behavior for Buyer Role</description>
|
|
</behavior>
|
|
</roleType>
|
|
<roleType name="SellerRole">
|
|
<description type="documentation">Role for Seller</description>
|
|
<behavior name="SellerBehavior" interface="SellerBehaviorInterface">
|
|
<description type="documentation">Behavior for Seller</description>
|
|
</behavior>
|
|
</roleType>
|
|
|
|
<relationshipType name="Buyer2Seller">
|
|
<description type="documentation">Buyer Seller Relationship</description>
|
|
<roleType typeRef="tns:BuyerRole"/>
|
|
<roleType typeRef="tns:SellerRole"/>
|
|
</relationshipType>
|
|
|
|
<participantType name="Seller">
|
|
<description type="documentation">Seller Participant</description>
|
|
<roleType typeRef="tns:SellerRole"/>
|
|
</participantType>
|
|
<participantType name="Buyer">
|
|
<description type="documentation">Buyer Participant</description>
|
|
<roleType typeRef="tns:BuyerRole"/>
|
|
</participantType>
|
|
|
|
<channelType name="Buyer2SellerChannel">
|
|
<description type="documentation">Buyer to Seller Channel Type</description>
|
|
<roleType typeRef="tns:SellerRole"/>
|
|
<reference>
|
|
<token name="tns:URI"/>
|
|
</reference>
|
|
<identity type="primary">
|
|
<token name="tns:id"/>
|
|
</identity>
|
|
</channelType>
|
|
|
|
|
|
<choreography name="IntermediateChoreography" root="true">
|
|
<description type="documentation">The Choreography for the degenerate use case</description>
|
|
<relationship type="tns:Buyer2Seller"/>
|
|
|
|
<variableDefinitions>
|
|
<variable name="Buyer2SellerC" channelType="tns:Buyer2SellerChannel"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">Channel Variable</description>
|
|
</variable>
|
|
<variable name="quoteRequest" informationType="tns:QuoteRequestType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">Request Message</description>
|
|
</variable>
|
|
<variable name="quoteResponse" informationType="tns:QuoteResponseType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">Response Message</description>
|
|
</variable>
|
|
<variable name="faultResponse" informationType="tns:QuoteResponseFaultType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">Fault Message</description>
|
|
</variable>
|
|
<variable name="orderRequest" informationType="tns:OrderRequestType"
|
|
roleTypes="tns:BuyerRole tns:SellerRole">
|
|
<description type="documentation">Order Request Message</description>
|
|
</variable>
|
|
<variable name="barteringDone" informationType="tns:Boolean" roleTypes="tns:SellerRole">
|
|
<description type="documentation">Variable used to control the loop exit from
|
|
t</description>
|
|
</variable>
|
|
</variableDefinitions>
|
|
|
|
<sequence>
|
|
<assign roleType="tns:SellerRole">
|
|
<description type="documentation">Initialise Loop Variable</description>
|
|
<copy name="setBarteringDone">
|
|
<description type="documentation">Set barteringDone to false</description>
|
|
<source expression="false()"/>
|
|
<target variable="cdl:getVariable('barteringDone','','')"/>
|
|
</copy>
|
|
</assign>
|
|
<interaction name="QuoteElicitation" operation="getQuote"
|
|
channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">Elicit a quote from the seller</description>
|
|
<participate relationshipType="tns:Buyer2Seller" fromRoleTypeRef="tns:BuyerRole"
|
|
toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="QuoteRequest" informationType="tns:QuoteRequestType"
|
|
action="request">
|
|
<description type="documentation">Quote Request Message Exchange</description>
|
|
<send variable="cdl:getVariable('quoteRequest','','')"/>
|
|
<receive variable="cdl:getVariable('quoteRequest','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponse" informationType="tns:QuoteResponseType"
|
|
action="respond">
|
|
<description type="documentation">Quote Response Message Exchange</description>
|
|
<send variable="cdl:getVariable('quoteResponse','','')"/>
|
|
<receive variable="cdl:getVariable('quoteResponse','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponseFault" informationType="tns:QuoteResponseFaultType"
|
|
action="respond" faultName="InvalidProductFault">
|
|
<send variable="cdl:getVariable('faultResponse','','')"
|
|
causeException="TerminalFailure"/>
|
|
<receive variable="cdl:getVariable('faultResponse','','')"
|
|
causeException="TerminalFailure"/>
|
|
</exchange>
|
|
</interaction>
|
|
<workunit name="WhileBarteringIsNotFinished"
|
|
guard="cdl:getVariable("barteringDone","","")
|
|
= true()" repeat="true()">
|
|
<description type="documentation">While barteringDone is false</description>
|
|
<choice>
|
|
<sequence>
|
|
<description type="documentation">Accept the quote and place the order</description>
|
|
<interaction name="QuoteAccept" operation="order"
|
|
channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">The Buyer accepts the quote and orders
|
|
the goods based on the last price</description>
|
|
<participate relationshipType="tns:Buyer2Seller"
|
|
fromRoleTypeRef="tns:BuyerRole" toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="OrderRequest" informationType="tns:OrderRequestType"
|
|
action="request">
|
|
<send variable="cdl:getVariable('orderRequest','','')"/>
|
|
<receive variable="cdl:getVariable('orderRequest','','')"/>
|
|
</exchange>
|
|
</interaction>
|
|
<assign roleType="tns:SellerRole">
|
|
<description type="documentation">Break out of the loop</description>
|
|
<copy name="setBarteringDone">
|
|
<description type="documentation">Set barteringDone to true</description>
|
|
<source expression="true()"/>
|
|
<target variable="cdl:getVariable('barteringDone','','')"/>
|
|
</copy>
|
|
</assign>
|
|
</sequence>
|
|
<sequence>
|
|
<description type="documentation">Reject the quote and ask for a new quote</description>
|
|
<interaction name="QuoteReelicitation" operation="updateQuote"
|
|
channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">Barter based on previous quote</description>
|
|
<participate relationshipType="tns:Buyer2Seller"
|
|
fromRoleTypeRef="tns:BuyerRole" toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="QuoteRequest" informationType="tns:QuoteRequestType"
|
|
action="request">
|
|
<description type="documentation">Quote re-request based on amended
|
|
quoteRequest</description>
|
|
<send variable="cdl:getVariable('quoteRequest','','')"/>
|
|
<receive variable="cdl:getVariable('quoteRequest','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponse" informationType="tns:QuoteResponseType"
|
|
action="respond">
|
|
<send variable="cdl:getVariable('quoteResponse','','')"/>
|
|
<receive variable="cdl:getVariable('quoteResponse','','')"/>
|
|
</exchange>
|
|
</interaction>
|
|
</sequence>
|
|
</choice>
|
|
</workunit>
|
|
|
|
</sequence>
|
|
</choreography>
|
|
</package>
|
|
|
|
</pre></div></div><p>In summary the WS-CDL description above represents the following:</p><div class="exampleInner"><pre>
|
|
Boolean barteringDone@Seller = false
|
|
|
|
Elicit a quote from the seller
|
|
|
|
repeat
|
|
{
|
|
choice
|
|
{
|
|
{
|
|
Accept the quote and place the order
|
|
barteringDone@Seller = true
|
|
}
|
|
{
|
|
Reject the quote and ask for a new quote
|
|
}
|
|
}
|
|
} until (barteringDone@Seller == false)
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="time" id="time"></a>4.1.3 Time</h4><p>In this extension to our simple bartering process we add a duration for a quote of 30 seconds.
|
|
When a <code>BuyerRole</code> requests a quote the <code>SellerRole</code> sets a duration,
|
|
or time to live, for the quote of 30 seconds. When a quote has exceeded this time then, as far
|
|
as the <code>SellerRole</code> is concerned the quote becomes invalid.</p><p>This is modeled in the WS-CDL description presented below:</p><div class="exampleInner"><pre>
|
|
<workunit name="WhileBarteringIsNotFinished"
|
|
guard="cdl:getVariable("barteringDone","","")
|
|
= true() " repeat="true()">
|
|
<description type="documentation">While barteringDone is false</description>
|
|
<choice>
|
|
<workunit name="TimeToLiveExceeded"
|
|
guard="cdl:hasDurationPassed(cdl:getVariable("quoteDuration","",""))
|
|
= false() " repeat="true()" block="true">
|
|
<description type="documentation">Quote times out</description>
|
|
<noAction roleType="tns:SellerRole">
|
|
<description type="documentation">DoNothing</description>
|
|
</noAction>
|
|
</workunit>
|
|
<sequence>
|
|
<description type="documentation">Accept the quote and place the order</description>
|
|
<interaction name="QuoteAccept" operation="order"
|
|
channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">The Buyer accepts the quote and orders
|
|
the goods based on the last price</description>
|
|
<participate relationshipType="tns:Buyer2Seller"
|
|
fromRoleTypeRef="tns:BuyerRole" toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="OrderRequest" informationType="tns:OrderRequestType"
|
|
action="request">
|
|
<send variable="cdl:getVariable('orderRequest','','')"/>
|
|
<receive variable="cdl:getVariable('orderRequest','','')"/>
|
|
</exchange>
|
|
</interaction>
|
|
<assign roleType="tns:SellerRole">
|
|
<description type="documentation">Break out of the loop</description>
|
|
<copy name="setBarteringDone">
|
|
<description type="documentation">Set barteringDone to true</description>
|
|
<source expression="true()"/>
|
|
<target variable="cdl:getVariable('barteringDone','','')"/>
|
|
</copy>
|
|
</assign>
|
|
</sequence>
|
|
<sequence>
|
|
<description type="documentation">Reject the quote and ask for a new quote</description>
|
|
<interaction name="QuoteReelicitation" operation="updateQuote"
|
|
channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">Barter based on previous quote</description>
|
|
<participate relationshipType="tns:Buyer2Seller"
|
|
fromRoleTypeRef="tns:BuyerRole" toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="QuoteRequest" informationType="tns:QuoteRequestType"
|
|
action="request">
|
|
<description type="documentation">Quote re-request based on amended
|
|
quoteRequest</description>
|
|
<send variable="cdl:getVariable('quoteRequest','','')"/>
|
|
<receive variable="cdl:getVariable('quoteRequest','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponse" informationType="tns:QuoteResponseType"
|
|
action="respond">
|
|
<send variable="cdl:getVariable('quoteResponse','','')"
|
|
recordReference="TimeToLive"/>
|
|
<receive variable="cdl:getVariable('quoteResponse','','')"/>
|
|
</exchange>
|
|
<record name="TimeToLive" when="before">
|
|
<description type="documentation">Record duration</description>
|
|
<source expression="quote/timeToLive"/>
|
|
<target variable="cdl:getVariable('quoteDuration','','')"/>
|
|
</record>
|
|
</interaction>
|
|
</sequence>
|
|
</choice>
|
|
</workunit>
|
|
|
|
</pre></div><p>The description above is presented in psuedo-code as follows:</p><div class="exampleInner"><pre>
|
|
Boolean barteringDone@Seller = false
|
|
|
|
Elicit a quote from the seller
|
|
Update quoteDuration@Seller from quote
|
|
|
|
while barteringDone@Seller = false do
|
|
choice
|
|
{
|
|
sequence
|
|
{ quote accept and set barteringDone@Seller=true }
|
|
sequence
|
|
{ reject quote }
|
|
workunit guard=hasDurationPassed@Seller and blocking=true
|
|
{ ...... }
|
|
}
|
|
done
|
|
</pre></div><p>The two "Update" lines in the pseudo-code represent the <code>records</code> in the
|
|
interactions and are tied to the quote response at the <code>SellerRole</code>. We shall look
|
|
more closely how we define our <code>records</code> in the relevant interactions.</p></div><div class="div3">
|
|
<h4><a name="records" id="records"></a>4.1.4 Recording information </h4><p> Often we need to record information returned from an interaction. For example we
|
|
need some way of setting the duration on the quote time to live from the <code>SellerRole</code>
|
|
to the <code>BuyerRole</code>.
|
|
To do this WS-CDL provides us with a convenient way of recording information at both ends of
|
|
an interaction. In our example above we add our record to the quote elicitation interactions
|
|
so that the duration for the quote can be passed and used in the repetition above and we show
|
|
these interaction as fragments of WS-CDL below:</p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="recordexample" id="recordexample"></a>Example: Record Example </div><div class="exampleInner"><pre>
|
|
<interaction name="QuoteElicitation" operation="getQuote"
|
|
channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">Quote Elicitation</description>
|
|
<participate relationshipType="tns:Buyer2Seller" fromRoleTypeRef="tns:BuyerRole"
|
|
toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="QuoteRequest" informationType="tns:QuoteRequestType"
|
|
action="request">
|
|
<description type="documentation">Quote Request Message Exchange</description>
|
|
<send variable="cdl:getVariable('quoteRequest','','')"/>
|
|
<receive variable="cdl:getVariable('quoteRequest','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponse" informationType="tns:QuoteResponseType"
|
|
action="respond">
|
|
<description type="documentation">Quote Response Message Exchange</description>
|
|
<send variable="cdl:getVariable('quoteResponse','','')"
|
|
recordReference="TimeToLive"/>
|
|
<receive variable="cdl:getVariable('quoteResponse','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponseFault" informationType="tns:QuoteResponseFaultType"
|
|
action="respond" faultName="InvalidProductFault">
|
|
<send variable="cdl:getVariable('faultResponse','','')"
|
|
causeException="TerminalFailure"/>
|
|
<receive variable="cdl:getVariable('faultResponse','','')"
|
|
causeException="TerminalFailure"/>
|
|
</exchange>
|
|
<record name="TimeToLive" when="before">
|
|
<description type="documentation">Record duration</description>
|
|
<source expression="quote/timeToLive"/>
|
|
<target variable="cdl:getVariable('quoteDuration','','')"/>
|
|
</record>
|
|
</interaction>
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="conditional" id="conditional"></a>4.1.5 Conditional Workunits</h4><p>Having recorded some information we now want to model the predicate and the activities
|
|
that are dependent on the outcome of the predicate. To do this we use a conditional workunit
|
|
that follows on from the recording example above, and we present this below:
|
|
</p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="conditionalexample" id="conditionalexample"></a>Example: Conditional Example </div><div class="exampleInner"><pre>
|
|
|
|
</pre></div></div><p> In this example what we have done is ask some validation service if the
|
|
buyer is valid. We have used a record to pull out the response and that
|
|
response in the variable "buyerIsValid" is used in the guard for the
|
|
workunit. The equivalent imperative language construct would be something
|
|
akin to: </p><div class="exampleInner"><pre> buyerIsValid = perform buyerValidation If (buyerIsValid)
|
|
perform credit checking </pre></div></div><div class="div3">
|
|
<h4><a name="choices" id="choices"></a>4.1.6 Choices </h4><p> The body of the workunit that we described above we introduced a
|
|
<code>choice</code>. The <code>choice</code> element is used to declare possible
|
|
alternative paths in a choreography. In our example there are only three choices
|
|
that can be made at this point. The quote could timeout, the buyer decides to
|
|
accept the quote or the buyer requests an update to the existing quote. We model
|
|
these as a <code>silentAction</code> for the timeout of the quote – we shall
|
|
change this later on -, as a simple <code>sequence</code> for the buyer
|
|
accepting the quote and as a complex <code>sequence</code> to handle the
|
|
bartering process itself. After adding the basic components the workunit is
|
|
illustrated below: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment11" id="wscdlfragment11"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>
|
|
<choice>
|
|
<sequence>
|
|
<description type="documentation">Accept the quote and place the order</description>
|
|
</sequence>
|
|
<sequence>
|
|
<description type="documentation">Reject the quote and ask for a new quote</description>
|
|
<interaction name="QuoteReelicitation" operation="updateQuote"
|
|
channelVariable="tns:Buyer2SellerC">
|
|
<description type="documentation">Barter based on previous quote</description>
|
|
<participate relationshipType="tns:Buyer2Seller"
|
|
fromRoleTypeRef="tns:BuyerRole" toRoleTypeRef="tns:SellerRole"/>
|
|
<exchange name="QuoteRequest" informationType="tns:QuoteRequestType"
|
|
action="request">
|
|
<description type="documentation">Quote re-request based on amended
|
|
quoteRequest</description>
|
|
<send variable="cdl:getVariable('quoteRequest','','')"/>
|
|
<receive variable="cdl:getVariable('quoteRequest','','')"/>
|
|
</exchange>
|
|
<exchange name="QuoteResponse" informationType="tns:QuoteResponseType"
|
|
action="respond">
|
|
<send variable="cdl:getVariable('quoteResponse','','')"
|
|
recordReference="TimeToLive"/>
|
|
<receive variable="cdl:getVariable('quoteResponse','','')"/>
|
|
</exchange>
|
|
<record name="TimeToLive" when="before">
|
|
<description type="documentation">Record duration</description>
|
|
<source expression="quote/timeToLive"/>
|
|
<target variable="cdl:getVariable('quoteDuration','','')"/>
|
|
</record>
|
|
</interaction>
|
|
</sequence>
|
|
</choice>
|
|
</pre></div></div><p> We shall start to elaborate the <code>choice</code> by defining the complex
|
|
sequence that will control the bartering collaboration. What we shall describe
|
|
are the interactions needed for the bartering process. We start by defining the
|
|
interaction from buyer to seller to update the price, <code>interaction
|
|
name</code>="Buyer updates the Quote - in effect requesting a new price", and
|
|
the exchanges that comprise this interaction. We model this as an interaction
|
|
within a sequence such that the exchanges are the outbound "updateQuote" and the
|
|
inbound "acceptUpdatedQuote". This illustrated below: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment12" id="wscdlfragment12"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre><workunit name="Repeat until bartering has been completed" repeat="barteringDone = false">
|
|
<choice>
|
|
<silentAction roleType="BuyerRoleType">
|
|
<description type="description">Do nothing - let the quote timeout</description>
|
|
</silentAction>
|
|
|
|
<sequence>
|
|
…
|
|
</sequence>
|
|
|
|
<sequence>
|
|
<interaction name="Buyer updates the Quote - in effect requesting a new price"
|
|
operation="quoteUpdate" channelVariable="Buyer2SellerC">
|
|
<description type="documentation">Quot Update</description>
|
|
<participate relationshipType="BuyerSeller"
|
|
fromRole="BuyerRoleType" toRole="SellerRoleType" />
|
|
<exchange name="updateQuote"
|
|
informationType="QuoteUpdateType" action="request">
|
|
</exchange>
|
|
<exchange name="acceptUpdatedQuote"
|
|
informationType="QuoteAcceptType" action="respond">
|
|
<description type="documentation">Accept Updated Quote</description>
|
|
</exchange>
|
|
</interaction>
|
|
</sequence>
|
|
</choice>
|
|
</workunit>
|
|
</pre></div></div><p> The final choice element in this workunit is the element that manages the repeat
|
|
variable "barteringDone". This sequence has two interactions, named "Buyer
|
|
accepts the quote and engages in the act of buying" and "Buyer send channel to
|
|
seller to enable callback behavior". The first describes the interaction between
|
|
buyer and seller to accept the quote – this has an exchange called "Accept
|
|
Quote" - and thus place an order. The second describes the additional
|
|
information passed to the seller by the buyer – this has an exchange called
|
|
"sendChannel" - so that a third party, in our case the shipper, may send back
|
|
delivery details to the buyer without knowing the buyer before hand. To effect
|
|
the exchange we need to make sure that the channel variable NAME that resides at
|
|
both the buyer and the seller independently of each other is used as the output
|
|
variable at the buyer and the input variable at the seller. To do this we use
|
|
the WS-CDL function that gets a variable at a specified role. This is why we see
|
|
"cdl:getVariable('DeliveryDetailsC','','')" and
|
|
"cdl:getVariable('DeliveryDetailsC','','')" in the exchange. The role is omitted
|
|
because it can be inferred through the channel used for interaction. The final
|
|
part of the sequence is to change the value in the variable, "barteringDone", to
|
|
"true"so that the workunit repeat condition evaluates to false and the workunit
|
|
terminates. To do this we use an assign element and indicate the actual variable
|
|
and where it resides my using the "cdl:getVariable('barteringDone','','')"
|
|
WS-CDL function. This part of the workunit and choice is illustrated below: </p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment13" id="wscdlfragment13"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre><workunit name="Repeat until bartering has been completed" repeat="barteringDone = false">
|
|
<choice>
|
|
<silentAction roleType="BuyerRoleType">
|
|
<description type="description">Do nothing - let the quote timeout</description>
|
|
</silentAction>
|
|
|
|
<sequence>
|
|
<interaction name="Buyer accepts the quote and engages in the act of buying"
|
|
operation="quoteAccept" channelVariable="Buyer2SellerC">
|
|
<description type="description">Quote Accept</description>
|
|
<participate relationshipType="BuyerSeller"
|
|
fromRole="BuyerRoleType" toRole="SellerRoleType" />
|
|
<exchange name="Accept Quote" informationType="QuoteAcceptType"
|
|
action="request">
|
|
</exchange>
|
|
</interaction>
|
|
<interaction name="Buyer send channel to seller to enable callback behavior"
|
|
operation="sendChannel" channelVariable="Buyer2SellerC">
|
|
<description type="description">Buyer sends channel to pass to shipper</description>
|
|
<participate relationshipType="BuyerSeller"
|
|
fromRole="BuyerRoleType" toRole="SellerRoleType" />
|
|
<exchange name="sendChannel" channelType="2BuyerChannelType" action="request">
|
|
<send variable="cdl:getVariable('DeliveryDetailsC','','')" />
|
|
<receive variable="cdl:getVariable('DeliveryDetailsC','','')" />
|
|
</exchange>
|
|
</interaction>
|
|
|
|
<assign roleType="BuyerRoleType">
|
|
<copy name="copy">
|
|
<source expression="true" />
|
|
<target variable="cdl:getVariable('barteringDone','','')" />
|
|
</copy>
|
|
</assign>
|
|
</sequence>
|
|
|
|
<sequence>
|
|
…
|
|
</sequence>
|
|
</choice>
|
|
</workunit>
|
|
</pre></div></div></div><div class="div3">
|
|
<h4><a name="parallel" id="parallel"></a>4.1.7 Parallelization </h4></div><div class="div3">
|
|
<h4><a name="modularization" id="modularization"></a>4.1.8 Modularization</h4><div class="div4">
|
|
<h5><a name="choreographiesandsubchoreographies" id="choreographiesandsubchoreographies"></a>4.1.8.1 Choreographies and sub-choreographies</h5></div></div><div class="div3">
|
|
<h4><a name="performing" id="performing"></a>4.1.9 Performing a sub choreography </h4></div><div class="div3">
|
|
<h4><a name="channelpassing" id="channelpassing"></a>4.1.10 Channel Passing </h4></div><div class="div3">
|
|
<h4><a name="exchanges" id="exchanges"></a>4.1.11 Exchanges </h4></div></div><div class="div2">
|
|
<h3><a name="intermediate-extra" id="intermediate-extra"></a>4.2 Extending the example</h3><p> We shall the example further by adding some more roles that will cover credit checking,
|
|
and delivery. In the context of this we shall look at how we deal with exceptions and faults
|
|
in WS-CDL and also how we deal with compensation when we need to either proceed or back things
|
|
out. The former is based on what we call exception work units and the latter finalization.
|
|
We shall also explain how silent actions and no action may be used to further document the
|
|
collaborative behavior of our roles.</p><p> We illustrate the example as a set of sequence diagrams that describe the scenarios for
|
|
exception handling, finalization, silent and no actions.</p><div class="div3">
|
|
<h4><a name="exceptionsandfaults" id="exceptionsandfaults"></a>4.2.1 Exceptions and Faults</h4><p> In this section we examine how we use faults in WSDL (both WSDL1.1 and WSDL2.0)
|
|
to drive exceptions in WS-CDL. </p><p> Credit Check returns a fault, which implies credit failure, and this is
|
|
dealt with in an exception block and you raise an exception to interrupt
|
|
the flow of the choreography. The Exception handler returns a message to
|
|
the buyer to let them know that the order has been cancelled.</p><div class="exampleOuter"></div></div><div class="div3">
|
|
<h4><a name="Finalization" id="Finalization"></a>4.2.2 Finalization</h4><p> Supposing the credit checking (which implies debiting the card if ok) and the
|
|
shipping details are done in parallel and are independent. Then we would have
|
|
two finalizers which handle the yes go ahead or the no back out both. Add some
|
|
further details that explain the use case in a real world situation in which
|
|
separate legs of a trade are executed in parallel (e.g. arbitrage). </p><div class="div4">
|
|
<h5><a name="finalizers" id="finalizers"></a>4.2.2.1 Finalizers and Finalization </h5></div></div><div class="div3">
|
|
<h4><a name="silentactionsandconditions" id="silentactionsandconditions"></a>4.2.3 Silent Actions and Conditions</h4><p> Add a silent action at the credit checker to show that something happens here to
|
|
do the actual credit checking that is invisible. Silent variable conditional -
|
|
silent conditional for sending back credit ok or credit fault. </p></div><div class="div3">
|
|
<h4><a name="noactions" id="noactions"></a>4.2.4 NoActions</h4></div><div class="div3">
|
|
<h4><a name="completeexample2" id="completeexample2"></a>4.2.5 Complete Example</h4><p>The rest of the example is all about describing the interactions and choices
|
|
needed by the seller to check credit and if successful to request delivery. This
|
|
is listed in schematic form below. We have not filled all of the details because
|
|
it is illustrated fully in Appendix I.</p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment14" id="wscdlfragment14"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre><interaction name="Seller check credit with CreditChecker"
|
|
operation="creditCheck" channelVariable="Seller2CreditChkC">
|
|
…
|
|
</interaction>
|
|
<choice>
|
|
<interaction name="Credit Checker fails credit check"
|
|
operation="creditFailed" channelVariable="Seller2CreditChkC">
|
|
…
|
|
</interaction>
|
|
<sequence>
|
|
<interaction name="Credit Checker passes credit"
|
|
operation="creditOk" channelVariable="Seller2CreditChkC">
|
|
…?
|
|
</interaction>
|
|
<interaction name="Seller requests delivery details"
|
|
operation="requestShipping" channelVariable="Seller2ShipperC">
|
|
…
|
|
</interaction>
|
|
<interaction name="Shipper forward channel to shipper"
|
|
operation="sendChannel" channelVariable="Seller2ShipperC">
|
|
<description type="description">Pass channel from buyer to shipper</description>
|
|
<participate relationshipType="SellerShipper"
|
|
fromRole="SellerRoleType" toRole="ShipperRoleType" />
|
|
<exchange name="forwardChannel" channelType="2BuyerChannelType" action="request">
|
|
<send variable="cdl:getVariable('DeliveryDetailsC','','')" />
|
|
<receive variable="cdl:getVariable('DeliveryDetailsC','','')" />
|
|
</exchange>
|
|
</interaction>
|
|
<interaction name="Shipper sends delivery details to buyer"
|
|
operation="deliveryDetails" channelVariable="DeliveryDetailsC">
|
|
<description type="description">Pass back shipping details to the buyer</description>
|
|
<participate relationshipType="ShipperBuyer"
|
|
fromRole="ShipperRoleType" toRole="BuyerRoleType" />
|
|
<exchange name="sendDeliveryDetails"
|
|
informationType="DeliveryDetailsType" action="request">
|
|
</exchange>
|
|
</interaction>
|
|
</sequence>
|
|
</choice>
|
|
</sequence>
|
|
</choreography>
|
|
</pre></div></div><p>In this outline we can see a choice made after a credit check has been done. If
|
|
the credit check fails we do very little. If it succeeds we "requestShipping"
|
|
from seller to shipper and pass the buyer details that we got previously onto
|
|
the shipper. The shipper then responds back to the buyer using the necessary
|
|
channel details that were passed ("DeliveryDetailsC") to affect the
|
|
interaction.</p></div></div></div><div class="div1">
|
|
<h2><a name="advanced" id="advanced"></a>5 Advanced Topics</h2><div class="div2">
|
|
<h3><a name="dependentworkunits" id="dependentworkunits"></a>5.1 Dependent Workunits</h3><p>We can change our example and make it somewhat more interesting by having two
|
|
workunits. The first is unchanged and the second incorporates all of the
|
|
previous choreography notation that follows the completion of the first
|
|
workunit. What we shall do to model this is to make the second workunit
|
|
dependent on the availability and value of 'barteringDone'. To do this we shall
|
|
introduce a guard condition into our workunit and make a blocking workunit. Such
|
|
dependent workunits represent a structural dependence that might exist in real
|
|
systems and so provides the choreography designer with an elegant way of
|
|
expressing the dependencies directly as opposed to adding further conditional
|
|
and state to achieve much the same thing. </p><p>Our workunit sketch looks like the following:</p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment15" id="wscdlfragment15"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre><parallel>
|
|
<workunit name="Repeat until bartering has been completed" repeat="barteringDone = false">
|
|
…
|
|
</workunit>
|
|
|
|
<workunit name="Process Order" guard="barteringDone = true" blocking="true">
|
|
…
|
|
</workunit>
|
|
</parallel>
|
|
</pre></div></div><p>In this example the guard condition is "barteringDone = true" and the
|
|
<code>blocking</code> is set to "true". This second workunit waits until
|
|
"barteringDone" is available and is set to true before enacting whatever is
|
|
described inside of it. We place the two workunits inside a
|
|
<code>parallel</code> construct which means that the two workunits operate
|
|
concurrently. The second being dependent on the first waits until its
|
|
preconditions are met before proceeding.</p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment16" id="wscdlfragment16"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre> <parallel>
|
|
<workunit name="Repeat until bartering has been completed" repeat="barteringDone = false">
|
|
…
|
|
</workunit>
|
|
|
|
<workunit name="Process Order" guard="barteringDone = true" blocking="true">
|
|
…
|
|
</workunit>
|
|
</parallel>
|
|
</pre></div></div><p>We can use the same data-driven collaboration technique to rewrite how we handle
|
|
the credit checking response, by introducing another variable, 'creditRatingOk',
|
|
at the seller role, that records, as a Boolean, the response from the credit
|
|
check. The second, blocking, workunit is made dependent on the outcome of the
|
|
first by using a guard that looks a little like the following:</p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment17" id="wscdlfragment17"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre> <parallel>
|
|
<workunit name="Check Credit Rating">
|
|
<sequence>
|
|
<interaction name="Seller check credit with CreditChecker"
|
|
operation="creditCheck" channelVariable="Seller2CreditChkC">
|
|
<description type="description">
|
|
Check the credit for this buyer with the credit check agency
|
|
</description>
|
|
<participate relationshipType="SellerCreditCheck"
|
|
fromRole="SellerRoleType" toRole="CreditCheckerRoleType" />
|
|
<exchange name="checkCredit" informationType="CreditCheckType" action="request">
|
|
</exchange>
|
|
</interaction>
|
|
<choice>
|
|
<sequence>
|
|
<interaction name="Credit Checker fails credit check"
|
|
operation="creditFailed" channelVariable="Seller2CreditChkC">
|
|
<description type="description">
|
|
Credit response from the credit checking agency
|
|
</description>
|
|
<participate relationshipType="SellerCreditCheck"
|
|
fromRole="SellerRoleType" toRole="CreditCheckerRoleType" />
|
|
<exchange name="creditCheckFails"
|
|
informationType="CreditRejectType" action="respond">
|
|
</exchange>
|
|
</interaction>
|
|
<assign roleType="SellerRoleType">
|
|
<copy name="copy">
|
|
<source expression="false" />
|
|
<target variable="cdl:getVariable('creditRatingOk','','')" />
|
|
</copy>
|
|
</assign>
|
|
</sequence>
|
|
|
|
<sequence>
|
|
<interaction name="Credit Checker passes credit"
|
|
operation="creditOk" channelVariable="Seller2CreditChkC">
|
|
<description type="description">
|
|
Credit response from the credit checking agency
|
|
</description>
|
|
<participate relationshipType="SellerCreditCheck" fromRole="BuyerRoleType"
|
|
toRole="CreditCheckerRoleType" />
|
|
<exchange name="creditCheckPasses"
|
|
informationType="CreditAcceptType" action="respond">
|
|
</exchange>
|
|
</interaction>
|
|
<assign roleType="SellerRoleType">
|
|
<copy name="copy">
|
|
<source expression="true" />
|
|
<target variable="cdl:getVariable('creditRatingOk','','')" />
|
|
</copy>
|
|
</assign>
|
|
</sequence>
|
|
</choice>
|
|
</sequence>
|
|
</workunit>
|
|
|
|
|
|
<workunit name="Request Delivery" guard="creditRatingOk = true" blocking="true">
|
|
…
|
|
</workunit>
|
|
</parallel>
|
|
</pre></div></div><p>The operational semantic of the workunit in WS-CDL can be described as follows:</p><div class="exampleOuter">
|
|
<div class="exampleHeader"><a name="wscdlfragment18" id="wscdlfragment18"></a>Example: WS-CDL Fragment</div><div class="exampleInner"><pre>Blocking
|
|
|
|
Workunit (G) (R) (B is True)
|
|
Body
|
|
|
|
Where
|
|
G => guard condition
|
|
R => repeat condition
|
|
B => blocking attribute
|
|
Body => CDL activities within the work unit
|
|
|
|
A typical order of evaluation is as follows:
|
|
|
|
(G) Body (R G) Body (R G) Body
|
|
|
|
With respect to a G then the G is only evaluated when the variables are available and evaluate to True and otherwise we wait at the guard condition. Thus the Body after the first G only gets executed when G is True. Or put another way Body is primed ready for action and then is executed when G evaluates to True.
|
|
|
|
IF G is unavailable or evaluates to False THEN it equates to:
|
|
|
|
when (G) {
|
|
Body
|
|
} until (!R)
|
|
|
|
IF G is always True THEN it equates to:
|
|
|
|
repeat {
|
|
Body
|
|
} until (!R)
|
|
|
|
IF R is always False THEN it equates to:
|
|
|
|
when (G) {
|
|
Body
|
|
}
|
|
|
|
|
|
</pre></div></div></div><div class="div2">
|
|
<h3><a name="concurrentperforms" id="concurrentperforms"></a>5.2 Concurrent Performs</h3><p> This is the unbounded number of sellers in an RFQ process that may use
|
|
hasDurationPassed in a join condition in one scenario and may use first past the
|
|
post in another join condition </p><div class="div3">
|
|
<h4><a name="managingjoinconditions" id="managingjoinconditions"></a>5.2.1 Managing join conditions</h4><p>NOTE: In this section make sure we handle join conditions and arrays and
|
|
lists.</p></div></div><div class="div2">
|
|
<h3><a name="isolationlevels" id="isolationlevels"></a>5.3 Isolation Levels </h3><p> In the RFQ process with multiple sellers the multiple concurrent sub-choreographies at
|
|
the buyer await responses from the sellers. When a response comes back the buyer
|
|
in the sub choreography updates an isolated variable if it's value that it has is
|
|
better than the value it can see for that variable. This ensures that the
|
|
sub-choreographies are synchronised in their updating of the new isolated variable so
|
|
that the correct value is arrived at. Note: This raises a pitfall and
|
|
implementation consideration about when isolated variables get locked. If you
|
|
lock too soon you may not get the correct or desired behavior. </p></div><div class="div2">
|
|
<h3><a name="advancedchannels" id="advancedchannels"></a>5.4 Advanced Channels</h3><p> Once - The passed channel to the shipper is usage once so that it adds to
|
|
privacy and ensures sound behavioral typing (aka this cannot participate in
|
|
deadlock and livelock) Shared/Distinct and passing using "new" to be done Note:
|
|
The "new" could be used to ensure that a fresh channel is passed. This would be
|
|
used with the once in the advanced example and used as per normal in the normal
|
|
example. Seller should not have "new" because the seller has received a channel
|
|
from the buyer to pass to the shipper. </p><div class="div3">
|
|
<h4><a name="usage" id="usage"></a>5.4.1 Usage</h4></div><div class="div3">
|
|
<h4><a name="channelpassingmodes" id="channelpassingmodes"></a>5.4.2 Channel Passing Modes</h4></div></div><div class="div2">
|
|
<h3><a name="id2272704" id="id2272704"></a>5.5 Pitfalls</h3><div class="div3">
|
|
<h4><a name="distributedchoice" id="distributedchoice"></a>5.5.1 Distributed choice and race conditions</h4><p>NOTE: Description of the distributed choice problem</p></div></div><div class="div2">
|
|
<h3><a name="alignmentandcoordination" id="alignmentandcoordination"></a>5.6 Alignment and Coordination </h3><p> Coordination - Credit Check fails. Seller throws exception so goes into an
|
|
exception state. And because the choreography is coordinated the buyer also goes
|
|
into its exception state because it was all coordinated. This of course involves
|
|
hidden communication so that buyer and seller know about each other state with respect to
|
|
exceptions. Alignment will be done after we have sorted out the rest </p></div></div><div class="div1">
|
|
<h2><a name="implementation" id="implementation"></a>6 Implementation Considerations</h2><div class="div2">
|
|
<h3><a name="endpointprojections" id="endpointprojections"></a>6.1 End Point Projections</h3><div class="div3">
|
|
<h4><a name="Java" id="Java"></a>6.1.1 Java</h4></div><div class="div3">
|
|
<h4><a name="WS-BPEL" id="WS-BPEL"></a>6.1.2 WS-BPEL </h4></div><div class="div3">
|
|
<h4><a name="monitoring" id="monitoring"></a>6.1.3 Runtime Monitoring </h4></div><div class="div3">
|
|
<h4><a name="wsdl1.1" id="wsdl1.1"></a>6.1.4 WSDL1.1 </h4></div><div class="div3">
|
|
<h4><a name="WSDL2.0" id="WSDL2.0"></a>6.1.5 WSDL2.0 </h4></div></div><div class="div2">
|
|
<h3><a name="wdaddressing" id="wdaddressing"></a>6.2 WS-Addressing </h3><div class="div3">
|
|
<h4><a name="channelrep" id="channelrep"></a>6.2.1 Channel Representation </h4></div></div></div></div></body></html>
|