Kategorie-Archiv: VBA

VBA-Related

Access Migration: Stolperstein Rechtsklick

Ein weiterer Stolperstein bei der Migration von älteren Access Versionen auf die aktuelle Access 2007er Version.
Bei einigen Formularen führt ein Rechtklick auf einen Totalabsturz der Applikation. Das Verhalten tritt häufig auf, wenn Unterformulare im Spiel sind, ein eindeutiges Muster lässt sich aber nicht erkennen.

Auch hierfür hat Microsoft einen Hotfix herausgebracht, der das Problem in den Griff bekommt. Zu bekommen ist der Hotfix im KB-Artikel 952699 mit der offiziellen Beschreibung (u.a.) "On a client computer that is running a Japanese version of the operating system, Access 2007 may stop responding when you right-click the subform on a database form.".
Lassen Sie sich nicht irritieren von der japanischen Sprachversion. In unserem Umfeld löste dieser Hotfix das Problem auch auf englischen und deutschen Sprachversionen.

Access Migration: Stolperstein Performance

Eigentlich mag man glauben, dass mit einer Umstellung auf eine neuere Softwareversion alles ein wenig besser und schneller wird. Bei der Migration von Access-Datenbanken und Access-Datenbankprojekten von 2000/ 2003/ XP auf Access 2007 gibt es hierbei aber mitunter eine Überraschung:
Die Performance kann weitaus schlechter sein. Gerade bei der Migration von Access-Projekten (ADP) habe ich dieses öfters festgestellt und wurden Performanceverluste von bis zu 250% gemessen.

Der entscheidende Hinweis zum Umgehung dieser Performanceeinbuße ist in einem Knowledge-Base-Artikel bei Microsoft zu finden. Es existiert nämlich ein Hotfix der hier helfen kann. Erreichbar unter
KB 936519 und bietet laut offizieller Beschreibung die folgenden Hilfe: "When you try to run a Microsoft Access project (.adp) in Access 2007, the project may run slowly. Or, the project may take longer than expected to respond to actions that are performed on the project."

Access Migration: Stolperstein “Benutzerdefinierte Toolbars”

Kürzlich habe ich bei einer Migration von Access2000 zu Access2007 festgestellt, dass eine in Access 2000 benutzerdefinierte Toolbar in Access 2007 nicht unbedingt das zu erwartende Verhalten an den Tag legt.
Konkret wurde in der Access 2000 Version beim Öffnen von Berichten eine benutzerdefinierte Toolbar eingeblendet, die unter anderem auch einen Standard-Schließen Button hatte. Im Zuge der Migration nach 2007 fiel dann auf, dass dieser Standard-Schließen Button nicht mehr funktioniert.
Ich habe mir dann mit einem kleinen Workaround geholfen, der zwar nicht wirklich elegant ist, aber in Anbetracht der begrenzten Anzahl von Reports in dieser Applikation einen guten Dienst erweist und sich vor allem als Access 2000- und Access 2007-tauglich erweist.

Der Standard-Close-Button wurde entfernt, stattdessen ein Button in der Toolbar integriert, der ein Makro aufruf. Dieses Makro wiederrum ruft die folgende Funktion auf:

Public Function CloseCurrentReport()
    Dim vReport As Variant
    With CurrentProject
        For Each vReport In .AllReports
            If CurrentProject.AllReports(vReport.Name).IsLoaded Then
                DoCmd.Close acReport, vReport.Name, acSaveNo
                Exit For
            End If
        Next vReport
    End With
End Function

Manchmal muss man eben auch die Wege gehen, die nicht ganz so schick sind.

Errorhandling in VBA. Teil 1.

Grundlagen 1/2

VBA bringt mit „On Error“ ein eigenes Konstrukt zur Fehlerbehandlung mit. Grundsätzlich gibt es zwei Arten wie man in VBA auf einen Fehler reagieren kann.
1. Ignorieren
2. Reagieren

Während im ersten Teil das Thema „ignorieren“ behandelt wird, wird sich der zweite Teil mit dem Thema „reagieren“ auseinandersetzen.

Der Standardfall.
Nehmen wir als Anschauungsobjekt eine einfache Prozedur. Nennen wir sie kreativerweise mal „RaisingError“. Diese Funktion kann erstmal recht wenig und sieht wie folgt aus:

Public Sub RaisingError
	debug.print 1 / 0
End Sub

Führen wir diese Funktion aus, erhalten wir eine Fehlermeldung in Form einer Dialogbox in wir die Ausführung beenden können, oder in die Debug-Umgebung springen können.
Für einen Entwickler ist das sicherlich noch kein Beinbruch, aber für einen Anwender ist das schnell die totale Überforderung. Erstens weiß dieser im Zweifel nichts mit „Debuggen“ anzufangen, und erst recht wird er im VBA-Editor nicht seine zweite Heimat haben, am wichtigsten aber ist, dass er keine Ahnung von dem Code haben wird, den ihr geschrieben habt. Also, was soll der arme Mensch dann in der Debug-Umgebung…

Fehler ignorieren. On Error Resume Next
Setzen wir bei der obigen Prozedur mal ein “On Error Resume Next” vor die 1. Zeile und starten die Prozedur erneut. Die Dialogbox, die uns darauf aufmerksam macht, dass eine Division durch Null ein Fehler ist, taucht nun nicht auf. Der Fehler wird schlicht ignoriert. Das ist auch gut so, jedenfalls in dem hier vorliegenden Fall.

Public Sub RaisingError
	On Error Resume Next

	debug.print 1 / 0
End Sub

Der ausgelöste Fehler wird zwar ignoriert, dennoch lässt er sich anzeigen. Hierfür können wir das Err-Objekt abfragen. Das Err-Objekt hat, neben ein paar anderen, zwei zentrale Eigenschaften: Number und Description. In Number wird der als letztes aufgetretene Fehlercode festgehalten, in Description eine manchmal mehr, manchmal weniger aussagekräftige Fehloerbeschreibung. Ein Fehler mit dem Fehlercode 0 ist dabei ein „Kein Fehler aufgetreten“-Antifehler.
Für unser obiges Beispiel heißt das, dass wir nach der 2.Zeile prüfen könnten, ob bei der geplanten Debug-Ausgabe ein Fehler aufgetreten ist. Wenn das der Fall ist, dann müsste der Fehlercode im Err-Objekt ungleich 0 sein.

Public Sub RaisingError
	On Error Resume Next

	debug.print 1 / 0

	If Err.Number <> 0 Then
		Debug.Print “Hier ist ein Fehler aufgetreten.”
		Debug.Print „Genauer: Fehlercode „ & Err.Number & „ Beschreibung: „ & Err.Description
	End If
End Sub

Nun muss man hier aber noch eine Anmerkung unterbringen. Sehen wir uns die folgende Prozedur an:

Public Sub RaisingError
	On Error Resume Next

	debug.print 1 / 0

	debug.print 1 + 2

	If Err.Number <> 0 Then
		Debug.Print “Hier ist ein Fehler aufgetreten.”
		Debug.Print „Genauer: Fehlercode „ & Err.Number & „ Beschreibung: „ & Err.Description
	End If
End Sub

Hier ist in der uns wohl bekannten Zeile der „übliche“ Fehler aufgetreten, in der folgenden Zeile wird eine einfache Addition ausgeführt bei der kein Fehler auftreten sollte. Dennoch finden wir in der folgenden Zeile bei der Fehlercode-Abfrage einen Fehler der ungleich 0 ist. Sprich: der letzte vorkommende Fehler muss zurückgesetzt werden um ein wirklich verlässliches Ergebnis zu erhalten. Hierfür kommt die Methode „Clear“ des Err-Objekts zum Einsatz.

Public Sub RaisingError
	On Error Resume Next

	debug.print 1 / 0
	Err.Clear

	debug.print 1 + 2

	If Err.Number <> 0 Then
		Debug.Print “Hier ist ein Fehler aufgetreten.”
		Debug.Print „Genauer: Fehlercode „ & Err.Number & „ Beschreibung: „ & Err.Description
	End If
End Sub

Damit sind wir mit diesem Teil schon am Ende. Wir haben gesehen dass es ein Möglichkeit gibt, die Standard-Fehlerbehandlung auszuschalten und damit die Interaktion zu unterbinden. Mit dem „On Error Resume Next“-Statement wird ein linearer Errorhandler initiiert, welche grundsätzlich einen auftretenden Fehler ignoriert und die Fehlerbehandlung in die Hände des Entwicklers legt.
Das hat den Vorteil dass sehr punktuell auf Fehler reagiert werden kann, aber auch den Nachteil dass man im Prinzip wissen muss, wann und wo ein Fehler auftreten kann. Zudem ist darauf zu achten, dass sich Fehler nach Auftreten nur mit einem Err.Clear zurücksetzt.
Bis zum nächsten Teil.

Errorhandling in VBA

Ich möchte hier mal ein Fass aufmachen und das Thema Errorhandling in VBA an Hand von Access genauer unter die Lupe nehmen. Das ist sicherlich ein komplexes Thema aber auch ein elementares da ohne ein vernünftiges Errorhandling Probleme nicht nur schwerer zu finden sind sondern vor allem weil es den negativen Seiteneffekt hat, dass Programme bei Problemen einen Runtime-Error produzieren. Das kann zu vielerlei Szenarien führen, die dann nicht mehr kontrolliert abgefangen werden können. Bsw dass Werte auf Grund des ad hoc Programmausstiegs verloren gehen, der User das aber gar nicht mitbekommt und daher in Situationen gerät, in der das Programm im freien Fall ist. Wenn all diese Unwägbarkeiten im Sourcecode kontrolliert werden sollen, kann man sich einfach vorstellen, dass sich das Programm dadurch ungeheuer aufblähen kann. Warum also nicht einfach eine funktionierende Fehlerbehandlung einsetzen und so eine Menge Probleme einfach gar nicht erst entstehen lassen.
Die Beiträge zum Thema Errorhandling werden sich auf mehrere Posts verteilen. Angefangen von den Basics bis letztendlich zu einem komplexen Errorhandler der Momentaufnahmen der Anwendung zur Fehlerzeit aufzeichnet und so auch im Nachhinein nachvollziehbar macht.

Beginnen werden wir also mit dem ersten Posting zu dem Thema, den Grundlagen. mehr dazu im Posting „Errorhandling in VBA. Teil 1: Grundlagen.“