Defekte Verweise: Ursachen und Lösungen

In diesem dritten Teil der Beitrags-Reihe rund um das Thema “Verweise” steigen wir tiefer in die Materie ein: Wie löst Access beziehungsweise VBA Verweise überhaupt auf Was läuft bei defekten Verweisen schief Und welche manuellen und welche VBA-Techniken gibt es, um solche Probleme zu lösen All dies erfahren Sie im vorliegenden Beitrag.

Um die von Verweisen ausgehenden Probleme zu verstehen, sollten Sie wissen, wie Access, genauer VBA, vorgeht, um die Bibliothek eines Befehls zu finden.

Disambiguation

VBA verwendet Disambiguation, um die passende Bibliothek für ein Objekt oder eine Methode zu finden. Wenn VBA (unbekannte) Objekte im Code findet, erfolgt die Suche in der folgenden Reihenfolge:

  • im eigenen Modul,
  • in anderen Standardmodulen des VBA-Projekts,
  • in den Verweisen in der Reihenfolge ihrer Priorität
  • und in den eingebauten Verweisen (VBA und Access).

Woher weiß VBA beispielsweise, was sich hinter dem Befehl Left$ verbirgt VBA prüft als Erstes, ob es in dem Modul, in dem es diese Codezeile findet, eine private oder öffentliche Funktion mit dem Namen Left$ gibt. Wenn eine Funktion mit dem Namen Left$ in diesem Modul vorhanden ist, verwendet es diese Funktion. Wenn das Modul kein passende Funktion enthält, prüft Access, ob in den anderen Standardmodulen der Datenbank eine öffentliche Funktion mit dem Namen Left$ vorhanden ist.

Offenbart das gesamte VBA-Projekt keine Funktion mit dem Namen Left$, durchsucht Access als Nächstes alle nicht eingebauten Verweise der Datenbank (also alle außer Access und VBA) in der Reihenfolge ihrer Priorität. Findet Access auch in diesen Verweisen nichts, untersucht es die eingebauten Verweise VBA und Access nach diesem Befehl. Im Fall von Left$ führt dies im Modul Strings der Bibliothek VBA zum Erfolg.

Sie können diesen Prozess mit der Beispieldatenbank Demo.Disambiguation.mdb nachvollziehen. Sorgen Sie vor dem Start dafür, dass die Bibliotheksdatenbank mit dem Namen Lib.Disambiguation.mdb im selben Verzeichnis wie die Beispieldatenbank liegt.

In der Beispieldatenbank können Sie über eine Schaltfläche zum VBA-Code wechseln. Setzen Sie dort den Cursor in den Befehl Left$. Wählen Sie den Eintrag Definition aus dem Kontextmenü aus und schauen Sie, wo sich der Befehl befindet.

Kommentieren Sie nun die gefundene Funktion aus und wählen Sie erneut Definition. Wiederholen Sie diese Schritte so lange, bis der Objektkatalog am Ende den Befehl Left$ anzeigt.

Disambiguation vermeiden

Sie können vermeiden, dass VBA auf der Suche nach der passenden Bibliothek den Prozess der Disambiguation durchläuft. Stellen Sie dazu dem Befehlswort den Namen der zu verwendenden Bibliothek und/oder des zu verwendenden Moduls voran. Im Fall von Left$ würden Sie dann Folgendes schreiben:

If VBA.Left$(Me!txtName,1)="M" Then

Wenn Sie einen Befehl aus der Access-Bibliothek verwenden wollen, schreiben Sie beispielsweise:

    Access.Application.Run

Für den Aufruf einer Funktion mit dem Namen MyFunction aus dem Modul basMyModul schreiben Sie:

    basMyModul.MyFunction

Wenn sich das Modul in einer als Verweis eingebundenen Bibliothek befindet, stellen Sie den Namen der Bibliothek zusätzlich voran. Bezogen auf das vorherige Beispiel haben Sie nun folgende Möglichkeiten:

    MyLib.MyFunction
    MyLib.basMyModul.MyFunction

Sie können VBA die Arbeit abnehmen und die Befehle vollständig qualifiziert ausschreiben, Sie müssen es aber nicht. Wenn Sie es tun, nehmen Sie VBA nicht nur die Suche nach der richtigen Bibliothek ab. Sie legen auch definitiv fest, welche Bibliothek verwendet wird. Das ist insbesondere dann von Bedeutung, wenn ein Objekt oder eine Methode in mehreren Bibliotheken zugleich vorhanden ist.

Ein Beispiel hierfür ist das Recordset-Objekt. Das Recordset-Objekt ist in den Bibliotheken ADODB und DAO zu finden. Wenn Sie bei der Deklaration des Recordset-Objekts keine spezielle Bibliothek angeben und nur eine der beiden Bibliotheken per Verweis eingebunden ist, verwendet Access diese, sonst die mit der höheren Priorität.

Geben Sie hingegen bei der Deklaration des Recordset-Objekts bereits die zu verwendende Bibliothek an, verwendet VBA die “richtige” Bibliothek. Wenn der zugehörige Verweis fehlt, erhalten Sie bereits beim Kompilieren eine Fehlermeldung.

    'Deklaration ohne Bibliothek
    Dim rst As RecordSet
    'Deklaration mit Bibliothek
    Dim rst As DAO.RecordSet

Prüfen der Verweise

Wenn VBA prüfen will, ob ein Objekt in der Type Library eines Verweises enthalten ist, ermittelt es den intern gespeicherten GUID zu diesem Verweis. Mit dieser Information fragt VBA die Registry ab. Als Ergebnis erhält VBA letztlich den Pfad zur Datei mit der Type Library zurück.

Wenn sich diese Datei am erwarteten Ort befindet, lädt VBA sie in den Speicher und prüft, ob diese Type Library Informationen zu dem gesuchten Objekt enthält. Enthält die Type Library das Objekt nicht, sucht VBA in den anderen Verweisen in der Reihenfolge ihrer Priorität weiter. Als Letztes kommen dabei die eingebauten Verweise Access und VBA zum Zuge.

Wenn VBA den gesuchten Befehl nicht finden konnte, quittiert VBA dies beim Kompilieren mit der Fehlermeldung Sub oder Function nicht definiert.

Den gesamten Prozess können Sie Bild 1 und Abb. 2 nachvollziehen. Aus diesen Schaubildern lassen sich folgende Erkenntnisse ableiten: Aus der Tatsache, dass Access Befehle zuerst im VBA-Projekt der Anwendung sucht, wird deutlich, dass Sie die Befehle, die VBA bereitstellt, durch eine eigene Version ersetzen können. Welche Möglichkeiten sich daraus ergeben und worauf Sie dabei achten sollten, wird in einem gesonderten Beitrag beschrieben.

missing image file

Bild 1: Vom Befehl im VBA-Code …

missing image file

Bild 2: … zur passenden Bibliothek

Wenn VBA beim Versuch, eine Type Library zu laden, auf ein Problem stößt, bricht der Prozess der Disambiguation ab. VBA lässt dann nicht etwa die fehlerhafte Bibliothek aus und sucht in den anderen Bibliotheken weiter, sondern bricht den Prozess komplett ab.

Wenn Sie sich nochmals in Erinnerung rufen, dass VBA die eingebauten Verweise erst am Ende durchsucht, wird deutlich, warum VBA so oft behauptet, der Befehl Left$ könne nicht gefunden werden. Dies liegt wohl ganz einfach daran, dass VBA auf der Suche nach der richtigen Bibliothek auf einen anderen, fehlerhaften Verweis gestoßen ist.

Fehlerhafte Verweise

Nachdem jetzt klar ist, was bei einem defekten Verweis passiert, ist es an der Zeit zu überlegen, wie es zu defekten Verweisen kommen kann.

Ein Verweis ist fehlerhaft, wenn auf dem ausführenden Rechner nicht dieselbe Version einer Bibliothek registriert ist, sie gar nicht registriert ist oder wenn die registrierte Datei nicht gefunden werden kann. Die Gründe dafür sind vielfältig. So kann es zum Beispiel sein, dass auf dem ausführenden Rechner eine ältere oder eine neuere Version einer Bibliothek registriert ist.

Es kann aber auch passieren, dass ein Verweis komplett fehlt. Dies kann dann der Fall sein, wenn die Type Library auf diesem Rechner (noch) nicht registriert worden ist oder wenn die Registrierung aufgehoben wurde, weil beispielsweise eine Komponente vom System entfernt wurde. Zu einem fehlerhaften Verweis kommt es auch, wenn die registrierte Datei umbenannt, verschoben oder gelöscht wurde.

Auch das Durchbrechen der so genannten binären Kompatibilität führt zu einem fehlerhaften Verweis. Dafür, dass dies nicht passiert, ist der Programmierer der Komponente verantwortlich. Leider passieren hier hin und wieder Fehler, auf die Sie keinen Einfluss haben.

Wo erfolgt Disambiguation

Als Nächstes ist zu überlegen, wann und wo VBA es überall mit Verweisen zu tun haben kann. Daraus ergibt sich dann, wann und wo sich ein Fehler in den Verweisen auswirken kann. Der Prozess der Disambiguation erfolgt zum einen in VBA, zum anderen wird dieser Prozess aber auch vom (Jet) Expression Service genutzt. Der Expression Service ist dafür verantwortlich, dass Ausdrücke ausgewertet werden. Solche Ausdrücke können an folgenden Stellen verwendet werden:

  • Abfragen
  • Steuerelemente
  • Feldeigenschaften

Auch in diesen Ausdrücken können Sie VBA-Befehle verwenden. Der Expression-Service sorgt dann dafür, dass das richtige Ergebnis ermittelt wird, und gibt dieses zurück an die Abfrage oder an das Steuerelement.

Unterschiede in MDB und MDE ()

Lassen Sie uns kurz die Frage betrachten, ob es Unterschiede zwischen einer .mdb-Datei und einer .mde-Datei gibt, wenn es um Verweise geht. In einer nicht kompilierten .mdb-Datei wird der Code modulweise geladen. Das gesamte Modul wird interpretiert. Dabei werden die passenden Klassen gesucht. Wenn dabei ein fehlerhafter Verweis gefunden wird, kommt es zur Fehlermeldung.

In einer kompilierten .mdb-Datei und in einer .mde-Datei ist der Ablauf etwas anders. Dort ist der Code bereits kompiliert. Es erfolgt also keine Suche mehr nach der passenden Klasse. Dies ist bereits bei der Kompilierung erfolgt. Wenn jetzt aber ein fehlerhafter Verweis geladen werden soll, gibt es auch in diesem Fall eine Fehlermeldung. Im Ergebnis unterscheiden sich .mdb-Datei und .mde-Datei also nicht. Wenn fehlerhafte Verweise vorhanden sind, führt dies zu einem Fehler.

Sie haben das Ende des frei verfügbaren Textes erreicht. Möchten Sie ...

TestzugangOder bist Du bereits Abonnent? Dann logge Dich gleich hier ein. Die Zugangsdaten findest Du entweder in der aktuellen Print-Ausgabe auf Seite U2 oder beim Online-Abo in der E-Mail, die Du als Abonnent regelmäßig erhältst:

Schreibe einen Kommentar