In WF4 esistono due tipologie di correlazione:
- Content-Based is WF4 (nuova), dove l’identificatore dell’istanza (id di correalazione) è passato come parte del messaggio;
- Context-Based Correlation, dove l’id di correlazione è parte del binding;
Content-Based is WF4
Supponiamo di avere due Activity Service nel nostro WF, il primo: GetData() ed il secondo: Add().
La sequenza di chiamate prevede l’invocazione iniziale di GetData() che ha la proprietà CanCreateInstance = true. L’istanza è quendi creata e ci si attende di poter chiamare il service Add() su di essa.
Per fare ciò dobbiamo operare sia attraverso il Designer che direttamente dal codice.
Designer
Il primo passo è quello di creare una Variabile di tipo “CorrelationHandle”.
Selezionare, quindi, il tab Variables (in basso a sinistra del designer), specificarne il nome (in questo caso “correlator”) e settare il tipo a CorrelationHandle.
Se si clicca sull’Activity Recive della primo service (GetData()) nella finestra delle proprietà è possibile vedere I seguenti attributi:
- Correlates On
- Correlates with
- Correlation Initializes
Prima di tutto bisogna inizializzare il correlation handle. Selezionando CorrelationInitializers, sempre sul primo Recive, si aprirà una finestra simile alla seuguente:
Il primo _handle è impostato automaticamente dalla coppia Receive/SendResponse e serve, appunto, a legare le due Activity. Creiamo un nuovo handler (“correlator”), selezioniamo “Query Correlation Initializer” ed impostiamo l’xpath relativo al parametro del messaggio che vogliamo utilizzare per effettuare la correlazione:
Nel caso in figura scegliamo OrderID, parte del messaggio OrderRequest. Accertarsi sempre che la proprietà “CanCreateInstance” della Recive sia settata a TRUE.
Selezioniamo la Recive successive (Add())
La proprietà CanCreateInstance, questa volta, va settata a FALSE perchè vogliamo usare lo stesso workflow istanziato dal primo servizio. Scegliamo, tra le proprietà, CorrelatesWith e settiamo il valore indicato la variabile di correlazione precedentemente create “correlator”.
Ora bisogna specificare l’elemento su cui effettuare la correlazione.
Selezioniamo CorrelatesOn e selezioniamo l’elemento del messaggio che verrà confrontato con quello scelto per la correlazione. In figura si è ipotizzato che il messaggio sia di tipo ConfirmationRquest e che contenga l’elemento OrderId.
Non è importate che il nome dell’elemento da confrontare sia uguale, ne che lo sia il mesaggio, l’importante è che uguale sia il loro valore.
Codice
Prima Receive: GetData()
- Creiamo un DataContact con due proprietà
[DataContract]
public class GetValues
{
[DataMember]
public Guid CorrelationId { get; set; }
[DataMember]
public Int32 Value1 { get; set; }
[DataMember]
public Int32 Value2 { get; set; }
}
- Ora settiamo il tipo di messaggio all’interno della Recive legata al servizio GetValues (la prima). Settiamo CanCreateInstance a TRUE.
Seconda Receive: Add()
- Creiamo un DataContact per chiamare la Add()
[DataContract]
public class Add
{
[DataMember]
public Guid CorrelationId { get; set; }
}
- Definiamo il tipo di messaggio della seconda Recive, Add, sul datacontract appena creato. Inoltre settiamo CanCreateInstance a FALSE.
Inovochiamo il Workflow
Proxyclient client = new Proxyclient();
Guid correlationId = Guid.NewGuid();
GetValues startData = new GetValues();
startData.CorrelationId = correlationId;
startData.Value1 = 24;
startData.Value2 = 54;
bool? result = client.GetData(startData);
Add calladd = new Add();
calladd.CorrelationId = correlationId;
bool? result = client.Add(calladd);