C# in Frends
How to use C# programming in Frends.
Core feature of Frends is to include C# programming features within the BPMN 2.0 notation. C# can also be used to develop custom Tasks for Frends, allowing you to extend the functionality available in Processes.
Supported .NET & C# versions
Main supported version of .NET is 8.0 in the latest Frends versions. Alongside .NET 8.0 Frends supports using C# language features from C# version 12.
Some older Frends versions allow targeting .NET 6.0 instead of 8.0, making the latest supported C# version to be 10.
Frends also supports targeting .NET Framework 4.7.1 for legacy support, as well as .NET Standard 2.0 for migrating from legacy Frends Agent to the newer cross platform Agent. When targeting the older frameworks, supported C# language feature version is 7.3.
Using C#
C# can be used in different shapes for more dynamic functionality, and to create functionality not directly available in Frends.
While some fields and places allow using C# quite extensively, a best practice is to keep it short and simple and not overuse C#. For Code Tasks a good reminder is to perform one action per shape, while for fields expecting a single expression of C# it's a good idea to limit the amount of code to what could be considered a "one-liner" that is also easy to read.
When using Handlebars syntax to embed C# into a text literal value, the best practice is to also avoid too long expressions and preferably perform any initial calculation and formatting before embedding the value into the text using C# and Handlebars.
A single expression of C# is a literal value such as string or integer, single or chained calculation, method call or accessing a field of object, or a creation of object or a lambda expression.
Assignment usually is not counted as an expression, because the expression should return or resolve in a value. This is allowed in fields where C# expression can be provided, but it does not store the resolved value for further use, such as Assign Variable shape or Code Task, if assign variable option is turned off.
Expression parameter fields
Majority of Tasks and shapes contain input fields that can be set to be of type Expression. This allows directly inputting a single line or expression of C# code that resolves into a value for the field when executed.
When using Expression for a field, make sure the type of value returned by the C# code matches the expected data type for the field. Text and number fields expect String and Integer, while selector fields may require a specific enum or class.

Handlebars inside Text parameter fields
All input fields that expect a textual value will also accept Handlebars syntax to be used within the text to include C# code. The code included will be resolved at runtime to replace the Handlebars with the resolved value. Field types Text, JSON, XML and SQL are all considered to be text type and can accept Handlebars.
Using Handlebars can be cleaner if there are multiple values being embedded into a string literal, or if the string literal is longer than one of few values being added to it, than performing the same task in C# code.
Handlebars also have an implicit ToString()
call, converting any value the C# provides into a string. This is why it's also common to use Handlebars syntax to insert a single value as C# expression to an input field, rather than changing the field type to an expression.

Environment Variables in Trigger parameters
Environment Variables can be used in Trigger parameters for fields which accept text input, such as File Trigger's File filter or Conditional Trigger's Subprocess parameters. The format in which those are input varies slightly from the usual expressions within a Process.
While typically a field is chosen to be either Expression or Text, which determines if the expected input value is in C# code or plain text format, Trigger parameter fields will always be considered as Text fields, with a caveat. Environment Variables can be input directly into Trigger parameters using the #env reference values, without using Handlebars ({{}}) syntax. Environment Variable references are translated directly into their value, while all other text content will not be evaluated.
For example this is a valid input for a File Trigger filter:
FilePrefix#env.ExampleGroup.FileName #env.ExampleGroup.FileSuffix
And would produce a value such as "FilePrefixFileName .csv", if content of the Environment Variables were "FileName" and ".csv". Note that the space between or after Environment Variable is required to separate the name of the Environment Variable from other input.
If the input value contains Handlebar characters or other C# code, those will not be evaluated, like in this example:
{{#env.ExampleGroup.FilePrefix}}_{{DateTime.Now.ToString()}}.csv
The result for that input in a Trigger parameter would result in something like the following, not evaluating the Handlebars or the included C# code, except for the Environment Variable reference value:
{{FileToSearchFor}}_{{DateTime.Now.ToString()}}.csv
Manual Trigger parameters for a Process are the only exception to this. Parameter input fields for a Manual Trigger do not evaluate any reference values or C# code.
Expression for Decision shapes
Exclusive Decision and each branch of Inclusive Decision expect an expression to be provided that results in a boolean value. The expression fields for these are locked to requiring C# expression to be given instead of textual or Handlebars input. Validation will also be performed on these fields to make sure the expression results in a boolean value.
For Exclusive Decision if the expression results to a True value, the Process flow will follow the "Yes" branch. Any other result, essentially when the expression results in a False value, the Process flow will go in the branch set as Default, which is the "No" branch by default. Default branch can be changed from the options for the branches.
For Inclusive Decision, any branch that has an expression that results in a True value will be executed. Inclusive Decision can also have a default branch set, which will be executed if no other branch was. If a branch's value results in False, it will not be executed at this time.

Expression for Assign Variable shape
Assign Variable shape's expression field is by default an expression input field, where a single C# expression can be provided and its value is assigned to the variable specified in the shape.

It's possible to change the shape's input field type into textual format, allowing the input of text that is enhanced by Handlebars. This can be useful if the variable's content should be a string.
Alternatively, Assign Variable shape can be used without assigning the value to a variable, allowing for execution of C# expression that does not result in a value. This can be used to change contents of an object in place, or also to perform an assignment operation that stores a value to an existing variable. When used in this format, it is actually against the validation rules for the expression to result in a value.

Code Task
Unlike most other methods of including C# code in Processes, Code Task is specifically made to include more than a single expression of C#. Instead, a scope is provided for the developer to write as much code as is necessary, while keeping the idea of "single action per shape" in mind. It's not recommended to write the whole Process into a single Code Task, because debugging and visualization will not be as easy as when the steps are split to separate shapes.
In addition to writing essentially a single method or procedure that will be executed during the Process, additional functions can also be included to help with the code writing and execution. Unless returned as lambda function, these helper functions will not be usable outside the Code Task.

When using the Code Task to assign a value to variable, the code contents must use return statement to save the value to a variable. If variable assignment is not enabled, the code should not return a value, but instead act as a void function. Assignment to existing variables using #var references is possible, but for general readability, this is not recommended and the assign variable option should be used instead.

Note that the Code Task does not support inclusion of additional libraries or namespaces that are not yet loaded in Frends. This means that including namespaces or libraries through using
keyword or by directly using the external library's FQDN class name is not possible in Code Task.
Using
keyword is possible to use when it is used to manage resources, such as file streams, and you want to make sure they are closed when the scope exits. Using using
keyword for including namespaces is not possible.
Custom Tasks
Custom Tasks are written as C# classes and can include additional libraries and namespaces otherwise not available in Frends Process Editor. Custom Tasks should be created and used when there is no ready-made Task for your use case, and creating the functionality in C# requires additional libraries that Frends does not include by default, making it impossible to implement the functionality in a Code Task.
Namespaces available for use
Frends Process Editor has a limited number of libraries and namespaces available for use.
Assets in following namespaces are directly available in Frends C# expressions without need to write the complete namespace:
System
System.Net
System.Security
System.Xml
System.Xml.Linq
System.Data
System.Threading.Tasks
System.Dynamic
System.Linq
System.Collections.Generic
System.Reflection
Newtonsoft.Json
Newtonsoft.Json.Linq
In addition, functions from the following namespaces are available to use when complete namespace of the function is written:
Microsoft.CodeAnalysis
Microsoft.CSharp
Finally, all the functions from mscorlib (Multilanguage Standard Object Runtime Library) are also available when complete namespace of the function is written. These include for example:
System.Collections
System.Configuration.Assemblies
System.Diagnostics
System.Diagnostics.SymbolStore
System.Globalization
System.IO
System.IO.IsolatedStorage
System.Reflection.Emit
System.Resources
System.Runtime.CompilerServices
System.Runtime.InteropServices
System.Runtime.InteropServices.Expando
System.Runtime.Serialization
System.Runtime.Serialization.Formatters
System.Runtime.Serialization.Formatters.Binary
System.Security.Cryptography
System.Security.Cryptography.X509Certificates
System.Security.Permissions
System.Security.Policy
System.Security.Principal
System.Text
System.Threading
Microsoft.Win32Â
Custom Tasks may use other libraries and namespaces as well, these limitations apply only to the C# code written in Frends Process Editor.
Last updated
Was this helpful?