{"id":55001314,"date":"2021-08-01T00:00:00","date_gmt":"2021-07-31T10:13:30","guid":{"rendered":"http:\/\/access-im-unternehmen.aix-dev.de\/aiu\/?p=1314"},"modified":"-0001-11-30T00:00:00","modified_gmt":"-0001-11-30T00:00:00","slug":"Verwaiste_APIFunktionen_finden","status":"publish","type":"post","link":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/","title":{"rendered":"Verwaiste API-Funktionen finden"},"content":{"rendered":"<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/vg07.met.vgwort.de\/na\/d47f81056dc9478892addb15dfb7b9ed\" width=\"1\" height=\"1\" alt=\"\"><\/p>\n<p><b>Wenn Sie eine gr&ouml;&szlig;ere Anwendung pflegen m&uuml;ssen, kann es hin und wieder sinnvoll sein, nicht mehr verwendete Routinen rauszuwerfen oder zumindest auszukommentieren. Das ist gerade praktisch, wenn Sie die API-Funktionen von 32-Bit auf 64-Bit umstellen wollen: Um hier Arbeit zu sparen, k&ouml;nnen Sie erst einmal alle API-Funktionen auskommentieren, die nicht mehr ben&ouml;tigt werden. Um die verwaisten Routinen zu finden, gibt es verschiedene M&ouml;glichkeiten: Sie k&ouml;nnen dies durch Auskommentieren und Testen manuell erledigen, ein Tool wie MZ-Tools einsetzen oder auch ein selbst programmiertes Tool. Letzteres k&ouml;nnte der entsprechenden Funktion von MZ-Tools noch einen draufsetzen und auch die Aufrufe aus den Eigenschaften von Formularsteuerelementen oder Abfragen ermitteln.<\/b><\/p>\n<h2>Hintergrund: 32-Bit- versus 64-Bit-Access<\/h2>\n<p>Mit Office 2019 hat Microsoft erstmalig die 64-Bit-Variante des Office-Pakets als Standard bei der Installation festgelegt. Zuvor war das noch die 32-Bit-Version. Wer also nicht gezielt die 64-Bit-Version installieren wollte, erhielt dort noch die 32-Bit-Version.<\/p>\n<p>Das f&uuml;hrte dazu, dass hier und da das Problem auftauchte, dass die f&uuml;r 32-Bit-Anwendungen ausgelegten API-Funktionen unter VBA nicht mehr funktionierten. Sie mussten an einigen Stellen angepasst werden, damit sie mit der 64-Bit-Version kompatibel waren.<\/p>\n<p>Zu dieser Zeit konnte man Kunden in einigen F&auml;llen noch zur Neuinstallation von Access in der 32-Bit-Version bewegen &#8211; auch vor dem Hintergrund, dass auch wichtige Steuerelemente wie das <b>TreeView<\/b>-Steuerelement und andere Elemente der Bibliothek <b>MSCOMCTL.ocx <\/b>nur unter 32-Bit zur Verf&uuml;gung standen. Nunmehr ist auch das kein Grund mehr, nicht die 64-Bit-Version zu verwenden, denn die <b>MSCOMCTL.ocx<\/b>-Bibliothek steht nun auch dort zur Verf&uuml;gung.<\/p>\n<p>Also steht bei vielen Entwicklern nun auch die Migration von 32-Bit zu 64-Bit auf dem Programm. In den beiden Beitr&auml;gen <b>API-Funktionen finden und speichern <\/b>(<b>www.access-im-unternehmen.de\/1312<\/b>) und <b>API-Typen und -Konstanten finden und speichern <\/b>(<b>www.access-im-unternehmen.de\/1313<\/b>) haben wir bereits einige Vorbereitungen getroffen und Routinen programmiert, die alle API-Funktionen eines VBA-Projekts auslesen und in Tabellen schreiben &#8211; das Gleiche f&uuml;r die Konstanten und Deklarationen eines VBA-Projekts.<\/p>\n<p>Nun ben&ouml;tigen wir noch ein Werkzeug, mit dem wir entscheiden k&ouml;nnen, welche dieser Elemente &uuml;berhaupt in der Anwendung ben&ouml;tigt werden &#8211; und welche wir gegebenenfalls einfach auskommentieren k&ouml;nnen und nicht mehr anzupassen brauchen. Genau das erledigen wir in diesem Beitrag.<\/p>\n<h2>Woher kommen &uuml;berz&auml;hlige API-Funktionen<\/h2>\n<p>Eine Frage, die sich hier stellt, ist folgende: Woher kommen denn eigentlich &uuml;berz&auml;hlige API-Funktionen Sollte man nicht annehmen, dass der Programmierer nur die unbedingt ben&ouml;tigten API-Funktionen zu seinem VBA-Projekt hinzuf&uuml;gt Und das &uuml;berz&auml;hlige API-Funktionen nur dann anfallen, wenn man sich im jeweiligen Fall f&uuml;r eine alternative Technik entscheidet oder die Anforderung einfach wegf&auml;llt und man dann vergisst, die API-Funktion zu entfernen<\/p>\n<p>In der Tat gibt es meist komplette Module mit den Deklarationen von Typen, Konstanten und Variablen samt API-Funktionen, die einen zusammenh&auml;ngenden Bereich abdecken &#8211; beispielsweise die Verschl&uuml;sselung oder Grafikfunktionen. Wenn man eine ben&ouml;tigte API-Funktion in einem solchen Modul vorfindet, f&uuml;gt man es in der Regel auch komplett zum VBA-Projekt hinzu &#8211; einfach, weil es zu aufwendig erscheint, nur die ben&ouml;tigten Elemente zu verwenden. Wenn Sie jedoch ein komplettes Modul mit GDI-Funktionen zum Projekt hinzuf&uuml;gen und nur eine Funktion daraus nutzen, sollten Sie sp&auml;testens bei einer drohenden Migration von 32-Bit nach 64-Bit &uuml;berlegen, den Umfang auf die ben&ouml;tigten Elemente zu reduzieren.<\/p>\n<h2>Basis: Funktionsname<\/h2>\n<p>Wir wollen in diesem Beitrag davon ausgehen, dass eine mehr oder weniger gro&szlig;e Menge von API-Funktionen vorliegt, die wir entweder aus der Tabelle entnehmen, die wir im Beitrag <b>API-Funktionen finden und speichern<\/b> erstellt und gef&uuml;llt haben oder die wir einfach so als Parameter an die Funktion zum Untersuchen von Aufrufen dieser Funktion &uuml;bergeben.<\/p>\n<p>Damit ist auch schon das Grundger&uuml;st definiert: Wir ben&ouml;tigen eine VBA-Funktion, der wir den Namen einer API-Funktion &uuml;bergeben und die das komplette VBA-Projekt nach Aufrufen dieser Funktion durchsucht.<\/p>\n<p>Wie aber finden wir solche Aufrufe Dazu suchen wir nach Zeilen, die folgende Bedingungen erf&uuml;llen:<\/p>\n<ul>\n<li>Die Zeile enth&auml;lt den Namen der API-Funktion, gefolgt von einer &ouml;ffnenden Klammer &#8211; also zum Beispiel <b>Sleep(<\/b> -, gefolgt von einem Leerzeichen oder gefolgt von einem Zeilenumbruch.<\/li>\n<li>Die Zeile enth&auml;lt nicht die Deklaration der API-Funktion selbst. Diese ist leicht zu definieren, n&auml;mlich durch das Schl&uuml;sselwort <b>Declare<\/b>.<\/li>\n<li>Die Zeile ist keine Kommentarzeile.<\/li>\n<\/ul>\n<p>Ein API-Aufruf kann n&auml;mlich beispielsweise wie folgt aussehen:<\/p>\n<pre>Sleep 30 ''mit Leerzeichen\r\nlngDriveType = GetDriveType(\"c:\") ''mit &ouml;ffnender Klammer\r\nEmptyClipboard ''mit folgendem Zeilenumbruch<\/pre>\n<h2>Speichern der Ergebnisse in einer Tabelle<\/h2>\n<p>Im Beitrag <b>API-Funktionen finden und speichern <\/b>haben wir bereits eine Tabelle namens <b>tblAPIDeclarations <\/b>vorgestellt, in die wir mir einer ebenfalls in diesem Beitrag vorgestellten Routine alle Deklarationen von API-Funktionen eintragen.<\/p>\n<p>Diese Tabellen wollen wir f&uuml;r den vorliegenden Beitrag um ein Feld erweitern. Dieses soll den Namen <b>IsCalled <\/b>erhalten.<\/p>\n<p>Sobald wir den Aufruf einer der in der Tabelle gespeicherten API-Funktionen gefunden haben, stellen wir den Wert dieses Feldes auf den Wert <b>True <\/b>ein (siehe Bild 1).<\/p>\n<p class=\"image\"><img decoding=\"async\" src=\"..\/fileadmin\/_temp_\/2021_04\/pic_1314_001.png\" alt=\"Tabelle zum Speichern der API-Deklarationen eines VBA-Projekts\" width=\"524,559\" height=\"410,9946\" \/><\/p>\n<p><b><span style=\"color:darkgrey;\">Bild 1: Tabelle zum Speichern der API-Deklarationen eines VBA-Projekts<\/span><\/b><\/p>\n<h2>Prozedur zum Auffinden von API-Aufrufen<\/h2>\n<p>Die Prozedur <b>FindAPICalls<\/b> erwartet lediglich die &Uuml;bergabe des VB-Projekts als Parameter. Sie referenziert mit der Objektvariablen <b>db <\/b>das aktuelle <b>Database<\/b>-Objekt und nutzt dessen <b>Execute<\/b>-Methode, um mit einer <b>UPDATE<\/b>-Abfrage den Wert des Feldes <b>IsCalled <\/b>auf den Wert <b>False <\/b>einzustellen (siehe Listing 1).<\/p>\n<pre><span style=\"color:blue;\">Public Sub <\/span>FindAPICalls(objVBproject<span style=\"color:blue;\"> As <\/span>VBProject)\r\n     <span style=\"color:blue;\">Dim <\/span>objVBComponent<span style=\"color:blue;\"> As <\/span>VBComponent, objCodeModule<span style=\"color:blue;\"> As <\/span>CodeModule\r\n     <span style=\"color:blue;\">Dim <\/span>db<span style=\"color:blue;\"> As <\/span>DAO.Database, rst<span style=\"color:blue;\"> As <\/span>DAO.Recordset\r\n     <span style=\"color:blue;\">Dim <\/span>lngStartLine<span style=\"color:blue;\"> As Long<\/span>, lngEndLine<span style=\"color:blue;\"> As Long<\/span>, lngStartColumn<span style=\"color:blue;\"> As Long<\/span>, lngEndColumn<span style=\"color:blue;\"> As Long<\/span>\r\n     <span style=\"color:blue;\">Dim <\/span>strLine<span style=\"color:blue;\"> As String<\/span>\r\n     <span style=\"color:blue;\">Dim <\/span>bolApiCall<span style=\"color:blue;\"> As Boolean<\/span>, bolFound<span style=\"color:blue;\"> As Boolean<\/span>\r\n     <span style=\"color:blue;\">Set<\/span> db = CurrentDb\r\n     db.Execute \"UPDATE tblAPIDeclarations SET IsCalled = False\", dbFailOnError\r\n     <span style=\"color:blue;\">Set<\/span> rst = db.OpenRecordset(\"SELECT * FROM tblAPIDeclarations\", dbOpenDynaset)\r\n     <span style=\"color:blue;\">Do While<\/span> <span style=\"color:blue;\">Not<\/span> rst.EOF\r\n         <span style=\"color:blue;\">Debug.Print<\/span> rst!Api<span style=\"color:blue;\">Call<\/span>\r\n         For Each objVBComponent In objVBproject.VBComponents\r\n             <span style=\"color:blue;\">Set<\/span> objCodeModule = objVBComponent.CodeModule\r\n             lngStartLine = 0\r\n             lngStartColumn = 0\r\n             lngEndLine = 0\r\n             lngEndColumn = 0\r\n             bolFound = objCodeModule.Find(rst!Api<span style=\"color:blue;\">Call<\/span> & \"(\", lngStartLine, lngStartColumn, lngEndLine, lngEndColumn) _\r\n                 Or objCodeModule.Find(rst!Api<span style=\"color:blue;\">Call<\/span> & \" \", lngStartLine, lngStartColumn, lngEndLine, lngEndColumn) _\r\n                 Or objCodeModule.Find(rst!Api<span style=\"color:blue;\">Call<\/span> & <span style=\"color:blue;\">vbCrLf<\/span>, lngStartLine, lngStartColumn, lngEndLine, lngEndColumn)\r\n             <span style=\"color:blue;\">Do While<\/span> bolFound = <span style=\"color:blue;\">True<\/span>\r\n                 bolApi<span style=\"color:blue;\">Call<\/span> = <span style=\"color:blue;\">True<\/span>\r\n                 strLine = objCodeModule.Lines(lngStartLine, 1)\r\n                 strLine = <span style=\"color:blue;\">Trim<\/span>(strLine)\r\n                 <span style=\"color:blue;\">If <\/span><span style=\"color:blue;\">Not<\/span> <span style=\"color:blue;\">InStr<\/span>(1, strLine, \"''\") = 0<span style=\"color:blue;\"> Then<\/span>\r\n                     <span style=\"color:blue;\">If <\/span><span style=\"color:blue;\">InStr<\/span>(1, strLine, \"''\") &lt; <span style=\"color:blue;\">InStr<\/span>(1, strLine, rst!Api<span style=\"color:blue;\">Call<\/span>)<span style=\"color:blue;\"> Then<\/span>\r\n                         bolApi<span style=\"color:blue;\">Call<\/span> = <span style=\"color:blue;\">False<\/span>\r\n                     <span style=\"color:blue;\">End If<\/span>\r\n                 <span style=\"color:blue;\">End If<\/span>\r\n                 <span style=\"color:blue;\">If <\/span><span style=\"color:blue;\">Not<\/span> <span style=\"color:blue;\">InStr<\/span>(1, strLine, \"Declare \") = 0<span style=\"color:blue;\"> Then<\/span>\r\n                     bolApi<span style=\"color:blue;\">Call<\/span> = <span style=\"color:blue;\">False<\/span>\r\n                 <span style=\"color:blue;\">End If<\/span>\r\n                 <span style=\"color:blue;\">If <\/span>bolApi<span style=\"color:blue;\">Call<\/span> = <span style=\"color:blue;\">True<\/span><span style=\"color:blue;\"> Then<\/span>\r\n                     rst.Edit\r\n                     rst!IsCalled = <span style=\"color:blue;\">True<\/span>\r\n                     rst.Update\r\n                     <span style=\"color:blue;\">Exit For<\/span>\r\n                 <span style=\"color:blue;\">End If<\/span>\r\n                 lngStartLine = lngStartLine + 1\r\n                 lngEndLine = 0\r\n                 bolFound = objCodeModule.Find(rst!Api<span style=\"color:blue;\">Call<\/span> & \"(\", lngStartLine, lngStartColumn, lngEndLine, lngEndColumn) _\r\n                      Or objCodeModule.Find(rst!Api<span style=\"color:blue;\">Call<\/span> & \" \", lngStartLine, lngStartColumn, lngEndLine, lngEndColumn) _\r\n                     Or objCodeModule.Find(rst!Api<span style=\"color:blue;\">Call<\/span> & <span style=\"color:blue;\">vbCrLf<\/span>, lngStartLine, lngStartColumn, lngEndLine, lngEndColumn)\r\n             <span style=\"color:blue;\">Loop<\/span>\r\n         <span style=\"color:blue;\">Next<\/span> objVBComponent\r\n         rst.Move<span style=\"color:blue;\">Next<\/span>\r\n     <span style=\"color:blue;\">Loop<\/span>\r\n<span style=\"color:blue;\">End Sub<\/span><\/pre>\n<p><!--30percent--><\/p>\n<p><b><span style=\"color:darkgrey;\">Listing 1: Prozedur zum Ermitteln, ob eine API-Funktion verwendet wird<\/span><\/b><\/p>\n<p>Danach erstellt die Prozedur ein Recordset auf Basis der Tabelle <b>tblAPIDeclarations<\/b>. Dieses durchl&auml;uft sie anschlie&szlig;end in einer <b>Do While<\/b>-Schleife.<\/p>\n<p>In dieser Schleife untersucht sie f&uuml;r alle <b>VBComponent<\/b>-Objekte, also f&uuml;r alle Module, ob darin ein Aufruf der API-Funktion aus dem aktuellen Datensatz des Recordsets vorkommt. Deshalb durchlaufen wir in einer weiteren Schleife, diesmal des Typs <b>For Each<\/b>, alle <b>VBComponent<\/b>-Objekte der Auflistung <b>objVBComponents <\/b>des aktuellen VB-Projekts. Hier weisen wir der Variablen <b>objCodeModule <\/b>das <b>CodeModule<\/b>-Element von <b>objVBComponent <\/b>zu. Au&szlig;erdem stellen wir die Werte der Variablen <b>lngStartLine<\/b>, <b>lngStartColumn<\/b>, <b>lngEndLine <\/b>und <b>lngEndColumn <\/b>auf <b>0 <\/b>ein.<\/p>\n<p>Schlie&szlig;lich suchen wir mit der <b>Find<\/b>-Methode von <b>objCodeModule <\/b>nach dem ersten Auftreten des API-Aufrufs aus <b>rst!ApiCall<\/b>. Dabei kombinieren wir gleich drei Aufrufe dieser Funktion, die jeweils einen anderen Suchbegriff enthalten, mit dem <b>Or<\/b>-Schl&uuml;sselwort. Hier suchen wir nach den bereits genannten Erscheinungsformen des API-Aufrufs mit folgender &ouml;ffnender Klammer, folgendem Leerzeichen und folgendem Zeilenumbruch.<\/p>\n<p>Liefert eine der drei Aufrufe der <b>Find<\/b>-Funktion den Wert <b>True<\/b>, erh&auml;lt auch <b>bolFound <\/b>den Wert <b>True <\/b>und wir steigen in den ersten Durchlauf der nun folgenden <b>Do While<\/b>-Schleife ein. Diese verlassen wir erst, wenn die am Ende folgende erneute Abfrage weiterer Auftreten des API-Aufrufs keine Suchergebnisse mehr liefert &#8211; oder wenn wir zwischendurch ein Auftreten gefunden wurde, das alle Bedingungen erf&uuml;llt.<\/p>\n<p>Der Find-Aufruf erledigt noch mehr, wenn er erfolgreich ist. Dann schreibt er n&auml;mlich die genaue Position des Fundortes in die vier Parameter <b>lngStartLine<\/b>, <b>lngStartColumn<\/b>, <b>lngEndLine <\/b>und <b>lngEndColumn<\/b>. Das ist hilfreich, damit wir beim erneuten Aufruf angeben k&ouml;nnen, dass die Suche eine Spalte weiter erneut starten soll.<\/p>\n<p>In der <b>Do While<\/b>-Schleife stellen wir die Variable <b>bolApiCall <\/b>tempor&auml;r auf <b>True <\/b>ein. Dann lesen wir die Zeile mit dem API-Aufruf in die Variable <b>strLine <\/b>ein. Dazu nutzen wir die <b>Lines<\/b>-Funktion mit der Zeilennummer aus dem Parameter <b>lngStartLine <\/b>des Find-Aufrufs als Parameter.<\/p>\n<p>Anschlie&szlig;end pr&uuml;fen wir zuerst, ob die Zeile ein Kommentarzeichen enth&auml;lt. Ist das der Fall, pr&uuml;fen wir, ob sich dieses vor oder hinter dem Auftreten des API-Aufrufs bedindet. Ist ein Kommentarzeichen vorhanden und befindet es sich vor dem Aufruf, stellen wir <b>bolApiCall <\/b>auf <b>False <\/b>ein. Hier handelt es sich also um einen auskommentierten Aufruf.<\/p>\n<p>Diese Pr&uuml;fung auf einen auskommentierten Aufruf ist nicht hundertprozentig sicher, denn es kann vorkommen, dass das Ergebnis der API-Funktion direkt als Parameter einer anderen Funktion zum Einsatz kommt, die in einem vorherigen Parameter eine Zeichenkette mit einem oder mehreren Hochkommata als Parameter &uuml;bergibt. Dieser Fall ist allerdings recht unwahrscheinlich.<\/p>\n<p>Anschlie&szlig;end pr&uuml;fen wir, ob sich die <b>Declare<\/b>-Anweisung in der gleichen Zeile wir der Name der API-Funktion befindet. Ist das der Fall, haben wir keinen Aufruf der API-Funktion gefunden, sonderen ihre Deklaration. Auch in diesem Fall stellen wir <b>bolApiCall <\/b>auf <b>False <\/b>ein.<\/p>\n<p>Nur wenn bolApiCall danach noch den Wert True aufweist, handelt es sich um einen Aufruf der Api-Funktion. Dann versetzen wir den aktuellen Datensatz des Recordsets mit der <b>Edit<\/b>-Methode in den Bearbeitungsmodus, legen f&uuml;r das Feld <b>IsCalled <\/b>den Wert <b>True <\/b>fest und speichern die &Auml;nderung mit der Methode <b>Update <\/b>in der zugrunde liegenden Tabelle. Au&szlig;erdem verlassen wir die <b>For Each<\/b>-Schleife mit der <b>Exit For<\/b>-Funktion und wenden uns so dem n&auml;chsten Datensatz des Recordsets <b>rst <\/b>zu.<\/p>\n<p>An dieser Stelle kann es nun auch sein, dass wir zwar ein Vorkommen der API-Funktion mit folgender &ouml;ffnender Klammer, Leerzeichen oder Zeilenumbruch gefunden haben, dieses sich aber als die Deklaration der API-Funktion selbst herausgestellt hat.<\/p>\n<p>Dann wollen wir im aktuellen Modul weitersuchen. Deshalb erh&ouml;hen wir den Wert der Variablen <b>lngStartLine <\/b>um <b>1 <\/b>und stellen <b>lngEndLine <\/b>wieder auf <b>0 <\/b>ein.<\/p>\n<p>Auf diese Weise suchen die folgenden Aufrufe der <b>Find<\/b>-Methode ab der folgenden Zeile weiter.<\/p>\n<h2>Nutzung der Funktion<\/h2>\n<p>Wenn Sie die Funktionen aus den beiden oben genannten Beitr&auml;gen nutzen wollen, um die API-Funktionen zu ermitteln und in die Tabelle <b>tblAPIDeclarations <\/b>zu schreiben, k&ouml;nnen Sie den Aufruf der Funktion <b>FindAPICalls <\/b>direkt wie folgt in die entsprechende Prozedur einf&uuml;gen:<\/p>\n<pre><span style=\"color:blue;\">Public Sub <\/span>FindAPIDeclares()\r\n     <span style=\"color:blue;\">Dim <\/span>objVBproject<span style=\"color:blue;\"> As <\/span>VBProject\r\n     <span style=\"color:blue;\">Dim <\/span>objVBComponent<span style=\"color:blue;\"> As <\/span>VBComponent\r\n     <span style=\"color:blue;\">Dim <\/span>db<span style=\"color:blue;\"> As <\/span>DAO.Database\r\n     <span style=\"color:blue;\">Set<\/span> objVBproject = GetCurrentVBProject\r\n     <span style=\"color:blue;\">Set<\/span> db = CurrentDb\r\n     For Each objVBComponent In objVBproject.VBComponents\r\n         FindAPIDeclaresInModule objVBComponent\r\n         FindAPITypes objVBComponent\r\n         FindConstants objVBComponent\r\n     <span style=\"color:blue;\">Next<\/span> objVBComponent\r\n     FindAPICalls objVBproject\r\n<span style=\"color:blue;\">End Sub<\/span><\/pre>\n<p>Damit lesen Sie erst alle Deklarationen von API-Funktionen in die Tabelle ein und legen dann den Wert des Feldes <b>IsCalled <\/b>f&uuml;r die jeweilige API-Funktion fest.<\/p>\n<p>In einer Beispieldatenbank eines Kunden brauchten wir so nur noch 160 statt 252 API-Funktionen von 32-Bit nach 64-Bit zu migrieren.<\/p>\n<h2>Ein Schritt weiter: Aufrufe von Aufrufen pr&uuml;fen<\/h2>\n<p>Und wir sind noch nicht am Ende der M&ouml;glichkeiten angekommen. Es kann auch sein, dass ein Entwickler einmal die Deklaration einer API-Funktion zu einem Projekt hinzuf&uuml;gt, diese dann in einer Funktion nutzt, die wiederum in einer anderen Routine zum Einsatz kommt.<\/p>\n<p>Und diese andere Routine wird irgendwann gel&ouml;scht oder auskommentiert. Oder der Entwickler holt das Modul mit den API-Funktionen in das VBA-Projekt, experimentiert ein wenig in Testroutinen mit den enthaltenen Funktionen und stellt dann fest, dass er diese doch nicht mehr ben&ouml;tigt.<\/p>\n<p>Auch dann werden die Deklarationen der API-Routinen faktisch nicht mehr ben&ouml;tigt und Sie brauchen sich etwa im Falle einer Migration von 32-Bit nach 64-Bit nicht die M&uuml;he zu machen, diese API-Funktion zu ber&uuml;cksichtigen.<\/p>\n<p>Geschweige, dass Sie die verworfenen oder nur testweise angelegten Routinen weiter mitschleppen &#8211; Sie k&ouml;nnen diese einfach aus dem Projekt entfernen.<\/p>\n<p>Um herauszufinden, welche Routinen nicht mehr ben&ouml;tigt werden, ist allerdings ein etwas h&ouml;herer Aufwand erforderlich. Ein Grund ist, dass viele Routinen zwar nicht von einer anderen Routine aufgerufen werden, aber von anderen Stellen aus. Zum Beispiel finden Sie nirgends einen Aufruf einer Ereignisprozedur &#8211; dieser ist implizit in den Eigenschaften von Formularen, Berichten und Steuerelementen enthalten. Andere Funktionen werden vielleicht in Ausdr&uuml;cken in Abfragen oder in den Eigenschaften von Steuerelementen verwendet.<\/p>\n<p>Dies alles l&auml;sst sich nicht mehr allein &uuml;ber das Durchsuchen des VBA-Editors abdecken, sondern erfordert weitere Schritte wie das Speichern der Definitionen von Elementen in Textdateien und deren Analyse.<\/p>\n<h2>Downloads zu diesem Beitrag<\/h2>\n<p>Enthaltene Beispieldateien:<\/p>\n<p>VerwaisteRoutinen.accdb<\/p>\n<p><a href=\"..\/fileadmin\/beispiele\/D88DF171-13BE-4669-99A9-4E35FE9C6F3B\/aiu_1314.zip\">Download<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Wenn Sie eine gr&ouml;&szlig;ere Anwendung pflegen m&uuml;ssen, kann es hin und wieder sinnvoll sein, nicht mehr verwendete Routinen rauszuwerfen oder zumindest auszukommentieren. Das ist gerade praktisch, wenn Sie die API-Funktionen von 32-Bit auf 64-Bit umstellen wollen: Um hier Arbeit zu sparen, k&ouml;nnen Sie erst einmal alle API-Funktionen auskommentieren, die nicht mehr ben&ouml;tigt werden. Um verwaisten Routinen zu finden, gibt es verschiedene M&ouml;glichkeiten: Sie k&ouml;nnen dies durch Auskommentieren und Testen von Hand erledigen, ein Tool wie MZ-Tools einsetzen oder auch ein selbst programmiertes Tool. Letzteres k&ouml;nnte der entsprechenden Funktion von MZ-Tools noch einen draufsetzen und auch die Aufrufe aus den Eigenschaften von Formularsteuerelementen oder Abfragen ermitteln.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"om_disable_all_campaigns":false,"_monsterinsights_skip_tracking":false,"_monsterinsights_sitenote_active":false,"_monsterinsights_sitenote_note":"","_monsterinsights_sitenote_category":0,"_uf_show_specific_survey":0,"_uf_disable_surveys":false,"footnotes":""},"categories":[662021,66042021,44000025],"tags":[],"class_list":["post-55001314","post","type-post","status-publish","format-standard","hentry","category-662021","category-66042021","category-VBA_und_Programmiertechniken"],"yoast_head":"<!-- This site is optimized with the Yoast SEO Premium plugin v20.9 (Yoast SEO v27.7) - https:\/\/yoast.com\/product\/yoast-seo-premium-wordpress\/ -->\n<title>Verwaiste API-Funktionen finden - Access im Unternehmen<\/title>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/\" \/>\n<meta property=\"og:locale\" content=\"de_DE\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"Verwaiste API-Funktionen finden\" \/>\n<meta property=\"og:description\" content=\"Wenn Sie eine gr&ouml;&szlig;ere Anwendung pflegen m&uuml;ssen, kann es hin und wieder sinnvoll sein, nicht mehr verwendete Routinen rauszuwerfen oder zumindest auszukommentieren. Das ist gerade praktisch, wenn Sie die API-Funktionen von 32-Bit auf 64-Bit umstellen wollen: Um hier Arbeit zu sparen, k&ouml;nnen Sie erst einmal alle API-Funktionen auskommentieren, die nicht mehr ben&ouml;tigt werden. Um verwaisten Routinen zu finden, gibt es verschiedene M&ouml;glichkeiten: Sie k&ouml;nnen dies durch Auskommentieren und Testen von Hand erledigen, ein Tool wie MZ-Tools einsetzen oder auch ein selbst programmiertes Tool. Letzteres k&ouml;nnte der entsprechenden Funktion von MZ-Tools noch einen draufsetzen und auch die Aufrufe aus den Eigenschaften von Formularsteuerelementen oder Abfragen ermitteln.\" \/>\n<meta property=\"og:url\" content=\"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/\" \/>\n<meta property=\"og:site_name\" content=\"Access im Unternehmen\" \/>\n<meta property=\"article:published_time\" content=\"2021-07-31T10:13:30+00:00\" \/>\n<meta property=\"og:image\" content=\"http:\/\/vg07.met.vgwort.de\/na\/d47f81056dc9478892addb15dfb7b9ed\" \/>\n<meta name=\"author\" content=\"Andr\u00e9 Minhorst\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:label1\" content=\"Verfasst von\" \/>\n\t<meta name=\"twitter:data1\" content=\"Andr\u00e9 Minhorst\" \/>\n\t<meta name=\"twitter:label2\" content=\"Gesch\u00e4tzte Lesezeit\" \/>\n\t<meta name=\"twitter:data2\" content=\"11\u00a0Minuten\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\\\/\\\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/#article\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/\"},\"author\":{\"name\":\"Andr\u00e9 Minhorst\",\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/#\\\/schema\\\/person\\\/13395c4bcd7d7963efe33be9c584d93f\"},\"headline\":\"Verwaiste API-Funktionen finden\",\"datePublished\":\"2021-07-31T10:13:30+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/\"},\"wordCount\":1915,\"commentCount\":0,\"publisher\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/#organization\"},\"image\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/#primaryimage\"},\"thumbnailUrl\":\"http:\\\/\\\/vg07.met.vgwort.de\\\/na\\\/d47f81056dc9478892addb15dfb7b9ed\",\"articleSection\":[\"2021\",\"4\\\/2021\",\"VBA und Programmiertechniken\"],\"inLanguage\":\"de\",\"potentialAction\":[{\"@type\":\"CommentAction\",\"name\":\"Comment\",\"target\":[\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/#respond\"]}]},{\"@type\":\"WebPage\",\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/\",\"url\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/\",\"name\":\"Verwaiste API-Funktionen finden - Access im Unternehmen\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/#website\"},\"primaryImageOfPage\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/#primaryimage\"},\"image\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/#primaryimage\"},\"thumbnailUrl\":\"http:\\\/\\\/vg07.met.vgwort.de\\\/na\\\/d47f81056dc9478892addb15dfb7b9ed\",\"datePublished\":\"2021-07-31T10:13:30+00:00\",\"breadcrumb\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/#breadcrumb\"},\"inLanguage\":\"de\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/\"]}]},{\"@type\":\"ImageObject\",\"inLanguage\":\"de\",\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/#primaryimage\",\"url\":\"http:\\\/\\\/vg07.met.vgwort.de\\\/na\\\/d47f81056dc9478892addb15dfb7b9ed\",\"contentUrl\":\"http:\\\/\\\/vg07.met.vgwort.de\\\/na\\\/d47f81056dc9478892addb15dfb7b9ed\"},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/Verwaiste_APIFunktionen_finden\\\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\\\/\\\/access-im-unternehmen.de\\\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Verwaiste API-Funktionen finden\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/#website\",\"url\":\"https:\\\/\\\/access-im-unternehmen.de\\\/\",\"name\":\"Access im Unternehmen\",\"description\":\"Das Magazin f\u00fcr Datenbankentwickler auf Basis von Microsoft Access\",\"publisher\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/#organization\"},\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\\\/\\\/access-im-unternehmen.de\\\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"de\"},{\"@type\":\"Organization\",\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/#organization\",\"name\":\"Andr\u00e9 Minhorst Verlag\",\"url\":\"https:\\\/\\\/access-im-unternehmen.de\\\/\",\"logo\":{\"@type\":\"ImageObject\",\"inLanguage\":\"de\",\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/#\\\/schema\\\/logo\\\/image\\\/\",\"url\":\"https:\\\/\\\/access-im-unternehmen.de\\\/wp-content\\\/uploads\\\/2019\\\/09\\\/aiu_wp.png\",\"contentUrl\":\"https:\\\/\\\/access-im-unternehmen.de\\\/wp-content\\\/uploads\\\/2019\\\/09\\\/aiu_wp.png\",\"width\":370,\"height\":111,\"caption\":\"Andr\u00e9 Minhorst Verlag\"},\"image\":{\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/#\\\/schema\\\/logo\\\/image\\\/\"}},{\"@type\":\"Person\",\"@id\":\"https:\\\/\\\/access-im-unternehmen.de\\\/#\\\/schema\\\/person\\\/13395c4bcd7d7963efe33be9c584d93f\",\"name\":\"Andr\u00e9 Minhorst\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"de\",\"@id\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/1b9d010cf1716692cb9c34f21554e07d17d461acaea5b61b8cb21cbec678d48a?s=96&d=mm&r=g\",\"url\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/1b9d010cf1716692cb9c34f21554e07d17d461acaea5b61b8cb21cbec678d48a?s=96&d=mm&r=g\",\"contentUrl\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/1b9d010cf1716692cb9c34f21554e07d17d461acaea5b61b8cb21cbec678d48a?s=96&d=mm&r=g\",\"caption\":\"Andr\u00e9 Minhorst\"}}]}<\/script>\n<!-- \/ Yoast SEO Premium plugin. -->","yoast_head_json":{"title":"Verwaiste API-Funktionen finden - Access im Unternehmen","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/","og_locale":"de_DE","og_type":"article","og_title":"Verwaiste API-Funktionen finden","og_description":"Wenn Sie eine gr&ouml;&szlig;ere Anwendung pflegen m&uuml;ssen, kann es hin und wieder sinnvoll sein, nicht mehr verwendete Routinen rauszuwerfen oder zumindest auszukommentieren. Das ist gerade praktisch, wenn Sie die API-Funktionen von 32-Bit auf 64-Bit umstellen wollen: Um hier Arbeit zu sparen, k&ouml;nnen Sie erst einmal alle API-Funktionen auskommentieren, die nicht mehr ben&ouml;tigt werden. Um verwaisten Routinen zu finden, gibt es verschiedene M&ouml;glichkeiten: Sie k&ouml;nnen dies durch Auskommentieren und Testen von Hand erledigen, ein Tool wie MZ-Tools einsetzen oder auch ein selbst programmiertes Tool. Letzteres k&ouml;nnte der entsprechenden Funktion von MZ-Tools noch einen draufsetzen und auch die Aufrufe aus den Eigenschaften von Formularsteuerelementen oder Abfragen ermitteln.","og_url":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/","og_site_name":"Access im Unternehmen","article_published_time":"2021-07-31T10:13:30+00:00","og_image":[{"url":"http:\/\/vg07.met.vgwort.de\/na\/d47f81056dc9478892addb15dfb7b9ed","type":"","width":"","height":""}],"author":"Andr\u00e9 Minhorst","twitter_card":"summary_large_image","twitter_misc":{"Verfasst von":"Andr\u00e9 Minhorst","Gesch\u00e4tzte Lesezeit":"11\u00a0Minuten"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/#article","isPartOf":{"@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/"},"author":{"name":"Andr\u00e9 Minhorst","@id":"https:\/\/access-im-unternehmen.de\/#\/schema\/person\/13395c4bcd7d7963efe33be9c584d93f"},"headline":"Verwaiste API-Funktionen finden","datePublished":"2021-07-31T10:13:30+00:00","mainEntityOfPage":{"@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/"},"wordCount":1915,"commentCount":0,"publisher":{"@id":"https:\/\/access-im-unternehmen.de\/#organization"},"image":{"@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/#primaryimage"},"thumbnailUrl":"http:\/\/vg07.met.vgwort.de\/na\/d47f81056dc9478892addb15dfb7b9ed","articleSection":["2021","4\/2021","VBA und Programmiertechniken"],"inLanguage":"de","potentialAction":[{"@type":"CommentAction","name":"Comment","target":["https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/#respond"]}]},{"@type":"WebPage","@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/","url":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/","name":"Verwaiste API-Funktionen finden - Access im Unternehmen","isPartOf":{"@id":"https:\/\/access-im-unternehmen.de\/#website"},"primaryImageOfPage":{"@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/#primaryimage"},"image":{"@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/#primaryimage"},"thumbnailUrl":"http:\/\/vg07.met.vgwort.de\/na\/d47f81056dc9478892addb15dfb7b9ed","datePublished":"2021-07-31T10:13:30+00:00","breadcrumb":{"@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/#breadcrumb"},"inLanguage":"de","potentialAction":[{"@type":"ReadAction","target":["https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/"]}]},{"@type":"ImageObject","inLanguage":"de","@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/#primaryimage","url":"http:\/\/vg07.met.vgwort.de\/na\/d47f81056dc9478892addb15dfb7b9ed","contentUrl":"http:\/\/vg07.met.vgwort.de\/na\/d47f81056dc9478892addb15dfb7b9ed"},{"@type":"BreadcrumbList","@id":"https:\/\/access-im-unternehmen.de\/Verwaiste_APIFunktionen_finden\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/access-im-unternehmen.de\/"},{"@type":"ListItem","position":2,"name":"Verwaiste API-Funktionen finden"}]},{"@type":"WebSite","@id":"https:\/\/access-im-unternehmen.de\/#website","url":"https:\/\/access-im-unternehmen.de\/","name":"Access im Unternehmen","description":"Das Magazin f\u00fcr Datenbankentwickler auf Basis von Microsoft Access","publisher":{"@id":"https:\/\/access-im-unternehmen.de\/#organization"},"potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/access-im-unternehmen.de\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"de"},{"@type":"Organization","@id":"https:\/\/access-im-unternehmen.de\/#organization","name":"Andr\u00e9 Minhorst Verlag","url":"https:\/\/access-im-unternehmen.de\/","logo":{"@type":"ImageObject","inLanguage":"de","@id":"https:\/\/access-im-unternehmen.de\/#\/schema\/logo\/image\/","url":"https:\/\/access-im-unternehmen.de\/wp-content\/uploads\/2019\/09\/aiu_wp.png","contentUrl":"https:\/\/access-im-unternehmen.de\/wp-content\/uploads\/2019\/09\/aiu_wp.png","width":370,"height":111,"caption":"Andr\u00e9 Minhorst Verlag"},"image":{"@id":"https:\/\/access-im-unternehmen.de\/#\/schema\/logo\/image\/"}},{"@type":"Person","@id":"https:\/\/access-im-unternehmen.de\/#\/schema\/person\/13395c4bcd7d7963efe33be9c584d93f","name":"Andr\u00e9 Minhorst","image":{"@type":"ImageObject","inLanguage":"de","@id":"https:\/\/secure.gravatar.com\/avatar\/1b9d010cf1716692cb9c34f21554e07d17d461acaea5b61b8cb21cbec678d48a?s=96&d=mm&r=g","url":"https:\/\/secure.gravatar.com\/avatar\/1b9d010cf1716692cb9c34f21554e07d17d461acaea5b61b8cb21cbec678d48a?s=96&d=mm&r=g","contentUrl":"https:\/\/secure.gravatar.com\/avatar\/1b9d010cf1716692cb9c34f21554e07d17d461acaea5b61b8cb21cbec678d48a?s=96&d=mm&r=g","caption":"Andr\u00e9 Minhorst"}}]}},"_links":{"self":[{"href":"https:\/\/access-im-unternehmen.de\/data\/wp\/v2\/posts\/55001314","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/access-im-unternehmen.de\/data\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/access-im-unternehmen.de\/data\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/access-im-unternehmen.de\/data\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/access-im-unternehmen.de\/data\/wp\/v2\/comments?post=55001314"}],"version-history":[{"count":0,"href":"https:\/\/access-im-unternehmen.de\/data\/wp\/v2\/posts\/55001314\/revisions"}],"wp:attachment":[{"href":"https:\/\/access-im-unternehmen.de\/data\/wp\/v2\/media?parent=55001314"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/access-im-unternehmen.de\/data\/wp\/v2\/categories?post=55001314"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/access-im-unternehmen.de\/data\/wp\/v2\/tags?post=55001314"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}