16.05.2016

Development in Dynamics NAV 2016: Events

Events are one of the biggest changes in the application structure since the release of Microsoft Dynamics NAV 2013. They allow to seperate the customized functionality from business logic of the application and leave the standard Dynamics NAV functionality intact. The use of this feature makes the update process of Microsoft Dynamics NAV much easier and faster.
Events look very similar to RSS feeds on the web, where the author of the text has published a message in the RSS feed and readers of the feed can receive a message about the emergence of new text, then retrieve the text and read it. Person who publishes the text can only be one, while readers of the published text can be many.
Event in NAV is a kind of declaration of new instance of a given situation or change in the existing situation in NAV. By analogy to the rss feed, in NAV events we also have two sides, on one side is Publisher (publishing event) and on the other side are Subscribers (subscribing events). Any object like Table, Page, Codedunit can be publisher of NAV event. While only function in
Codeunit can be subscriber of the event.
In Microsoft Dynamics NAV we can select the following type of events: Business Events, Integration Events, Global Events and Trigger Events.
Integration and Business Events must be declared and published by changing the application code.
At the moment between Business and Integration Events is only the conventional boundary, because they are created and handled in the same way. In accordance with the Microsoft guidelines Events declared as Business may not change over time, so once implemented must remain unchanged in the next version of the application. This type of events was reserved for vendors which provide vertical solutions. During normal development you should use Integration Events.

Global Events are predefined system events and are placed in Codeunit 1 ApplicationManagement. Codeunit 1 contains many triggers of global functions like CompanyOpen, CompanyClose etc. For each such function Codeunit 1 contains one or two Global Events named Before and After. For example, OnCompanyClose function will have two Global Events OnBeforeCompanyClose and OnAfterCompanyClose.

Trigger Events are system events and you cannot change them. They are placed in Tables and Pages.
Events in Table:

Events in Page:

In the example, we insert External Document No. field value from Sales Shipment Header table to Description 2 field in sales invoice line. The assignment is to take place when you create invoice lines using Get Shipment function.

In the Table 111 Sales Shipment Line will be declared Integration Event. Event should be initiated after invoice line insertion in InsertInvLineFromShptLine function. InsertInvLineFromShptLine function is run during getting shipment lines to invoice.
You have to create new function and set Events property to Publisher.

By default, NAV Development Environment will set EventType property as Business, so you have to change the property to Integration. At this point it should be mentioned that function which publishes the event must be declared as local (In Microsoft Dynamics NAV 2016 all new functions are declared as local, by default), to be sure that any other object will not trigger the event. Setting the IncludeSender property to Yes (by default No) enables you to call global functions in the object that contains the event publisher function from event subscriber functions that subscribe to the published event. When you set the GlobalVarAccess property to Yes, event subscriber functions that subscribe to an event can call the global variable parameters in the object that is specified by the EventPublisherObject Property, which contains the event publisher function that declares the event. With GlobalVarAccess property you have to be very careful, because when you change global variable in event publisher object (for example changing type of variable from Code to Text or changing the name of global variable), you disconnect event subscriber function from published event. In a word: Event subscriber function will no longer be notified of event occurrence and functionality placed in event subscriber function will not run.
In event publisher function we don’t have any possibility to place C/AL code besides comments. If you try to compile object with event publisher function which have C/AL code inside, compiler will stop and throw an error.

Another thing is fuctions naming. The name of our event publisher function is OnAfterInsertInvLineFromShptLine. Name of the function should clearly describe place of function anchor. In our example event publisher function anchor place is sales invoice line insertion, therefore name of event publisher function contains the expression InsertInvLineFromShptLine. Prefix OnAfter means, that anchor will occur after sales invoice line insertion. Before setting the anchor you have to set parameters in event publisher function, which you would like to pass to event subscriber function. In the example, we pass Sales Line table, which is passed as parameter in InsertInvLineFromShptLine function.

The anchor is made by calling event publisher function after sales invoice line insertion.

The next step is creation of event subscriber function. As was mentioned earlier event subscriber function can only be placed in codeunit. For this purpose we will create new Codeunit 50000 and name it EventSubscribers.

In the codeunit we create function named AddExtDocNoToSalesInvLineOnGetSalesShipment.

In the function properties we set Event property to Subscriber.

In EventPublisherObject property we select object, which contains the event.

In EventFunction property we select event publisher function.

The whole declaration of event subscriber function looks as follows:

The next step is to add some functionality to event subscriber function. The functionality will assign External Document No. value to Description 2 field in Sales Invoice Line.

Sales Shipment Header table was declared as local variable in this function. In the first line of code Sales Shipment Header is got based on Document No. from Sales Shipment Line. In the second line of code External Document No. from Sales Shipment Header is assigned to Description 2 field. In the third line of code is modification of invoice line.
Now you can test the functionality.

  1. Create Sales Order with items in order lines.
  2. Fill External Document No. in sales order header.

  1. Post shipment from sales order.
  2. Create sales invoice in Sales Invoice page.
  3. Get shipment lines to invoice and check if External Document No. was assigned to Description 2 in every invoice line.