Tuesday, 13 March 2018

How to export Data into the CSV File with Cross Company

In this post we will go through the exporting the data into the CSV file using X++.

For this you can use a class or Job,

public static void main(Args _args)
{
   // take the commaio class used for CSV formate
    Commaio                     file;
    container                   line,companies; // to store the data need to exported and company information
    InventTable                 inventTable;
    ItemGroupId                 itemGroupId;
    Name                        itemGroupName;
    ItemName                    itemName;
    InventModelGroupItem        invModGrp;
    str                         invmodeGroupId,filename,strdatetime;
    date                        currentDate = today();

    str                         product_class,product_class_desc,master_product,master_product_desc,product_name;
    str                         product_name_desc,product_desc,product_id,search_name,hazard,pricing_strategy,packaging_group;
    str                         weight,net_weight,purchase_stopped,sales_stopped,inventory_stopped,rckpit,item_model_number;

    int                         row; // for how many records exported
    #File
    ;
    strdatetime = date2Str(currentDate,321,DateDay::Digits2,DateSeparator::Hyphen,DateMonth::Digits2,DateSeparator::Hyphen,DateYear::Digits4); //  for current date
    filename = "G:\\PRODUCT_CSV_"+ strdatetime +".csv"; // file name
    file = new Commaio(filename , #io_write); // file permissions
    //file.outFieldDelimiter(';'); //delimeter
    if( !file || file.status() != IO_Status::Ok) // checking the file
    {
        throw error("File Cannot be opened");
    }
    companies = ["230","320"];
    while select crossCompany:companies * from inventTable
    {
        invModGrp = InventModelGroupItem::findByItemIdLegalEntity(inventTable.ItemId,                          inventTable.dataAreaId,false);
        invmodeGroupId = invModGrp.ModelGroupId;
            if((invmodeGroupId == "FIN") || (invmodeGroupId == "RAW"))
            {
                product_class = (inventTable.itemGroupId()?inventTable.itemGroup().ItemGroupId:'');
                product_class_desc = (inventTable.itemGroupId()?inventTable.itemGroup().Name:'')?                          (inventTable.itemGroupId()?inventTable.itemGroup().Name:''):'NA';
                master_product = 'MP-'+inventTable.RES_MasterProduct;
                master_product_desc = inventTable.RES_MasterProduct;
                itemName = inventTable.itemName();
                line = [product_class,product_class_desc,master_product,master_product_desc];
                file.writeExp(line);
                row++;
            }
    }
    info(strFmt("Completed, total number of rows exported:  %1",row));
}

Monday, 12 March 2018

How to Give The FIle IO Permissions in AX 2012

Some Times we need to give the File IO Permissions to Read or Write the File.
These situations can be occur when we are running a file in Client and that need server permissions.
the following code will help you to do that.

public static void main(Args _args)
{

    Set permissionSet;
    WinAPIServer winAPIServer;
    str fileName;
    int size;
    RES_PROS_BatchJobProductExcelExport bjex;
    str                         strdatetime;
    date                        currentDate;
    ;

    currentDate = today();
    strdatetime = date2Str(currentDate,321,DateDay::Digits2,DateSeparator::Hyphen,DateMonth::Digits2,DateSeparator::Hyphen,DateYear::Digits4);
    fileName = "C:\\filenPath.xlsx";

    permissionSet =  new Set(Types::Class);
    //get file write permission for createFile
    permissionSet.add(new FileIoPermission(fileName,'w'));
    //get file read/write permission for getFileSize and closeHandle
    permissionSet.add(new FileIoPermission('','rw'));
    CodeAccessPermission::assertMultiple(permissionSet);

        //invoke protected APIs
    WinAPIServer::createFile(fileName);
    size = WinAPIServer::FileSize(fileName);

    bjex = new RES_PROS_BatchJobProductExcelExport();
    bjex.run();

}

the above code can help you.

Tuesday, 6 March 2018

How to create a Batch Job to export Data to XML Using Class and job.

The Batch Job can be created in Different manners. I am explaining one way for it.
Steps:
1) Create a class for the logic what you want you want to do.
2) Add this class with the Batch Job.
3) run the Batch Job.

Note: If you want to run the batch job in the client mode to one more step needed.
4) run the batch job in client mode.

Step:1


I am creating a simple class for export data into XML.
go to classes node in the AOT. create a New Class name it. Open Class Declaration
and extend it to the  RunBaseBatch class.

class Batch4Demo extends RunBaseBatch
{}

after this override the run method of the class. Right click on the class in the AOT go to Override and select run method. in this run methode write your own logic like as shown bellow.
public void run()
{
    XmlDocument doc;
    XmlElement nodeXml;
    XmlElement nodeTable;
    XmlElement nodeAccount;
    XmlElement nodeName;
    CustTable   custTable;
    #define.filename(@'C:\\Users\nagan020\Desktop\productsXML.xml')
    ;
    doc = XmlDocument::newBlank();
    nodeXml = doc.createElement('xml');

    doc.appendChild(nodeXml);
     //Determines the runtime
    if (xSession::isCLRSession())
    {
        info('Running in a CLR session.');
    }
    else
    {
        info('Running in an interpreter session.');

        //Determines the tier
        if (isRunningOnServer())
        {
            info('Running on the AOS.');
        }
        else
        {
            info('Running on the Client.');
        }
    }

    while select custTable
    {
        nodeTable = doc.createElement(tablestr(CustTable));
        nodeTable.setAttribute(fieldstr(CustTable, RecId),int2str(custTable.RecId));
        nodeXml.appendChild(nodeTable);
        nodeAccount = doc.createElement(fieldstr(CustTable, AccountNum));
        nodeAccount.appendChild(doc.createTextNode(custTable.AccountNum));
        nodeTable.appendChild(nodeAccount);
        nodeName = doc.createElement(fieldstr(CustTable,CustGroup));
        nodeName.appendChild(doc.createTextNode(custTable.CustGroup));
        nodeTable.appendChild(nodeName);
      }
    doc.save(#filename);
    info(strFmt("File %1 created.", #filename));
}

after this override pack and unpack methods.
public container pack()
    {
        return conNull();
    }
public boolean unpack(container packedClass)
    {
        return true;
    }
now create a main method foe the class and call the run method in that 
(this is very important with out main you cant run the class) 
right click and add new method write following code.
public static void main(Args _args)
{
    Batch4Demo  b = new Batch4Demo ();
   b.run();
 }

Step:2

Create a Job in the Job Node of AOT write the following code in it.
static void Job_ScheduleBatch2(Args _args)
{
    BatchHeader batHeader;
    BatchInfo batInfo;
    RunBaseBatch rbbTask;
    str sParmCaption = "My Demonstration (b351)";
    ;
    rbbTask = new Batch4Dem0();
    batInfo = rbbTask .batchInfo();
    batInfo .parmCaption(sParmCaption);
    batInfo .parmGroupId(""); // The "Empty batch group".
    batHeader = BatchHeader ::construct();
    batHeader .addTask(rbbTask);
    batHeader .save();
    info(strFmt("'%1' batch has been scheduled.", sParmCaption));
}

Step:3

Now Compile the Job And Class. run the Batch Job by pressing F5.
Before running Generate the IL code. Go to Build and click on Generate Incremental CIL..
It will create a Batch job in the Batch Jobs Form you can view it by going into the 
following path
System Administration --> Inquiries --> BatchJobs --> Batch Jobs.
You should see the status as waiting---> Executing --> Ended in the status column
of the Batch Jobs form.
Now the above batch job will run only on the server.
If you want to make it run on the Client. follow bellow steps.

Step:4

Override the method  runsImpersonated. Right click on the Batch4Demo class and override the above method write the following code in it. 
public boolean runsImpersonated()
{
    // false means that the batch must run on a client.
    return false;
}
Now run the class as mentioned above.
After running it we have to add it to the client section to do this.
Go to Organization administration --> Basic Or Periodic --> Batch Processing.
open the form and you can see batch group and private check box option.
in the group option select empty group( Because in the above code we have selected empty in the batch group). uncheck the private. now click ok. the batch job will run.

Happy Daxing.......

Monday, 5 March 2018

How to Export Data into the XML using X++ in AX 2012.

To Export the data into the XML file using X++ use the bellow code.

public void xmlGeneration(Args _args)
{
    XmlDocument doc;
    XmlElement nodeXml;
    XmlElement nodeTable;
    XmlElement nodeAccount;
    XmlElement nodeName;
    CustTable   custTable;
    #define.filename(@'C:\\Users\nagan020\Desktop\productsXML.xml')
    ;
    doc = XmlDocument::newBlank();
    nodeXml = doc.createElement('xml');

    doc.appendChild(nodeXml);
     //Determines the runtime
    if (xSession::isCLRSession())
    {
        info('Running in a CLR session.');
    }
    else
    {
        info('Running in an interpreter session.');

        //Determines the tier
        if (isRunningOnServer())
        {
            info('Running on the AOS.');
        }
        else
        {
            info('Running on the Client.');
        }
    }

    while select custTable
    {
        nodeTable = doc.createElement(tablestr(CustTable));
        nodeTable.setAttribute(fieldstr(CustTable, RecId),int2str(custTable.RecId));
        nodeXml.appendChild(nodeTable);
        nodeAccount = doc.createElement(fieldstr(CustTable, AccountNum));
        nodeAccount.appendChild(doc.createTextNode(custTable.AccountNum));
        nodeTable.appendChild(nodeAccount);
        nodeName = doc.createElement(fieldstr(CustTable,CustGroup));
        nodeName.appendChild(doc.createTextNode(custTable.CustGroup));
        nodeTable.appendChild(nodeName);
      }
    doc.save(#filename);
    info(strFmt("File %1 created.", #filename));
}

Hope this will help...
Happy Daxing...