Define different types of Input and Output arguments for custom workflow activity

As a MS Dynamics CRM Developer there are certain situations where you need to pass some of the entity field values as Input arguments to a Custom Workflow activity and some cases you may require to get some of the code execution results as Output arguments from a custom workflow activity.

In order to accomplish this you definitely need to have an idea on the Syntax of the Input and Output arguments for different types of fields.

Here i considered an entity called Patient which is having different types of fields and those are given below
1. Patient Name : String
2. Date Of Birth : Date and Time
3. Hospital : Lookup (to an entity called Hospital)
4. Patient Status : Option Set
5. Hospitalization Required : Two Option Set
6. Patient Age : Whole Number
7. Consultation Fee : Decimal Number
8. Estimated Amount : Floating Point Number
9. Treatment Cost : Currency
10. Patient Id : String

Types of arguments

  1. Input : Entity field value can be passed to Custom workflow activity
  2. Output : Execution result (if any) can be passed as output from Custom workflow activity
  3. Input/Output : It can be used as both Input and Output

The following Custom Workflow Activity code will explains how to declare Input and Output arguments.

using System;
using Microsoft.Xrm.Sdk;
using Microsoft.Xrm.Sdk.Workflow;
using System.Activities;

namespace InputOutputParameters
{
    public class InputOutputParameters : CodeActivity
    {
        //Data Type : String 
        [Input("patientname")]
        [RequiredArgument]
        public InArgument<string> PatientName { get; set; }

        //Data Type : Date and Time
        [Input("dateofbirth")]
        [RequiredArgument]
        public InArgument DateOfBirth { get; set; }

        //Data Type : Lookup
        [Input("hospital")]
        [ReferenceTarget("new_hospital")]
        [RequiredArgument]
        public InArgument Hospital { get; set; }

        //Data Type : Option Set
        [Input("patientstatus")]
        [RequiredArgument]
        [AttributeTarget("new_patient", "statuscode")]
        public InArgument PatientStatus { get; set; }

        //Data Type : Two Option Set
        [Input("hospitalizationrequired")]
        [RequiredArgument]
        public InArgument<bool> HospitalizationRequired { get; set; }

        //Data Type : Whole Number
        [Input("patientage")]
        [RequiredArgument]
        public InArgument<int> PatientAge { get; set; }

        //Data Type : Decimal Number
        [Input("consultationfee")]
        [RequiredArgument]
        public InArgument<decimal> ConsultationFee { get; set; }

        //Data Type : Floating Point Number
        [Input("estimatedamount")]
        [RequiredArgument]
        public InArgument<decimal> EstimatedAmount { get; set; }

        //Data Type : Currency
        [Input("treatmentcost")]
        [RequiredArgument]
        public InArgument TreatmentCost { get; set; }

        //Data Type : String
        [Output("showpatientdetails")]
        public OutArgument<string> ShowPatientDetails { get; set; }


        //Data Type : String (Can be used as Input/Output)
        [Input("patientinput")]
        [Output("patientoutput")]
        [RequiredArgument]
        public InOutArgument<string> PatientInOut { get; set; }


        protected override void Execute(CodeActivityContext context)
        {
            try
            {
                IWorkflowContext workflowContext = context.GetExtension();
                IOrganizationServiceFactory serviceFactory = context.GetExtension();
                IOrganizationService service = serviceFactory.CreateOrganizationService(workflowContext.UserId);
                ITracingService tracingService = context.GetExtension();

                tracingService.Trace("Patient Details using input and output parameters Workflow Started.");
                var patientName = PatientName.Get(context);
                var dateOfBirth = DateOfBirth.Get(context);
                var hospital = Hospital.Get(context)?.Name;
                var patientStatus = PatientStatus.Get(context).Value;
                var hospitalizationRequired = HospitalizationRequired.Get(context);
                var patientAge = PatientAge.Get(context);
                var consultationFee = ConsultationFee.Get(context);
                var estimatedAmount = EstimatedAmount.Get(context);
                var treatmentCost = TreatmentCost.Get(context).Value;
                var patientId = PatientInOut.Get(context);
                tracingService.Trace($"Patient Name : {patientName}, Date Of Birth : {dateOfBirth}, Hospital : {hospital}, Patient Status : {patientStatus}, Hospitalization Required: {hospitalizationRequired}, Patient Age: {patientAge}, Consultation Fee : {consultationFee}, Estimated Amount : {estimatedAmount}, Treatment Cost : {treatmentCost}, Patient ID : {patientId}");
                var patientDetails = $"Patient Name : {patientName}, Date Of Birth : {dateOfBirth}, Hospital : {hospital}, Patient Status : {patientStatus}, Hospitalization Required: {hospitalizationRequired}, Patient Age: {patientAge}, Consultation Fee : {consultationFee}, Estimated Amount : {estimatedAmount}, Treatment Cost : {treatmentCost}, Patient ID : {patientId}";
                PatientInOut.Set(context, PatientInOut.ToString());
                ShowPatientDetails.Set(context, patientDetails);
                tracingService.Trace("Patient Details using input and output parameters Workflow Ended.");
            }
            catch(Exception ex)
            {
                throw new InvalidPluginExecutionException(ex.Message);
            }
        }
    }

 

The below screen shot will show you the representation of the Input arguments once after you successfully build and deploy the above custom workflow code activity.

Input_Output_Parameters

One thought on “Define different types of Input and Output arguments for custom workflow activity

  1. Hi Ravindra,

    Thank you so much for your wonderful and useful blog.

    Could you please check on Lookup, Optionset and Currency fields data getting from context.. it seems it is not working for me.

    It is throwing below error for Lookup field and same way for other fields as well

    “‘object’ does not contain a definition for ‘Name’ and no accessible extension method ‘Name’ accepting a first argument of type ‘object’ could be found (are you missing a using directive or an assembly reference?)”

    Like

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

This site uses Akismet to reduce spam. Learn how your comment data is processed.