none
WWFでのスレッドアクティビティに引数、戻り値を持たせた処理を行いたい場合にエラーが発生します RRS feed

  • 質問

  • お世話になります。
    現在ワークフローファンデーションでフローを製作できるプログラムを作成しております。
    その中でアクティビティを並列で動かしたい要望がございましたので文献を調べたところ
    下記サンプルコードをweb上で拝見しましたので実装しました。
    ですが、このコードを使用して作成されたスレッドアクティビティ上に
    引数(変数)を持っているアクティビティを設定すると初回のフロー実行はできるのですが2回目以降は不定なエラーが発生してしまいます。
    引数(変数)を持っていないアクティビティを設定しても何度実行しても特にエラーは発生しません。
    文献を探しても情報が中々ないようですので困っております。
    もしお詳しい方がみえましたらお助けいただきたく思います。
    何卒よろしくお願いします。

    (やりたいこと)
    ・WWF上にスレッド動作をさせるためのアクティビティを追加したい
    ・このアクティビティは引数を持たせ、また内部で計算させた結果も
    引数に返すことができる処理としたい

    実装しましたサンプルコードを下記します。

    <コード部>
    Imports System.Activities
    Imports System.Activities.Presentation.Metadata
    Imports System.ComponentModel
    Imports System.Threading.Tasks
    Imports Microsoft.VisualBasic.Activities

    Public Class AsyncTaskActivity
    Inherits AsyncCodeActivity
    Implements IRegisterMetadata
    <Browsable(False)>
    Public Property Body As New ActivityAction
    Protected Overrides Function BeginExecute(context As System.Activities.AsyncCodeActivityContext, callback As System.AsyncCallback, state As Object) As System.IAsyncResult
    Dim act = Me.CreateDynamicActivity(context)
    Dim inpArgAndVal = Me.GetArgumentsAndVariables(context)
    Dim asyncTask = task.Factory.StartNew(Function(ignore)
    Return WorkflowInvoker.Invoke(act, inpArgAndVal)
    End Function, state)
    asyncTask.ContinueWith(Sub(t)
    callback(t)
    End Sub)
    Return asyncTask
    End Function
    Protected Overrides Sub EndExecute(context As System.Activities.AsyncCodeActivityContext, result As System.IAsyncResult)
    End Sub
    Private Function GetArgumentsAndVariables(ByVal context As AsyncCodeActivityContext) As IDictionary(Of String, Object)
    Dim result As New Dictionary(Of String, Object)
    For Each wfProp As PropertyDescriptor In context.DataContext.GetProperties
    result.Add(wfProp.Name, wfProp.GetValue(context.DataContext))
    Next
    Return result
    End Function
    Private Function CreateDynamicActivity(ByVal context As AsyncCodeActivityContext) As Activity
    Dim result As New DynamicActivity
    For Each wfProp As PropertyDescriptor In context.DataContext.GetProperties
    Dim dynActProperty As New DynamicActivityProperty With {.Name = wfProp.Name,
    .Type = GetType(InArgument(Of )).MakeGenericType(wfProp.PropertyType)
    }
    dynActProperty.Value = Activator.CreateInstance(dynActProperty.Type)
    result.Properties.Add(dynActProperty)
    Next
    VisualBasic.SetSettings(result, VisualBasic.GetSettings(Me))
    result.Implementation = Function() (Body.Handler)
    Return result
    End Function
    #Region "メタデータ"
    Public Sub Register() Implements System.Activities.Presentation.Metadata.IRegisterMetadata.Register
    Dim metadata As New Core.Presentation.DesignerMetadata 'DLLの参照追加が必要 System.Activities.Core.Presentation.dll
    metadata.register()
    Dim builder As New AttributeTableBuilder
    builder.AddCustomAttributes(GetType(AsyncTaskActivity),
    New DesignerAttribute(GetType(AsyncTaskActivityDesigner))
    )
    MetadataStore.AddAttributeTable(builder.CreateTable)

    End Sub
    #End Region
    End Class

    <WPF部>

    <sap:ActivityDesigner x:Class="AsyncTaskActivityDesigner" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    xmlns:sap="clr-namespace:System.Activities.Presentation;assembly=System.Activities.Presentation" 
    xmlns:sapv="clr-namespace:System.Activities.Presentation.View;assembly=System.Activities.Presentation">
    <sap:WorkflowItemPresenter Margin="7" 
    Item="{Binding Path=ModelItem.Body.Handler, Mode=TwoWay}" 
    HintText="Drop Activity"/> 

    </sap:ActivityDesigner>
    2017年9月22日 4:13