0
votes

In an existing mailbox folder hierarchy, there is a folder containing subfolders named "01", "05", "06", etc. Notice that the numbers are not consecutive: "02", "03", "04" are missing in this example. In my VBA code, I need to check whether a folder named, say, "02" exists and if not, create it.

I currently have (stripped to bare minimum):

Dim NameStr as String
NameStr="02"
On Error Resume Next
Set NewSubFolder = ContainerFolder.folders(NameStr)
On Error GoTo 0
If NewSubFolder Is Nothing Then
    Set NewSubFolder = ContainerFolder.folders.Add(NameStr)
End If

As long as NameStr contains an alphanumeric string, or a numbers-only string with value larger than the count of items if ContainerFolder (such as "2020"), everything works. However, if NameStr is set to "02" (or other value low enough to be interpeted as sequence number of an existing subfolder), the first set statement, instead of failing and returning Nothing, returns a pointer to the third folder (counting from zero, 02 corresponds to 3rd item) in the container folder. That would be "06" in the example above. No folder named "02" will be created.

Apparently the VBA interpreter "kindly" converts the string "02" to integer 2, and then returns pointer to the third folder. How do I prevent this behaviour? How do I force Outlook to check for existence of a folder with only digits in its name?

3
Looking further at my debug output, I am even not sure that the string "02" would be interpreted as the sequence number of the subfolder. A pointer to a seemingly-random existing subfolder seems to be returned.Toomas T
Is using the Item property helping? Set NewSubFolder = ContainerFolder.Folders.Item(NameStr) ?Vincent G
I think I had the Item() there originally and removed it just to see if it made a difference. Now added back. There wasn't any difference.Toomas T
Not really addressing the root problem, but you could create a function to which you pass the parent folder and the name of the subfolder you want to look for: the function loops over the child folders, checking the Name of each for a match, and returns the matching subfolder (or Nothing if no match).Tim Williams

3 Answers

0
votes

The result of On Error Resume Next is often non-working code. You may want to apply it as a last resort.

Option Explicit ' Consider this mandatory
' Tools | Options | Editor tab
' Require Variable Declaration
'
' If desperate declare as variant

Sub createFolder_MinimalVerifiableExample_Dangerous_OnErrorResumeNext_TheOtherWay()

Dim containerFolder As folder
Dim newSubFolder As folder

Dim nameStr As String
nameStr = "03"

Set containerFolder = Session.GetDefaultFolder(olFolderInbox)

On Error Resume Next
' Bypass error if folder exixts
Set newSubFolder = containerFolder.folders.Add(nameStr)
On Error GoTo 0

End Sub
0
votes

The Folders takes a string representing the folder name or just an index number. To be sure you will get the folder you can iterate over all subfolders and check the folder name. Following this way you can be sure you will get what you need.

0
votes

Based on niton's response as well as others' contributions, here is my solution. Instead of trying to get a pointer to the folder, and if that fails, create the folder, lets try to create the folder first, ignore the error if the folder is already there, and then get the pointer no matter whether the folder pre-existed or was newly created.

Dim containerFolder As folder
Dim newSubFolder As folder

' containerFolder needs to point to a valid folder (code not shown)
Dim nameStr As String
nameStr = "03"

On Error Resume Next
Set newSubFolder = containerFolder.folders.Add(nameStr)
On Error GoTo 0
Set newSubFolder = containerFolder.folders.Item(nameStr)

The .Item part in the last statement is optional.

Many thanks to all contributors!