Runtime:Debugging

From FlexRule Wiki
Jump to: navigation, search

Debugging refers to a capability that allows the examination of internal states on a running logic during execution while you are attaching the process to a debugger (e.g., running your application in Visual Studio).

Break Points

By putting a break point in a specific element (line) of your logic, when execution reaches that specific element, it pauses and allows the examination of values in the debugger. When any of the Rule commands (Except Inference) is used to model logic, you can add a debug parameter to the element as a break point.

debug = "true"

Watching Expression

If Visual Studio is used and you run your rule inside it, when execution pauses by reaching a break point you can add the following expression to the watch window in order to explore the internals of the execution:

global::FlexRule.Diagnostics.Debugger.Current

This would provide the following information:

  1. /// <summary>
  2. /// Information on the current element that has debug="true" parameter
  3. /// </summary>
  4. public interface ICurrentDebuggingState
  5. {
  6.     /// <summary>
  7.     /// The current element that is about to run
  8.     /// </summary>
  9.     ActiveElement ActiveElement { get; }
  10.  
  11.     /// <summary>
  12.     /// The current logic that is running
  13.     /// </summary>
  14.     IActiveElementEngine Engine { get; }
  15.  
  16.     /// <summary>
  17.     /// The current execution context
  18.     /// </summary>
  19.     IActiveElementExecutionContext Context { get; }
  20.  
  21.     /// <summary>
  22.     /// The current parameters values
  23.     /// </summary>
  24.     IDictionary<string, object> Values { get; }
  25. }

Decision Table

To enable debugging in a Decision Table, the debug parameter (attribute) must be added to the Data element.

Example

For example, in the the sample application called Airline Discount Program which comes with the Runtime installer, we added debug="true" to its validation logic:

  1. <Validation name="input check">
  2.   <Declaration>
  3.     <Define name="input" direction="in"/>
  4.   </Declaration>
  5.   <Logic name="main">
  6.     <And processAll="true" debug="true">
  7.       <Null negate="true" value="input.Birthday" message="Birthday cannot be null or empty"/>
  8.       <Null negate="true" value="input.Departure" message="Departure cannot be null or empty"/>
  9.       <Null negate="true" value="input.Return" message="Return cannot be null or empty"/>
  10.       <Or negate="true" message="Destination cannot be null or empty">
  11.         <Null value="input.Destination" />
  12.         <Empty value="input.Destination" />
  13.       </Or>
  14.       <Check value="input.Return gt input.Departure" message="Retrun must happen after your Departure date"/>
  15.       <And message="Return and Departure date must be after Birthday">
  16.         <Check value="input.Departure gt input.Birthday"/>
  17.         <Check value="input.Return gt input.Birthday"/>
  18.       </And>
  19.     </And>
  20.   </Logic>
  21. </Validation>

When you run the application, once execution reaches the line that is running the validation logic inside application's controller, it calls to the engine and the validation logic gets executed:

Debugging-Controller.png

You can add the expression to the watch window, and you will be able to check what is happening inside your rules as shown below:

Debugging.png

Position in Source

While debugging or when an exception happens (ActiveElementException) the source information below can help you to locate the position back to the actual source:

  1. LineNumber
  2. LinePosition
  3. SourceLine

As you can see SourceInfo under the ActiveElement's Model property provides the exact line and position (location (6,6) which matches the above XML line number) that validation logic is about to run.

In some complex scenarios, when rules are transforming into other types of logic at runtime for execution, the SourceLine property refers back to the original source of the rule. For example, when a Decision Table is transformed to validation logic for execution, the source will have the Data information line. When an exception (ActiveElementException) occurs, the ErrorLine property on the exception object has the corresponding validation logic line but SourceLine still has the original line from the Decision Table.

Exception Handling

When an error occurs during the creation of execution plan or execution of rules, ActiveElementException will be thrown. This exception implements the ISourceInfo interface by which you can retrieve the specific information about where and why the exception has happened.

The code below gives you a pattern to use:

  1. try
  2. {
  3.     // code for rule execution goes here
  4.  
  5.     // TODO: Run your rules here
  6. }
  7. catch (ActiveElementException aex)
  8. {
  9.     var info = (ISourceInfo)aex;
  10.     // information on where the problem is 
  11.     // in your rule can be retrieved here
  12.  
  13.     // TODO: do what you need to do...
  14. }

More on Debugging

  1. Introduction to debugging
  2. Debugging using Designer
  3. Debugging using code
  4. Debugging in Visual Studio
  5. Inspection Windows
    1. Parameters window
    2. Watch window
  6. Debugging Workflow

Tutorial