Dynamics AX Blog - sysoperation-framework

These posts are machine-translated.
Currently, only posts are displayed, which contain the tag »sysoperation-framework« Filter entfernen

SysOperation-Framework: Force Batch Processing

If you want to make sure that a function implemented via the SysOperation-framework is always executed via batch processing, you can set the SysOperationExecutionMode to ScheduledBatch (e.g. via the MenuItem of the controller - see here).

If this is a function that requires a user dialog, however, the problem is that the "Batch" tab is displayed by default and, for example, the "Batch" check box is not activated there.

Of course you can activate this checkbox by including a call to parmBatchExecute() in the UIBuilder:

public void build()
{
    super();

    this.controller().batchInfo().parmBatchExecute(this.controller().parmExecutionMode() == SysOperationExecutionMode::ScheduledBatch);
}

 
 
 

SysOperation-Framework: Usage data per MenuItem

Imagine you have a function build using the SysOperation framework that can be called at different places in the system, and you want to make sure that these calls do not share the same usage data.

In such a case you could create two (or more) MenuItems and override the method lastValueDesignName() of the controller as follows. This will store separate usage data for each MenuItem.

protected IdentifierName lastValueDesignName()
{
    IdentifierName ret;

    ret = super();

    if (this.parmArgs() && this.parmArgs().menuItemName())
    {
        ret = this.parmArgs().menuItemName();   
    }

    return ret;
}

 
 
 

Create batch job with multiple tasks by code

The code snippets below show how to create batch jobs using the BatchHeader class.

Examples for a RunBaseBatch construct

static void createBatchWithMultipletasks(Args _args)
{
    BatchHeader batchHeader;
    Tutorial_RunbaseBatch batchTask1, batchTask2, batchTask3;

    //create batch header
    batchHeader = BatchHeader::construct();
    batchHeader.parmCaption("Example of a batch job with multiple tasks");

    //create instances of the classes to use as batch tasks
    batchTask1 = Tutorial_RunbaseBatch::construct();
    batchTask2 = Tutorial_RunbaseBatch::construct();
    batchTask3 = Tutorial_RunbaseBatch::construct();

    //add the batch tasks to the batch header
    batchHeader.addTask(batchTask1);
    batchHeader.addTask(batchTask2);
    batchHeader.addTask(batchTask3);

    //save the batch
    batchHeader.save();
}

 
 
 

SysOperation-Framework: Simplest class construct

The code below is the simplest way to implement a function using the SysOperation framework. Without DataController, Dataprovider and UIBuilder. Only with a service class and a MenuItem.

Service

class TutorialSysOperationSimpleService extends SysOperationServiceBase
{
}

The runService() method is the actual service method. The SysEntryPointAttribute attribute controls that no further authorization checks are necessary.

[SysEntryPointAttribute(false)]
public void runService()
{
    info("Done");
}

 
 
 

SysOperation-Framework: Enable batch processing by default

If you want to activate batch processing by default for a function implemented via the SysOperation framework, you can do this by modifying the UI Builder like in the following example.

public void build()
{
    super();
    
    this.controller().batchInfo().parmBatchExecute(NoYes::Yes);
}

The code activates the checkbox Batch processing in the Batch tab.

Screenshot


 
 
 

SysOperation framework: Pass selected records from a temporary table

In the following scenario, all records of a temporary table are to be passed to a SysOperation construct.

For that we need:

  • In the DataContract, a accessor method (parm-method) that takes a container
  • In the controller, a logic that iterates the records of a calling data source and packs it into a container, and passes it to the service using the above method
  • In the service class we need code, which unpacks and processed the transferred container

 

Controller

class TutorialSysOperationController extends SysOperationServiceController
{
}

 
 
 

SysOperation-Framework: Refresh calling form/formdatasource

Often, a function that has been created based on the SysOperation-framework, is called from a form via a button. Therefore there is the requirement, that the displayed data should be updated in the form after execution.

I like to use the following logic. This assumes that the call of the function is done via a button and thereby the main()-method is triggered.

This refresh is done via a sub-method and could look like this:

private void refreshCallingForm(args _args)
{
    FormRun callerFormRun;
    #Task

    if(_args && _args.caller() && _args.caller() is formRun)
    {
        callerFormRun = _args.caller();
        callerFormRun.task(#taskF5);
    }
}

The call of this method takes place in the mentioned main():

public static void main(Args _args)
{
    TutorialSysOperationController controller;
    SysOperationStartResult sysOperationStartResult;

    controller = new TutorialSysOperationController();
    controller.parmArgs(_args);
    controller.parmExecutionMode(
        SysOperationExecutionMode::Synchronous);

    sysOperationStartResult =
    controller.startOperation();

    controller.refreshCallingForm(_args);
}

Variations of the refreshCallingForm()

Instead of the task()-method of the form, one could also call some methods of the form data source.

Use of ExecuteQuery()

If you use the executeQuery() of the respective FomDataSource, any filters and the data set focus will be lost.

private void refreshCallingForm(args _args)
{
    FormDataSource fds;
    
    if(_args && 
       _args.record() && 
       _args.record().isFormDataSource())
    {
        fds = _args.record().dataSource();
        fds.executeQuery();
    }
}

Use of ReSearch()

private void refreshCallingForm(args _args)
{
    FormDataSource fds;
    
    if(_args && 
       _args.record() && 
       _args.record().isFormDataSource())
    {
        fds = _args.record().dataSource();
        fds.research(true);
    }
}

Use of ReRead()

A reRead() would be conceivable, but in this case only the active record would be updated.

private void refreshCallingForm(args _args)
{
    if(_args && 
       _args.record() && 
       _args.record().isFormDataSource())
    {
        _args.record().reread();
    }
}

 
 
 
Pages 1 2 3 » 

 

 
 
 
Posts of the actual month
September 2019
MoTuWeThFrSaSu
 1
2345678
9101112131415
16171819202122
23242526272829
30 
 
© 2006-2019 Heinz Schweda | Imprint | Contact | German version | Mobile version
In order to provide you with better service, this site uses cookies. By continuing to browse the site, you are agreeing to our use of cookies.