Bad Smells in Dynamics NAV

Bad Smells


Unter Bad Smells, kurz Smell (deutsch ‚[schlechter] Geruch‘) oder deutsch übelriechender Code versteht man in der Programmierung ein Konstrukt, das eine Überarbeitung des Programm-Quelltextes nahelegt (Quelle Wikipedia).


Kurzum bei Bad Smells geht es nicht um Programmfehler! Vielmehr handelt es sich um funktionierenden Programmcode, der schlecht strukturiert ist. Demzufolge nicht optimal auf die Daten des SQL Servers zugreift und sie verarbeitet.
Das größte Problem liegt darin, dass der Code für den Programmierer schwer verständlich ist. So können sich bei Korrekturen und Erweiterungen häufig wieder neue Fehler einschleichen. Code-Smell kann auch auf ein tieferes Problem hinweisen, das in der schlechten Struktur verborgen liegt. Oft wird diese Problem erst durch eine Überarbeitung erkannt.



Bad Smells existieren in jedem Softwaresystem (auch bei uns!)


Bad Smells entstehen aus verschiedenen Gründen. Sei es beispielsweise durch Anforderungen an das NAV System und somit Geschäftsregeln oder Berechnungen zu verändern. Manchmal auch wegen schlechter Abstimmung in einem Entwicklerteam. Infolgedessen geschieht es schnell, das z. B. duplizierter Quellcode entsteht.
Jeder Programmierer kennt zudem das Problem, dass häufig unter Zeitdruck gearbeitet wird und dadurch nicht alle Anforderungen oder Erweiterungen gut durchdacht und getestet werden.

Beim Thema Variablen- und Funktionsnamen im C/AL Code verwenden, haben wir in den bei der Analyse von Performance Problemen in Dynamics NAV interessante Variationen entdeckt.

Hier ein kleines Beispiel:

Genauer gesagt haben mit V8 Search ein SQL Statements analysiert, dass von Dynamics NAV erstellt wurden. Diese Abfrage führt eventuelle zu Blockaden, Deadlocks oder brauchen einfach nur lange bei der Ausführung (Long Duration).


TSQL:

SELECT „timestamp“
,“Document Type“
,“Document No_“

FROM „Datenbank“.dbo.“Mandant$Sales Line“ WITH (READUNCOMMITTED)
WHERE (
„Document Type“ = @0
AND „Document No_“ = @1
)
ORDER BY „Document Type“ ASC
,“Document No_“ ASC


Die Abfrage benutzt einen gruppierten Index mit eindeutigen Spalten. Die Antwortzeit des SQL Skripts ist Top und Logical Reads optimal.

Demzufolge begibt man sich auf die Suche der verwendeten SQL Tabelle „Sales Line“ (Record 37) im Dynamics NAV C/AL Code. Bei der NAV Lösung unseres Kunden mit über 8.000 NAV Objekten und über 6,5 Mio. Zeilen C/AL Code eine echte Herausforderung.

Das Ergebnis wie oft die Tabelle „Sales Line“ (Record 37) in gesamten Code als Record benutzt wird lag bei 10.626 mal.
Und jetzt kommt der eigentlich Punkt des Themas – die verwendeten Variablennamen für den Record 37.


Bad Smells in Dynamics NAV
Bad Smells



Mit V8 Search hatten wir das Ergebnis in ca. 2 Sekunden.

Hier das Ergebnis:


SalesLine
SalesOrderLine
Loc_SalesLine
SalesLine2
OldSalesLine
locSalesLine
l_SalesLine
TempSalesLine
SalesLine3
SalesLine_loc
p_SalesLine
NewSalesLine
ToSalesOrderLine
CompSalesLine
TotalSalesLine
TotalSalesLineLCY
ATOSalesLine
SL_loc
l_SalesLineRec
v_SalesLine
Verkaufszeile_loc
RentalLine2
RentalLine
RentalOrderLine
TempSalesLines
SalesLineInvoice
OrderLine
SalesLine5
SalesLineForQuoteDetails_Loc
AVZ
VKZ_loc
verkzeile_loc
lSalesLine
TotalsSalesLine
FilterSalesLine
SalesLineToUpdate
ToSalesLine
PreviousSalesLine
SalesLines_loc
xSalesLine
SalesLineACY
JobTaskSalesLine
GlobalSalesLine
l_Salesline2
SalesLineBackup
ItemChargeSalesLine
ItemJnlLine2
PrepmtSalesLine
NewTotalSalesLine
BlanketOrderSalesLine
xBlanketOrderSalesLine
SalesOrderLine2
SalesOrderInvLine2
SalesLineToPost
TempPrepmtSalesLine
SalesInvoiceLine
CombinedSalesLine
TotalSalesLineLCY2
HasATOShippedNotInvoiced
ItemLedgEntryNotInvoiced
SalesLineForCharge
SlsLine
SL
SalesLine2_loc
SalesQuoteLine
OrderSalesLine
AttachedToSalesLine
SalesLine_loc2
pSalesLine
FromSalesLine
InvRoundingSalesLine
SalesLines
SalesLineOld
NewSalesLineLCY
SelectedSalesLine
SalesLineRec
BlanketSalesLine
TempSalesLine2
ToSalesInvLine
FromSalesHeader
ToSalesLine2
FromSalesLine2
FromSalesLineBuf
EmptyToSalesLine
ToAssemblyLine
TempFromAsmLine
ToSalesHeader
p_doclineno
SourceRefNo
retSalesLine
recSalesLIne
SalesLineMach_loc
VZ
LSalesLine1
FoundSalesLine
Rec
ActRec
NewRec
SalesLine4
CurrentSalesLine
pItemChargeSalesLine
tmpSalesLine
OldRentalLine
crMemoLine_loc
Loc_SalesLineFrom
Loc_SalesLineTo
PAR_SalesLine
AngebotsZeilen
SalLine
loc_SalesQuoteLines
xRec
VKZeile
SalesLineCharge
SalesLine1
SalesLineSplit
SalesLineReturn
Amount
DummySalesLine
ReturnSalesLine
OriginalSalesLine
DestinationSalesLine
ItemSalesLine
SalesLineBlanket
SalesLineOrder
SalesLineBoAfterCrM
RefSalesLine
InvDiscAmountEditable
SalesLineDest
CalcMethod
SalesHeader
WithDemandSalesLine
SalesLineItem
SalesLineBC
SalesLineNM
SalesLineRestored
SalesLineWithNegativeQuantity
SalesLineItemCharge
SalesLineRetOrder
SalesLineApplyTo
Factor
FirstSalesLine
SecondSalesLine
ReferenceSalesLine
InvoiceSalesLine
QuoteSalesLine
TestSalesLine
InvoiceLine
LastLine
wlRecSalesLine
ForSalesLine
CalcSalesLine
SynchronizingSalesLine
vkZeile2_loc
recSL
recTmp
recTmp2
recNew
LocOrderLines
LocReturnLines
CurrSalesLine
Verkaufszeile
PAR_SalesLines
BlanketSalesOrderLine



Nicht schlecht oder.
Die Benennung ist schwierig, aber es gibt eine einfache Möglichkeit, sicherzustellen, dass die Variablen- und Funktionsnamen mindestens von annehmbarer Qualität sind. Solange den Namen eine Art von Informationen hinzufügt, die der Rest des Codes nicht vermittelt, wird es für andere Entwickler einfacher, Ihren Code zu lesen. Der Grund, warum Benennung so wichtig ist, ist, dass Namen eine allgemeine Vorstellung davon geben können, was der C/AL Code ausführt. Mit anderen Worten ein guter Name kann Ihnen in Sekunden helfen, zu verstehen, was der C/AL Code oder das TSQL Statement tut.


Gerne beantworte ich Ihnen persönlich weitergehende Fragen zu diesem Thema. Kontaktieren Sie mich einfach über unser Kontaktformular oder per E-Mail an info@dynamicsproject.com!


Olav Treffurt