Access JumpStart 2.0 | Blog

A Rapid Development Framework for Microsoft Access

Ok, so I got a test started up here, let’s try to continue and see where it goes:

'@TestMethod("FormListener")
Private Sub FormListenerRaisesBoundDataChangedEvent()
    FormListenerTest.Setup NewForm
    NewForm.TestText = "NewThing"

End Sub
Visual Basic

There’s what I have so far.

I’m thinking next line will need to save the record. One simple way to do that is to use this command:

NewForm.Dirty = False
Visual Basic

So now at this point the BeforeUpdate routine on the form should fire and I want to make sure that the FormListenerTest is activated and then fires off it’s own event. But perhaps before that event is fired off, I want a FormIterator to search the form for updated fields. Then perhaps I want to pass that dictionary into the new event that is raised.

So, can I run a test to listen to FormListenerTest and see what the FormIterator event returns?

I think I will have to create a test class module (not a test normal module like I have now). The test class module will listen to a formlistener class instance.

Hmm… but am I actually looking again at architecture / design here? Maybe. Perhaps ultimately I am talking about an interface here that will allow me to expose just the necessary elements on what will eventually be a “Live” class, but also allow a “Test” class to implement the interface and extend it to provide more testing capabilities to be able to return things. Ooh, I like where this is going. In fact perhaps I could extract interfaces from FormListener and/or FormIterator and perform more tests using a test version of the object which would expose the internals enough to see if they were doing what they were supposed to do.

Yes, Eureka! I will not run butt-naked through the streets though.

Ok, so let’s try having RubberDuck extract an interface from my current version of the FormListener.

Ooh, check that out. I had to refresh RubberDuck, but then it let me Right Click inside the class and choose RubberDuck->Refactor->Extract Interface.

I’ll use the default name, Implementation Options, and Instancing, and just choose the Public Setup member which is all I really need initially. The other property and methods were there for testing originally. We’ll leave them in the class but extract the interface and we get:

'@Interface

Option Explicit

Public Sub Setup(theForm As Access.Form)
End Sub
Visual Basic

Nice, then I’ll go back to my current FormListener class and implement it:

Oh my, I didn’t even have to implement it. It was already done for me! Check this out:

Option Compare Database
Option Explicit

Implements IFormListener

Private WithEvents frm As Access.Form
Private m_bBeforeUpdateTriggered As Boolean

Public Sub Setup(theForm As Access.Form)
    Set frm = theForm
    frm.BeforeUpdate = "[Event Procedure]"
End Sub

Public Property Get BeforeUpdateTriggered() As Boolean: BeforeUpdateTriggered = m_bBeforeUpdateTriggered: End Property

Public Property Let BeforeUpdateTriggered(ByVal bNewValue As Boolean): m_bBeforeUpdateTriggered = bNewValue: End Property

Private Sub frm_BeforeUpdate(Cancel As Integer)
    Me.BeforeUpdateTriggered = True
End Sub

Public Function TimesFieldChanged(theFieldName As String) As Long
    Dim retVal As Long
    retVal = 0
    TimesFieldChanged = 0
End Function

Private Sub IFormListener_Setup(theForm As Access.Form)
    Setup theForm
End Sub
Visual Basic

That was fun. And all my tests still pass. I guess I’m really in the “refactoring” phase at this point and will need to continue it a little further. I think I can leave that setup the way it is for now. I kind of find it interesting how I will be able to run the “IFormListener_Setup” sub and it will just pass it through to the Public Setup sub. This means I will see the Setup autocomplete whether I Dim the variable that will hold the class as an IFormListener or as FormListener. Interesting.

Looking forward to the next session.

Sign up For a Daily Email Adventure in Microsoft Access

Every business day (typically M-F), I'll send you an email with information about my ongoing journey as an advanced Access application developer. It will be loaded with my tips and musings.

    We won't send you spam. Unsubscribe at any time.