How to pass Arguments/records in RDP Report through form, how to open report from the Form using controller class (X++) in D365 Finance and operation.
In this article, I will guide you on how to pass arguments or records from a form to a report as parameters. I have developed a report that prints the purchase order for a specific purchase ID (with either ‘Received’ or ‘Invoiced’ purchase status), which I pass through the form.
Let’s begin by creating a simple Finance and Operations project in Visual Studio. We will add all the elements required to develop the report. The following elements are necessary:
- Temp table (with required fields, fields which mapped in Dp class)
- Contract class
- Data Provider Class
- Report (Add the DP class to the Dataset of the Report, and create the report design according to your requirements)
For the PurchTable
Form, create a Form Extension of the PurchTable
Form and add a button group and button in the Action pane.
DP Class:
[SrsReportParameterAttribute(classStr(PurchTable_Contract))]
class PurchTable_DP extends SRSReportDataProviderBase
{
PurchReceiptTmp prt;
//Serializing The Code
[SrsReportDataSetAttribute("PurchReceiptTmp")] //Fetching Data from Table
public PurchReceiptTmp get_RecieptTable()
{
select * from prt;
return prt;
}
/// <summary>
/// Processing Report
/// </summary>
public void processReport()
{
PurchTable_Contract contract;
ListIterator iter;
List purchID;
contract =this.parmDataContract();
purchID = contract.parm_purchID();
prt.clear();
iter = new ListIterator(purchID);
while(iter.more())
{
prt.PurchId = iter.value();
this.populate_Line();
iter.next();
}
}
/// <summary>
/// This is Filling the Table
/// </summary>
public void populate_Line()
{
PurchTable pt;
PurchLine pl;
VendInvoiceJour venInvJr;
VendInvoiceTrans venInvTr;
// Query For Filling the Table
while select firstonly pt where prt.PurchID == pt.PurchId
join pl where prt.PurchId == pl.PurchId
{
if(pt.PurchStatus == PurchStatus::Received)
{
this.DataofRecievedStatus();
}
else if(pt.PurchStatus == PurchStatus::Invoiced)
{
this.DataofRecievedStatus();
while select * from venInvJr where prt.PurchId == venInvJr.PurchId
join venInvTr where prt.PurchId == venInvTr.PurchID
{
while select forupdate prt
where prt.PackingSlipId == venInvTr.getPackingSlip().PackingSlipId && prt.OrderedQuantity == venInvTr.Qty
{
ttsbegin;
prt.InvoiceId = venInvJr.InvoiceId;
prt.InvoiceQty = venInvTr.Qty;
prt.PurchPrice = venInvTr.PurchPrice;
prt.InvoiceItemId = venInvTr.ItemId;
prt.InvoiceName = venInvTr.Name;
prt.update();
ttscommit;
}
}
}
}
}
/// This Method is for collecting data in case of Purchase Status is Recieved
public void DataofRecievedStatus()
{
VendPackingSlipTrans venPacSlipTrans;
VendPackingSlipJour venPacSlipJour;
while select * from venPacSlipTrans where prt.PurchID == venPacSlipTrans.OrigPurchid
join venPacSlipJour where prt.PurchId == venPacSlipJour.PurchId && venPacSlipJour.PackingSlipId == venPacSlipTrans.PackingSlipId
{
prt.PackingSlipId = venPacSlipTrans.PackingSlipId;
prt.OrderedQuantity = venPacSlipTrans.Ordered;
prt.RecievedQty = venPacSlipTrans.Qty;
prt.ValueMST = venPacSlipTrans.ValueMST;
prt.ItemId = venPacSlipTrans.ItemId;
prt.Name = venPacSlipTrans.Name;
prt.PurchId = venPacSlipTrans.OrigPurchid;
prt.insert();
}
}
}
======================================================================
[SRSReportParameterAttribute(classStr(VTGMRLINWHSWorkReportContract))]
class VTGMRLINWHSWorkReportDP extends SRSReportDataProviderBase
{
GMRLINWHSWorkTableCopy workTable;
[SRSReportDataSetAttribute(tablestr(GMRLINWHSWorkTableCopy))]
public GMRLINWHSWorkTableCopy getWorkTable()
{
select workTable;
return workTable;
}
public void processReport()
{
VTGMRLINWHSWorkReportContract contract;
ListIterator iter;
List whsWorkIdList;
WHSWorkId getWhsWorkId;
WHSWorkTable WHSWorkTable;
WHSWorkLine WHSWorkLine;
// contract = this.parmDataContract() as VTGMRLINWHSWorkReportContract;
contract = this.parmDataContract();
whsWorkIdList = contract.parm_WHSWorkId();
workTable.clear();
iter = new ListIterator(whsWorkIdList);
// Get sales agreement header record from the contract parameter
// WHSWorkTable = WHSWorkTable::find(contract.parmWHSWorkId());
while(iter.more())
{
getWhsWorkId = iter.value();
WHSWorkTable = WHSWorkTable::find(getWhsWorkId);
if (WHSWorkTable.RecId)
{
while select * from WHSWorkLine
where WHSWorkLine.WorkId == WHSWorkTable.WorkId
{
workTable.WorkId = WHSWorkTable.WorkId;
workTable.WaveId = WHSWorkTable.WaveId;
workTable.WorkTransType = WHSWorkTable.WorkTransType;
workTable.LoadId = WHSWorkTable.LoadId;
workTable.CombinedWorkId = WHSWorkTable.CombinedWorkId;
workTable.TargetLicensePlateId = WHSWorkTable.TargetLicensePlateId;
workTable.OrderNum = WHSWorkTable.OrderNum;
workTable.InventSiteId = WHSWorkTable.InventSiteId;
workTable.InventLocationId = WHSWorkTable.InventLocationId;
workTable.LineNum = WHSWorkLine.LineNum;
workTable.WorkType = WHSWorkLine.WorkType;
workTable.ItemId = WHSWorkLine.ItemId;
workTable.WMSLocationId = WHSWorkLine.WMSLocationId;
workTable.QtyWork = WHSWorkLine.QtyWork;
workTable.UnitId = WHSWorkLine.UnitId;
workTable.WorkStatus = WHSWorkLine.WorkStatus;
workTable.itemBarCode = InventItemBarcode::findItem(WHSWorkLine.ItemId, WHSWorkLine.InventDimId, true, true).itemBarCode;
workTable.ProductName = InventTable::name(WHSWorkLine.ItemId, InventDim::find(WHSWorkLine.InventDimId));
workTable.CustName = CustTable::find(SalesTable::find(WHSWorkTable.OrderNum).CustAccount).name();
workTable.wMSStoreZoneId = WMSLocation::find(WHSWorkLine.WMSLocationId, InventDim::find(WHSWorkLine.InventDimId).InventLocationId).ZoneId;
workTable.inventBatchId = InventDim::find(WHSWorkLine.InventDimId).inventBatchId;
workTable.expDate = InventBatch::find(InventDim::find(WHSWorkLine.InventDimId).inventBatchId, WHSWorkLine.ItemId).expDate;
workTable.insert();
}
// read the next record
iter.next();
}
}
}
}
- Class Declaration: The class
PurchTable_DP
extendsSRSReportDataProviderBase
, which is a base class for all RDP classes in Microsoft Dynamics AX/365. - Data Members: The class has one data member
prt
of typePurchReceiptTmp
. - get_RecieptTable() Method: This method is decorated with the
SrsReportDataSetAttribute
attribute, which indicates that the method will provide data for the report. It selects all records fromprt
and returns them. - processReport() Method: This method is responsible for processing the report. It retrieves the contract from the data contract, gets the purchase ID, and then iterates over the list of purchase IDs to populate the line.
- populate_Line() Method: This method populates the
prt
table based on the purchase status. If the purchase status isReceived
, it calls theDataofRecievedStatus()
method. If the purchase status isInvoiced
, it first calls theDataofRecievedStatus()
method and then updates theprt
table with invoice details. - DataofRecievedStatus() Method: This method is used to collect data when the purchase status is
Received
. It selects records fromvenPacSlipTrans
andvenPacSlipJour
based on the purchase ID and packing slip ID, and then inserts the selected data into theprt
table.
The code is designed to handle the processing of purchase receipts based on their status (Received
or Invoiced
). It populates a temporary table (prt
) with the relevant data, which is then used to generate a report. The actual report layout would be defined elsewhere, likely in an SSRS report design (RDL) file.
Contract Class:
/// <summary>
/// Forcing the report to get Parameters From User
/// </summary>
class PurchTable_Contract // This Class is used to take input Parameters From The User
{
List purchID;
[
DataMemberAttribute("purchID"), // This Serailizes the Variable
SysOperationLabelAttribute(literalStr('Purchase Order')),// This Changes the Input Parameter name
AifCollectionTypeAttribute("purchID",Types::String) // This Serializes the List Type
]
public List parm_purchID( List _purchID = purchID)
{
purchID = _purchID;
return purchID;
}
}
==================================================================
[DataContractAttribute]
public class VTGMRLINWHSWorkReportContract
{
List whsWorkIdList;
[
DataMemberAttribute("WHSWorkId"),
SysOperationLabelAttribute(literalStr('Work Id')),
AifCollectionTypeAttribute("WHSWorkId",Types::String)
]
public List parm_WHSWorkId( List _whsWorkId = whsWorkIdList)
{
whsWorkIdList = _whsWorkId;
return whsWorkIdList;
}
}
This class is used to take input parameters from the user for a report. Here’s a brief explanation of the code:
- Class Declaration: The class
PurchTable_Contract
is declared. This class is used to take input parameters from the user. - Data Members: The class has one data member
purchID
of typeList
. - parm_purchID() Method: This method is a getter-setter for the
purchID
data member. It takes an optional parameter_purchID
which defaults topurchID
. If_purchID
is provided, it setspurchID
to_purchID
and then returnspurchID
. - Attributes: The
purchID
data member is decorated with three attributes:
DataMemberAttribute
: This attribute serializes thepurchID
variable.SysOperationLabelAttribute
: This attribute changes the input parameter name to ‘Purchase Order’.AifCollectionTypeAttribute
: This attribute serializes theList
type.
This class is typically used in conjunction with a report data provider (RDP) class to supply parameters to a report. The user is prompted to enter these parameters when running the report. The parameters are then used to filter or otherwise manipulate the data that the RDP class provides to the report. In this case, the parameter is a list of purchase IDs (purchID
).
Handle the Button Click Event: In the form extension class, create a static event handler method for the Clicked
event of the button. In this method:
[ExtensionOf(formStr(PurchTable))]
final class PurchTableForm_Extension
{
/// <summary>
/// Gets the selected records and pass them to the Report
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
///
[FormControlEventHandler(formControlStr(PurchTable, Report), FormControlEventType::Clicked)]
public static void Report_OnClicked(FormControl sender, FormControlEventArgs e)
{
//super();
PurchTable purchtable;
FormRun formrun = sender.formRun();
FormDataSource purchTable_ds;
Array records;
purchTable_ds = sender.formRun().dataSource(1);
// purchtable = purchTable_ds.cursor(); // This line is for getting one parameter where the cursor is present
SrsReportRunController controller = new SrsReportRunController();
PurchTable_Contract purchTable_contract = new PurchTable_Contract();
List parm = new List(Types::String);
// Accessing the Report Name along with the design
controller.parmReportName(ssrsReportStr(PurchTable_Report,PurchTable_Report));
// getting all the selected records
purchtable = purchTable_ds.getFirst(true);
while(purchtable)
{
parm.addEnd(purchtable.PurchId);
purchtable = purchTable_ds.getNext();
}
// passing the parameters to the contract class
purchTable_contract.parm_purchID(parm);
controller.parmReportContract().parmRdpContract(purchTable_contract);
// Disabling the parameter Dialog field
controller.parmShowDialog(false);
controller.startOperation();
}
}
===================================================================
[ExtensionOf(formStr(WHSWorkTableListPage))]
final class VTWHSWorkTableListPageFrm_Extension
{
/// <summary>
/// Gets the selected records and pass them to the Report
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
[FormControlEventHandler(formControlStr(WHSWorkTableListPage, VTGMRLINWHSWork), FormControlEventType::Clicked)]
public static void VTGMRLINWHSWork_OnClicked(FormControl sender, FormControlEventArgs e)
{
//super();
WHSWorkTable whsWorkTable;
FormRun formrun = sender.formRun();
FormDataSource whsWorkTable_ds;
Array records;
whsWorkTable_ds = sender.formRun().dataSource(1);
SrsReportRunController controller = new SrsReportRunController();
VTGMRLINWHSWorkReportContract whsWorkReportContract = new VTGMRLINWHSWorkReportContract();
List parm = new List(Types::String);
// Accessing the Report Name along with the design
controller.parmReportName(ssrsReportStr(VTGMRLINWHSWork,Report));
// getting all the selected records
whsWorkTable = whsWorkTable_ds.getFirst(true);
while(whsWorkTable)
{
parm.addEnd(whsWorkTable.WorkId);
whsWorkTable = whsWorkTable_ds.getNext();
}
// passing the parameters to the contract class
whsWorkReportContract.parm_WHSWorkId(parm);
controller.parmReportContract().parmRdpContract(whsWorkReportContract);
// Disabling the parameter Dialog field
controller.parmShowDialog(false);
controller.startOperation();
}
}
This class extends the form PurchTable
and is used to handle the event when the Report
button is clicked on the form. Here’s a brief explanation of the code:
- Class Declaration: The class
PurchTableForm_Extension
is declared. This class extends the formPurchTable
. - Report_OnClicked() Method: This method is decorated with the
FormControlEventHandler
attribute, which indicates that it’s an event handler for theClicked
event of theReport
button on thePurchTable
form. - Inside the Report_OnClicked() Method:
- It first initializes some variables and objects, including a
SrsReportRunController
object and aPurchTable_Contract
object. - It then sets the report name in the controller.
- It gets all the selected records from the
PurchTable
form’s data source and adds their purchase IDs to a list. - It passes the list of purchase IDs to the
PurchTable_Contract
object. - It sets the
PurchTable_Contract
object in the report contract of the controller. - It disables the parameter dialog field of the controller.
- Finally, it starts the operation of the controller, which would run the report with the provided parameters.
This class is typically used to handle user interactions with the form. In this case, it handles the event when the Report
button is clicked, gets the selected records from the form, and runs a report with those records as parameters. The actual report would be defined elsewhere, likely in an SSRS report design (RDL) file. The report would use the provided parameters to filter or otherwise manipulate the data it displays.
Comments
Post a Comment