Creating a background task handler in C#

This example shows how to create a custom background task handler to implement specific ways to process standard and custom events.

Before you begin

The following products need to be already installed on your machine:
  • Microsoft .NET FrameWork
  • Microsoft Visual Studio

Procedure

  1. Create a Visual Studio Project. In this example, the project is called MyCustomBackgroundTaskLibrary, and its type is Class Library.
  2. Add a reference to a plugin SDK (Trisoft.InfoShare.Plugins.SDK.dll). For example, you can copy the file from \Applications\Common\Trisoft.InfoShare.Plugins.SDK.dll.
    1. Browse to the project, then right-click References, and select Add Reference.
    2. To select the reference you want to add, use the Browse button.
    3. Select Trisoft.InfoShare.Plugins.SDK.dll, then Add.
    4. To be able to view the code documentation of the Trisoft.InfoShare.Plugins.SDK.dll, also copy Trisoft.InfoShare.Plugins.SDK.xml.
  3. Add a reference to a plugin common helper (Trisoft.InfoShare.Plugins.Common.dll). For example, you can copy the file from \Applications\Plugins\Trisoft.InfoShare.Plugins.Common.dll.
    1. Browse to the project, then right-click References, and select Add Reference.
    2. To select the reference you want to add, use the Browse button.
    3. Select Trisoft.InfoShare.Plugins.Common.dll, then Add.
    4. To be able to view the code documentation of the Trisoft.InfoShare.Plugins.Common.dll, also copy Trisoft.InfoShare.Plugins.Common.xml.
  4. Add a reference to the System.ComponentModel.Composition assembly.
  5. Add a reference to the System.Xml assembly.
  6. Create a new MyCustomHandler class.
    • The name of the background task handler corresponds to the value assigned to ExportAttribute, and it needs to be unique.
    • The LogService on IBackgroundTaskHandlerConfiguration manages all log entries as part of the standard log chaining, as configured in NLog.config. If you want to create a separate logging chain, you need to set up a new Logger
    
    using System;
    using System.Collections.Generic;
    using System.ComponentModel.Composition;
    using System.Diagnostics;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    using System.Xml;
    using Trisoft.InfoShare.Plugins.SDK;
    using Trisoft.InfoShare.Plugins.SDK.BackgroundTasks;
    
    namespace MyCustomBackgroundTaskLibrary
    {
        // This attribute is used to make the class discoverable by the background task service.
        [Export("MyCustomHandler", typeof(IBackgroundTaskHandler))]
        [PartCreationPolicy(CreationPolicy.NonShared)]
        /// <summary>
        /// Custom background task handler that will be executed by the background task upon an event it is configured for.
        /// The handler logs the passed even input data into the event monitor with the configured action and description.
        /// </summary>
        public class MyCustomHandler : IBackgroundTaskHandler
        {
            // This variable is used to store the action passed through the parameters.
            private string _action;
            // This variable is used to store the description passed through the parameters.
            private string _description = String.Empty;
            /// <summary>
            /// The background task configuration
            /// </summary>
            private IBackgroundTaskHandlerConfiguration _configuration;
    
            /// <summary>
            /// The name of the event (e.g. "EXPORTFORPUBLICATION", "CREATETRANSLATIONFROMREPORT" etc.).
            /// Will be set by the background task service.
            /// </summary>
            public string EventTypeName
            {
                get;
                set;
            }
    
            /// <summary>
            /// This method will be called by the background task service after the instance of the handler is created.
            /// </summary>
            /// <param name="configuration">Parameters configured in the XML Background Task Settings.</param>
            public void Initialize(IBackgroundTaskHandlerConfiguration configuration)
            {
                _configuration = configuration;
    
                // Read the value of the required parameter from the background task xml configuration
                if (!_configuration.Parameters.TryGetValue("action", out _action))
                {
                    // If required parameter was not provided, throw (and log) an exception
                    var exception = new InvalidOperationException("action parameter was not provided");
                    _configuration.LogService.ErrorException(String.Format("Background task '{0}' failed", this.EventTypeName), exception);
                    throw exception;
                }
                // Read the value of the optional parameter from the background task xml configuration
                _configuration.Parameters.TryGetValue("description", out _description);
            }
    
            /// <summary>
            /// This method will be called by the background task service to run the handler.
            /// </summary>
            /// <param name="context">The context of the hander execution.</param>
            public void Run(IBackgroundTaskHandlerContext context)
            {
                try
                {
                    // Log the passed event data with the configured action/description
                    context.EventMonitor.AddEventDetail(
                        context.ProgressId, EventLevel.Information, _action, _description, DetailStatus.Success, EventDataType.Xml, context.InputDataStream);
    
                    // Add a message to the logging pipeline
                    _configuration.LogService.Info("Background handler has finished successfully for the event " + this.EventTypeName);
    
                    // Execution is successful, so end the event
                    context.EventMonitor.EndEvent(context.ProgressId, ProgressStatus.Success, 1, 1);
                }
                catch (Exception ex)
                {
                    // Add a message to the logging pipeline
                    _configuration.LogService.ErrorException("Background handler has failed for the event " + this.EventTypeName, ex);
    
                    // Background task service may retry the execution if configured, in that case, you cannot end the event yet
                    if (!context.WillRetryOnException(ex))
                    {
                        // If the retries are not configured, the service has exhausted the retry attempts, you need to end the event
                        context.EventMonitor.EndEvent(context.ProgressId, ProgressStatus.Failed, 1, 1);
                    }
                    throw;
                }
            }
    
            /// <summary>
            /// This method will be called by the plugin engine after all plugins have executed
            /// </summary>
            public void Dispose()
            {
                // In our example we don't need a cleanup
            }
        }
    }
              
  7. Deploy the new background task handler.
  8. Configure the new background task handler.
    
    <handler eventType="INBOXEXPORT">
      <scheduler executeSynchronously="false" />
      <authorization type="authenticationContext" />
      <execution timeout="01:00:00" recoveryGracePeriod="00:10:00" isolationLevel="None" useSingleThreadApartment="false" />
      <activator>
    	<net name="MyCustomHandler">
    	  <parameters>
    		<parameter name="action">My custom plugin</parameter>
    		<parameter name="description">Here attached you can find the event data passed to the handler.</parameter>
    	  </parameters>
    	</net>
      </activator>
      <errorHandler maximumRetries="0" />
    </handler>
              
  9. Restart the BackgroundTask service for the changes to become effective.