When writing any VBA for Excel, Access or Word or whatever you automate you have the option to use the default settings in the VBE editor. Well one of the default that Microsoft provides is to not enforce variable declaration. This code can run just fine
Function MyNewFunction()
a = 5 * 7
MyNewFunction = a
End Function
While this is not a very useful function you'll notice that
a was used without every being declared. This often leads to a lot of problems for people. the usual things are
- They don't know when their variable went out of scope
- They don't know the data type of their variable (and consequently) there is no intellisense support for variables used like this
-
They use it in appropriately like trying to add a string to a date
the trick is to always have option explicit declared at the top of all your modules. This means that if you do not declare a variable your code will not compile.
You should have the VBE automatically put option explicit at the top of any new modules/class you make by going to Tools>Options>Editor> Require Variable Declaration = true

Now you can only write the much less sloppy
Function MyNewFunction()
Dim a as Integer
a = 5 * 7
MyNewFunction = a
End Function
Now start hitting Compile often! These two together will save you a lot of headaches.
Because you should be splitting your Access database before you give it
to a customer to use you can oftern run into the problem of your app not
finding that backend file. This is what I do to always ensure my front
end points to the right data
I generally use an AutoExec macro to apply some basic settings when
the app starts up (hiding the navigation pane, disabling full menus
maybe, minimizing the ribbon maybe). At the end of all this I check to
make sure the backend data re in place. The general process is to try to
open a record set from a table you know exists. If that succeeds then
super! you're conencted to your backend already. If that fails then you
are probably not connected and you should take some action.
Private Sub VeryifyBackendIsInPlace()
Dim rst As DAO.Recordset
Dim ITEM_NOT_FOUND_IN_COLLECTION_ERROR As Integer, FILE_NOT_FOUND_ERROR As Integer
Dim INVALID_PATH_ERROR As Integer, NETWORK_CONNECTION_ERROR As Integer
ITEM_NOT_FOUND_IN_COLLECTION_ERROR = 3265
FILE_NOT_FOUND_ERROR = 3024
INVALID_PATH_ERROR = 3044
NETWORK_CONNECTION_ERROR = 3043
On Error Resume Next
Set rst = CurrentDb.OpenRecordset("Select top 1 * from Table_I_Know_Exists")
If Err.Number = FILE_NOT_FOUND_ERROR Or Err.Number = INVALID_PATH_ERROR Then
MsgBox Err.Description & vbNewLine & "You will be prompted next to locate the data file. Without this file the database cannot open." _
, vbCritical + vbOKOnly, "Backend Data File Not Found"
GoTo FindBackEndFile
ElseIf Err.Number = NETWORK_CONNECTION_ERROR Then
If MsgBox(Err.Description & vbNewLine & "Would you like to connect to another data source", vbYesNo, "Network error") = vbYes Then
GoTo FindBackEndFile
End If
ElseIf Err.Number <> 0 Then
MsgBox Err.Description, , "Could load the data"
End If
rst.Close
On Error GoTo 0
Exit Sub
FindBackEndFile:
AttachToAnotherDataFile
End Sub
You see if we get an assortment of network/file connection issues I prompt the user to go look for the backend data file.
Public Function AttachToAnotherDataFile() As Boolean
On Error GoTo 0
Dim ofd As FileDialog
Dim result As VbMsgBoxResult
Set ofd = FileDialog(msoFileDialogFilePicker)
ofd.show
If ofd.SelectedItems.Count = 1 Then
result = RelinkLinedTablesToBackend(ofd.SelectedItems(1))
If result = vbCancel Then
AttachToAnotherDataFile = False
End If
AttachToAnotherDataFile = True
Else
AttachToAnotherDataFile = False
End If
End Function
Then I relink all the linked tables to it.
Function RelinkLinedTablesToBackend(backendPath As String) As VbMsgBoxResult
Dim tdf As TableDef
Dim db As Database
Dim tdfRefresh As TableDef
Set db = CurrentDb
For Each tdf In CurrentDb.TableDefs
If tdf.Connect <> vbNullString Then
On Error Resume Next
db.TableDefs(tdf.Name).Connect = ";DATABASE=" & backendPath
db.TableDefs(tdf.Name).RefreshLink
If Err.Number <> 0 Then
RelinkLinedTablesToBackend = MsgBox(Err.Description, vbCritical + vbRetryCancel, "Error #:" & Err.Number)
End If
'' RelinkLinedTablesToBackend = VbMsgBoxResult.vbOK
On Error GoTo 0
End If
Next
Set tdf = Nothing
Set db = Nothing
End Function
This strategy only works if all the linked tables are in the same file.
I could update it so that it only updates those linked tables which it could not conenct to.
Computer backups
I thought I should write a little about how our data are backed up because I always forget.
My desktop is backed up internally. There are 4 drives.
A 128 GB SSD which is where Windows lives (C: drive) is backed up to another internal mechanical 500 GB drive (A: drive)
A 1 TB internal data drive (J: drive) where all our "stuff" (not programs) is stored. This is backed up to another internal 1 TB drive (B: drive).
Drives A: and B: are hidden from being seen in Windows Explorer by setting the NoDrives key in the registry (HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Policies\Explorer) to 3. (A = 1) + (B = 2) = 3.

My drive setup in Disk Management
1 - The OS Backup
The OS is backed up to the A: drive through the built in Windows back up utility (File History)
Control Panel\System and Security\File History

2 - The Data Backup
Data are backed up using the Microsoft tool SyncToy. You point it to a folder (Left Folder, J:) and tell it where to sync (Right Folder, B:). It's set up to Echo which means it will
New and updated files are copied left to right. Renames and deletes on the left are repeated on the Right.
This is set up to run as a scheduled task. I named it "SyncToy Data Drives" and set it to run every Monday at 3:18 AM. It runs the following command
"C:\Program Files\SyncToy 2.1\SyncToyCmd.exe" -R "Back up new TB to old TB"

I allow it to "Run whether user is logged on or not"
This all works pretty well. Except sometimes 1. hits a glitch not recognizing the drive.

I'm not sure what the heck is going on.
Emma's laptop is also set up to back up to the 500 GB drive. There is a virtual drive created in a folder there which is mounted on her computer as a 'local drive'. This was the only way I could get Windows 7 Home (the version she has) to do network backups; trick it. I can write about that more later. It is very finicky and doesn't always reconnect.
The only off site backups we have going on are a lot of pictures backed up to Google+ and out YNAB accounts are synced to Dropbox. We should be better about that but we really don't have all that much going on with out PCs at home.
Excel allows you to create .xlsm files (macro enabled spreadsheets) but these are a bit of a hassle because whenever someone wants to open one they need to click "Enable Content". The other big issue is that any code you write is not reusable in other files. Creating an Excel Add-in means you can save commonly used functions in a central repository. They don't move with the file but they are always there for you on your computer. So, depending on your needs this might be better than an xlsm.
Note: there is another option of saving your reusable code in your Personal.xlsb file.
To make an Excel Add-in
- Open a new Excel file and Save As...
- Make the file type Excel 97-2003 Add-In (*.xla). This will change the save path to something like C:\Users\%UserName%\AppData\Roaming\Microsoft\AddIns. If you are using a new version of Excel you can also use the .xlam Excel Add-In file type)
- Make the File name something like "MyUDFs"
- Save. Close your new xla (or .xlam)
- Reopen your just made file (the VBA IDE can be finicky about what shows up and this is a good step just to ensure everything is fresh in the Project Explorer window)
- Open the VBA IDE (Alt+F11) and add a new Module
- With "VBAProject (MyUDFs.xla)" selected, Insert > Module
- Let's create an example function
Function IsFormula(rng As Range) As Boolean
IsFormula = rng.HasFormula
End Function
Whatever code you write in here will be available in your worksheets. Only functions (not subs) will show up as available worksheet functions. You can save subs in here if you want, too; they will be usable but not from a worksheet. - Save. Close.
- Open a fresh, blank Excel workbook. On the ribbon select Developer > Add-Ins
- If the developer tab is not showing for you you can make it show up by right clicking on the ribbon > Customize the Ribbon...
- When you have the Add-Ins dialog open you can select your newly minted add-in from the list.
- Now test it out!

I'll include the current contents of my MyUDFs file here for my own use and yours. I'll try to keep it updated.
I moved my Excel UDFs to GitHub so I can keep them up to date better.