Dynamics AX Blog - Page 16
Get all tables, where a particular property has a specific valueThe following job lists all tables where a particular property - in the example the property ModifiedBy is requested - has a specific value. static void findTablesWithSpecificProperty(Args _args) { TreeNode treeNodeTables; TreeNode treeNode; str prop; str properties; #aot #Properties; treeNodeTables = TreeNode::findNode(#TablesPath + #AOTRootPath); treeNodeTables = treeNodeTables.AOTfirstChild(); while(treeNodeTables) { properties = treeNodeTables.AOTgetProperties(); prop = Global::findProperty(properties,#PropertyModifiedBy); if(prop == "yes") { info(treeNodeTables.AOTname()); } treeNodeTables = treeNodeTables.AOTnextSibling(); } } |
Create pallet through codeThe following job shows how to create a palette by code and it pulls the pallet number from a number sequence. Important in the latter case, is to the call numberSeq.used() so that the drawn number is marked as "used".
static void howToUseNumberSeq(Args _args)
{
WMSPallet wmsPallet;
NumberSeq numberSeq;
#define.InventLocationId("12")
#define.WMSLocationId("L01")
ttsbegin;
wmsPallet.clear();
wmsPallet.initValue();
wmsPallet.InventLocationId = #InventLocationId;
wmsPallet.wmsLocationId = #WMSLocationId;
numberSeq = WMSPallet::numberSeq(true,true);
if (numberSeq)
{
wmsPallet.wmsPalletId = WMSPalletIdGenerate::newPalletIdFromNumberSeq(numberSeq);
numberSeq.used();
}
if(wmsPallet.validateWrite())
{
wmsPallet.insert();
}
else
{
throw error("@SYS96731");
}
ttscommit;
} |
Check/post Price-/discount agreement journals trough codeThe next lines of code should show, how checking or posting of Price-/discount agreement journals is done. static void checkOrPostPriceDiscJournal(Args _args) { PriceDiscAdmCheckPost priceDiscAdmCheckPost; PriceDiscAdmTable priceDiscAdmTable; PriceDiscJournalNum priceDiscJournalNum = "PDJ-00014"; priceDiscAdmTable = PriceDiscAdmTable::find(priceDiscJournalNum); if (priceDiscAdmTable.Posted) { throw error("@SYS21497"); } priceDiscAdmCheckPost = new PriceDiscAdmCheckPost(true); // true = Checkonly, false = Post priceDiscAdmCheckPost.initJournalNum(priceDiscJournalNum); priceDiscAdmCheckPost.run(); } |
Create a picking list for production orderThe following job creates a picking list for a production order.
static void createPickingList(Args _args)
{
ProdJournalCreateBOM prodJournalCreateBOM;
prodJournalCreateBOM = ProdJournalCreateBOM::construct();
prodJournalCreateBOM.parmProdId('P000188');
prodJournalCreateBOM.parmJournalNameId(ProdJournalName::standardJournalName(ProdJournalType::Picklist, prodJournalCreateBOM.parmProdId()));
prodJournalCreateBOM.parmTransDate(systemDateGet());
prodJournalCreateBOM.parmBOMAutoConsump(BOMAutoConsump::Never);
prodJournalCreateBOM.parmProposalAsConsump(NoYes::No);
prodJournalCreateBOM.parmQtyCalc(5);
prodJournalCreateBOM.parmConsumpProposal(ProdBOMConsumpProposal::Qty);
prodJournalCreateBOM.run();
}
If the Header already exists, you can use the following Job:
static void createPickingList(Args _args)
{
ProdJournalCreateBOM prodJournalCreateBOM;
prodJournalCreateBOM = ProdJournalCreateBOM::construct();
prodJournalCreateBOM.parmProdId('P000188');
prodJournalCreateBOM.parmJournalId('00926'); // Bei bestehendem Journalkopf
prodJournalCreateBOM.parmTransDate(systemDateGet());
prodJournalCreateBOM.parmBOMAutoConsump(BOMAutoConsump::Never);
prodJournalCreateBOM.parmProposalAsConsump(NoYes::No);
prodJournalCreateBOM.parmQtyCalc(11);
prodJournalCreateBOM.parmConsumpProposal(ProdBOMConsumpProposal::Qty);
prodJournalCreateBOM.run();
} |
Create a production order for a sales order line through codeIf you want to create a production order for a sales order line, the following job can provide an idea of how to do it. static void createProdTableForSalesLine(Args _args)
{ SalesLine salesLine = SalesLine::findInventTransId('011748'); ProdTable prodTable; prodTable.initValue(); prodTable.initFromCaller(salesLine); prodTable.insert(); }
|
End/finish a production order through code
Dynamics AX provides a framework, which can be used to update production orders to a specific status. In the example, a production order is ended/finished. If you want to update several production orders at the same time, you must invoke the ProdMultiHistoricalCost.insert() method per production order and pass the respective record of ProdTable.
static void prodEnd(Args _args) { ProdTable prodTable; ProdMultiHistoricalCost prodMultiHistoricalCost; prodTable = ProdTable::find("P000195"); prodMultiHistoricalCost = ProdMultiHistoricalCost::construct(new Args()); RunBaseMultiParm::initParm(prodMultiHistoricalCost); prodMultiHistoricalCost.insert(prodTable, prodMultiHistoricalCost.defaultParmBuffer()); prodMultiHistoricalCost.run(); } |
|
|
|
|
|
|

Using the class InventDimOnhand, you can determine the on-hand inventory of articles and/or specific inventory-dimensions.
The following job determines the inventory for a specific item and a specific inventlocation. This is grouped per color.
static void getInventOnhandExample(Args _args) { ItemId itemId; InventDimOnHand inventDimOnHand; InventDimParm inventDimParmOnHandLevel; InventDimOnHandIterator inventDimOnHandIterator; InventDimOnHandMember inventDimOnHandMember; InventDim inventDim; InventDim inventDimCriteria; InventDimParm inventDimParmCriteria; // Item: Query specific item itemId = "DMO003"; // inventDimCriteria: Apply ranges inventDimCriteria.wmsLocationId = "12-1"; inventDimCriteria.InventBatchId = "DMOBatch001"; // inventDimParmCriteria: should values from inventDimCriteria be used? inventDimParmCriteria.ItemIdFlag = false; inventDimParmCriteria.InventSiteIdFlag = false; inventDimParmCriteria.InventLocationIdFlag = false; inventDimParmCriteria.wmsLocationIdFlag = true; // wmsLocationId from inventDimCriteria will be used inventDimParmCriteria.wmsPalletIdFlag = false; inventDimParmCriteria.InventBatchIdFlag = false; // inventBatchId from inventDimCriteria will not be used inventDimParmCriteria.InventSerialIdFlag = false; inventDimParmCriteria.ConfigIdFlag = false; inventDimParmCriteria.InventSizeIdFlag = false; inventDimParmCriteria.InventColorIdFlag = false; inventDimParmCriteria.InventStyleIdFlag = false; // inventDimParmOnHandLevel: Which dimensions should be used to group for? // inventDimParmOnHandLevel necessary for inventDimOnHandLevel::DimParm inventDimParmOnHandLevel.ItemIdFlag = true; // necessary inventDimParmOnHandLevel.InventSiteIdFlag = false; inventDimParmOnHandLevel.InventLocationIdFlag = false; inventDimParmOnHandLevel.wmsLocationIdFlag = false; inventDimParmOnHandLevel.wmsPalletIdFlag = false; inventDimParmOnHandLevel.InventBatchIdFlag = false; inventDimParmOnHandLevel.InventSerialIdFlag = false; inventDimParmOnHandLevel.ConfigIdFlag = false; inventDimParmOnHandLevel.InventSizeIdFlag = false; inventDimParmOnHandLevel.InventColorIdFlag = true; // group by color inventDimParmOnHandLevel.InventStyleIdFlag = false; inventDimOnHand = InventDimOnHand::newAvailPhysical(itemId, inventDimCriteria, inventDimParmCriteria, InventDimOnHandLevel::DimParm, inventDimParmOnHandLevel); inventDimOnHandIterator = inventDimOnHand.onHandIterator(); while (inventDimOnHandIterator.more()) { inventDimOnHandMember = inventDimOnHandIterator.value(); inventDim = InventDim::find(inventDimOnHandMember.parmInventDimId()); info(con2Str([ inventDimOnHandMember.parmItemId(), inventDim.InventSiteId, inventDim.InventLocationId, inventDim.wmsLocationId, inventDim.wmsPalletId, inventDim.InventBatchId, inventDim.InventSerialId, inventDim.ConfigId, inventDim.InventSizeId, inventDim.InventColorId, inventDim.InventStyleId, inventDimOnHandMember.parmInventQty()])); inventDimOnHandIterator.next(); } }The output of the above job looks is an infolog like the following:
DMO003,,,12-1,,,,,,Cherry,,54
DMO003,,,12-1,,,,,,Black,,100