Dynamics AX Blog - Dynamics AX 4.0 - Microsoft Dynamics AX (Axapta)

Momentan angezeigt werden nur Beiträge der Kategorie »Microsoft Dynamics AX (Axapta)« Filter entfernen

In den letzten Jahren, in denen ich mich fast hauptsächlich mit der Entwicklung im Umfeld von Microsoft Dynamics AX (vormals Axapta) beschäftigt habe, ist das eine oder andere Code-Fragment entstanden, von dem ich mir vorstellen könnte, daß es auch für andere AX-Entwickler ganz nützlich sein könnte. Aber auch Tips und Tricks zu dem mächtigen ERP-System werde ich in dieser Kategorie präsentieren.

RSS-Feed dieser Kategorie
Momentan angezeigt werden nur Beiträge, welche für die Dynamics AX-Version »Dynamics AX 4.0« relevant sind. Filter entfernen

RSS-Feed dieser Version

Namen der Shared Projects nach einem String durchsuchen

Um sich alle (Shared-)Projekte ausgeben zu lassen, die einen bestimmten Text im Namen tragen, kann man den folgenden Code verwenden.

static void searchProjectName(Args _args)
{
    ProjectNode projectNode;

    #AOTExport

    projectNode    = infolog.projectRootNode();
    projectNode    = projectNode.AOTfindChild(#expProjectShared);
    projectNode    = projectNode.AOTfirstChild();

    while(projectNode)
    {
        setPrefix(projectNode.name());

        if(strScan(projectNode.name(), "BR_", 0, 60))
        {
            info(projectNode.name());
        }

        projectNode    = projectNode.AOTnextSibling();
    }
}

 
 
 

Statt Parameter-Listen einen DataContract verwenden

Wer schon einmal die Parameter einer Methode erweitern musste, kennt vielleicht das Problem: Wenn man Glück hat kann man seinen neuen Parameter am Ende einfügen und mit einem Default-Wert vorbelegen.

Hat man nicht ganz so viel Glück und muss entweder der Parameter zwischen den vorhandenen einbauen oder darf/kann keinen Default-Wert angeben so muss man den gesamten AOT nach den Aufrufen dieser Methode durchsuchen (die Querverweise helfen hier enorm) und diese entsprechend anpassen.

Aufgrund dieser Problematik gehe ich bei meinen Methoden nun oft den Weg, daß ich nur einen einzigen Parameter einfüge, und zwar vom Typ einer - nennen wir sie einfach einmal DataContract-Klasse.

DataContracts sind dem einen oder anderen vielleicht aus dem SSRS-Umfeld bekannt, aber die selbe Logik kann ich auch in vielen anderen Situationen anwenden.

So sieht eine solche DataContract-Klasse beispielweise wie folgt aus:

classDeclaration MyDataContract
{
    ItemId itemId;
    Qty qty;
}

 

Public ItemId parmItemId(ItemId _itemId = itemId)
{
    itemId = _itemId;
    return itemId;
}

 

Public Qty parmQty(Qty _qty = qty)
{
    qty = _qty;
    return qty;
}


Eine Methode könnte dann wie folgt aussehen:

Public void myMethod(MyDataContract _dataContract)
{
    // … do something…
    info(_dataContract.parmItemId());
}


Aufrufen muss ich eine solche Methode so:

MyDataContract dataContract;
dataContract = new MyDataContract();
dataContract.parmItemId("A1000");
dataContract.parmQty(123);

Object.myMethod(dataContract);


Kommt nun später ein neuer Parameter hinzu, muss ich den lediglich entsprechend in der DataContract-Klasse einfügen und die Logik in der Methode erweitern. Die Methodenaufrufe können u.U. so bleiben wie sie waren, lediglich die Aufrufe wo die geänderten Parameter berücksichtigt werden müssen, müssen angepasst werden.

Und zu guter Letzt kann ich solche DataContract-Klassen natürlich für mehrere Methoden verwenden.
 

 


 
 
 

Eine bestimmte Dimension als Dialogfeld einbinden

Wenn man in Dynamics AX 2009 (oder früheren Versionen) eine bestimmte Dimension als Dialogfeld verwenden möchte, kann man sich einen eigenen Extended Datatype (abgeleitet von Criterias) wie im folgenden beschrieben anlegen. Entscheidend sind dabei die Relations dieses EDTs.

Im Beispiel soll beispielsweise der Kostenträger als Dialogfeld angeboten werden.

Screenshot EDT

Der Beispiel-Code ist einer von RunBase abgeleitenden Klasse entnommen.

protected Object dialog(DialogRunbase dialog, boolean forceOnClient)
{
    Object ret;

    ret = super(dialog, forceOnClient);

    df_project = ret.addField(TypeId(DimensionCostCenter));

    return ret;
}

Der so angepasste Dialog sollte wie folgt aussehen:

Screenshot Dialog


 
 
 

Ursache von Fehlermeldungen ermitteln

In Dynamics AX können unterschiedliche (Fehler-)Meldungen auftreten, die meisten kommen von der Applikation, es gibt aber auch Meldungen, die vom AX-Client ausgegeben werden.

Leider sind nicht alle Meldungen so sprechend, daß man (als Entwickler) sofort weiß, was nun zu tun ist. Deshalb gibt es, je nachdem um welche Art von Fehlermeldung es sich handelt, unterschiedliche Herangehensweisen, wie man die Ursache der Meldung findet.

Meldung über das Infolog der Applikation

Screenshot InfologBei manchen Meldungen genügt ein Doppelklick auf die Meldung im Infolog und man landet im Code, welcher die Meldung geworfen hat (vorausgesetzt man befindet sich als Benutzer gerade im Entwicklungsmodus).


 
 
 

Objekte per Code zu einem Projekt hinzufügen

Nachstehend ein kurzer Job, mit dessen Hilfe man AOT-Elemente zu einem bestehenden Shared Project hinzufügen kann.

static void AddNodeToSharedProject(Args _args)
{
    projectNode projectNode;
    TreeNode treeNode;
    #AOT
    #AOTExport

    projectNode    = infolog.projectRootNode();
    projectNode    = projectNode.AOTfindChild(#expProjectShared);
    projectNode    = projectNode.AOTfindChild('MyProject');
   
    // Add objects
    treenode = TreeNode::findNode(#TablesPath+'\\'+tableid2name(tablenum(CustGroup)));
    projectNode.addNode(treenode);

    treenode = TreeNode::findNode(#TablesPath+'\\'+tableid2name(tablenum(VendGroup)));
    projectNode.addNode(treenode);
   
    treenode = TreeNode::findNode(#ClassesPath+'\\'+classStr(PriceDisc));
    projectNode.addNode(treenode);
}

Das geänderte Projekt sieht beispielsweise wie folgt aus:

Screenshot


 
 
 

Werte eines Base-Enums durchlaufen

SysDictEnum SysDictEnum = new SysDictEnum(enumNum(SalesStatus));
int i;

for (i=0;i<SysDictEnum.values();i++)
{
    info(SysDictEnum.index2Label(i));
}

 
 
 

Makro innerhalb eines SELECT-Statements verwenden

Das Beispiel listet beispielsweise nur aktive Stücklistenpositionen (Tabelle BOM) auf (aktiv über die Felder FromDate und ToDate). Lässt man den zweiten Parameter des Makros leer (dateNull()), so werden alle Stücklistenpositionen gelistet.

static void useMacroInSelectStatement(Args _args)
{
    bom bom;
    date emptyDate;
    
    // parameters: %1 = table instance, %2 date, %3 empty date value
    #localmacro.bomDateFilter
        && ( %2 == dateNull() || (
            ((%1.FromDate <= %2) && (%1.ToDate >= %2)) ||
            ((%1.FromDate == %3) && (%1.ToDate == %3)) ||
            ((%1.FromDate <= %2) && (%1.ToDate == %3)) ||
            ((%1.FromDate == %3) && (%1.ToDate >= %2))
            ))
    #endMacro
    ;
    
    while select bom
    where bom.ItemId == '123'
    #bomDateFilter(bom, systemDateGet(), emptyDate)
    {
        info(bom.bomid);
    }
}

 
 
Seiten 1 2 3 4 ... 8 » 

 

 
 
 
Beiträge des aktuellen Monats
November 2024
MoDiMiDoFrSaSo
 123
45678910
11121314151617
18192021222324
252627282930 
 
© 2006-2024 Heinz Schweda | Impressum | Kontakt | English version | Mobile Version
Diese Webseite verwendet Cookies, um Benutzern einen besseren Service anzubieten. Wenn Sie weiterhin auf der Seite bleiben, stimmen Sie der Verwendung von Cookies zu.  Mehr dazu