DEV Community

Wild Cat
Wild Cat

Posted on • Updated on

Automate WinMerge comparison via Excel VBA Tool

Summary

Via this tool, WinMerge compares files in the specified folder including those in subfolders, and outputs the comparison results in HTML format.

The target files are those with the same name in the same folder structure.

Image description

How to use

  1. Input setting values in 'Tool' sheet in the tool.
  2. Push the button on 'Tool' sheet in the tool.
  3. WinMerge exports comparison results in HTML format.

Setting

Image description

Source code

'********************************************************************
'[Summary]
' Via this tool, WinMerge compare files in the specified folder
' including those in subfolders, and output the comparison results
' in HTML format.
' The target files are those with the same name in the same
' folder structure.
'********************************************************************

Option Explicit

'Declare Sleep Function
Declare PtrSafe Sub Sleep Lib "kernel32" (ByVal MilliSecounds As LongPtr)

'Declare a FileSystemObject variable as a module-level variable.
Dim FSO As Object

'********************************************************************
'[Summary]
' Main Procedure
' 1.Input Check
' 2.Execute WinMerge
'********************************************************************
Sub ExportWinMergeReport()

    Dim startTime As Date: startTime = Now

    'Assign setting values to variables
        With ThisWorkbook.Sheets("Tool")

            Dim inputFolderPath1 As String 'Source folder 1
            Dim inputFolderPath2 As String 'Source folder 2
            Dim outputFolderPath As String 'Destination folder
            Dim filePathWinMerge As String 'WinMerge EXE file

            inputFolderPath1 = .Range("B2").Value
            inputFolderPath2 = .Range("B3").Value
            outputFolderPath = .Range("B4").Value
            filePathWinMerge = .Range("B5").Value

        End With

    'Validate input values
        Call ValidateInputValues(inputFolderPath1, inputFolderPath2, outputFolderPath, filePathWinMerge)

    'Execute WinMerge
        Call ExecWinMerge(inputFolderPath1, inputFolderPath2, outputFolderPath, filePathWinMerge)

        Set FSO = Nothing

    'Completion Message
    MsgBox "Completed" & vbLf & "Time " & Format(Now - startTime, "hh:mm:ss"), vbInformation

End Sub

'********************************************************************
'[Summary]
' Sub procedure to validate input values
'
'[Argument]
' inputFolderPath1 : Source folder 1
' inputFolderPath2 : Source folder 2
' outputFolderPath : Destination folder
' filePathWinMerge : WinMerge EXE file
'********************************************************************
Sub ValidateInputValues(ByVal inputFolderPath1 As String, _
                        ByVal inputFolderPath2 As String, _
                        ByVal outputFolderPath As String, _
                        ByVal filePathWinMerge As String)

    'Validate that values are entered in each field
        If inputFolderPath1 = "" Then
            MsgBox "The first source folder is not entered in the input field.", vbInformation
            End
        End If

        If inputFolderPath2 = "" Then
            MsgBox "The second source folder is not entered in the input field.", vbInformation
            End
        End If

        If outputFolderPath = "" Then
            MsgBox "The output folder is not entered in the input field.", vbInformation
            End
        End If

        If filePathWinMerge = "" Then
            MsgBox "The file Path of WinMerge EXE file is not entered in the input field.", vbInformation
            End
        End If

    'Validate that folders and files exist
        Set FSO = CreateObject("Scripting.FileSystemObject")

        If Not FSO.FolderExists(inputFolderPath1) Then
            MsgBox "The first source folder doesn't exit.", vbInformation
            Set FSO = Nothing
            End
        End If

        If Not FSO.FolderExists(inputFolderPath2) Then
            MsgBox "The second source folder doesn't exit.", vbInformation
            Set FSO = Nothing
            End
        End If

        If Not FSO.FileExists(filePathWinMerge) Then
            MsgBox "WinMerge EXE file doesn't exist", vbInformation
            Set FSO = Nothing
            End
        End If

End Sub

'********************************************************************
'[Summary]
' Sub procedure to execute WinMerge
'
'[Argument]
' inputFolderPath1 : Source folder 1
' inputFolderPath2 : Source folder 2
' outputFolderPath : Destination folder
' filePathWinMerge : WinMerge EXE file
'********************************************************************
Sub ExecWinMerge(ByVal inputFolderPath1 As String, _
                 ByVal inputFolderPath2 As String, _
                 ByVal outputFolderPath As String, _
                 ByVal filePathWinMerge As String)

    Dim inputFilePath1 As String
    Dim inputFilePath2 As String
    Dim outputFilePath As String
    Dim exeCode As String
    Dim oFile As Object
    Dim exeTimeLimit As Date
    Dim canContinue As Boolean
    Dim exeResult As Long

    'Create the folder to export results of WinMerge
    If Not FSO.FolderExists(outputFolderPath) Then
        FSO.CreateFolder (outputFolderPath)
    End If

    'Execute WinMerge
    For Each oFile In FSO.GetFolder(inputFolderPath1).Files

        'Check for the existence of the comparison target file.
        'If the same file exists, execute WinMerge.
        If FSO.FileExists(inputFolderPath2 & "\" & oFile.Name) Then

            inputFilePath1 = inputFolderPath1 & "\" & oFile.Name
            inputFilePath2 = inputFolderPath2 & "\" & oFile.Name
            outputFilePath = outputFolderPath & "\" & FSO.GetBaseName(oFile) & ".htm"

            exeCode = filePathWinMerge & " " & _
                      inputFilePath1 & " " & _
                      inputFilePath2 & _
                      " /or " & outputFilePath & _
                      " /noninteractive /minimize /xq /e /u"

            exeResult = Shell(exeCode, vbMinimizedNoFocus)

            If exeResult = 0 Then
                MsgBox "Failed to execute WinMerge.", vbInformation
                Set FSO = Nothing
                End
            End If

            'Wait for the output of the comparison result.
            'Maximum time is 10 secounds.
                exeTimeLimit = Now + TimeSerial(0, 0, 10)
                canContinue = False

                Do
                    If FSO.FileExists(outputFilePath) Then
                        canContinue = True
                        Exit Do
                    End If
                    Call Sleep(100) 'Wait 100 milliseconds
                Loop Until canContinue Or Now > exeTimeLimit

                If Not canContinue Then
                    MsgBox "Failed to output the following report file." & vbLf & vbLf & outputFilePath, vbInformation
                    Set FSO = Nothing
                    End
                End If

        End If

    Next

    'Execute WinMerge for subfolders as well.
    Dim subfolder As Object
    Dim subInputFolderPath1 As String
    Dim subInputFolderPath2 As String
    Dim subOutputFolderPath As String

    For Each subfolder In FSO.GetFolder(inputFolderPath1).Subfolders

        'If a subfolder exists, execute recursive processing.
        If subfolder.Name <> "" Then
            subInputFolderPath1 = subfolder.Path
            subInputFolderPath2 = inputFolderPath2 & "\" & subfolder.Name
            subOutputFolderPath = outputFolderPath & "\" & subfolder.Name
            Call ExecWinMerge(subInputFolderPath1, subInputFolderPath2, subOutputFolderPath, filePathWinMerge)
        End If

    Next

End Sub
Enter fullscreen mode Exit fullscreen mode

Command line parameters of WinMerge

The following are the command line parameters of WinMerge used in this tool.

/or
Specifies an optional output folder to save comparison result files.

/noninteractive
Exits WinMerge after the process is completed.

/minimize
Starts WinMerge as a minimized window.

/xq
Does not show the message about identical files.

/e
Enables you to close WinMerge with a single Esc key press.

/u
Prevents WinMerge from adding either path to the Most Recently Used list.

Top comments (0)