VBA to copy only matching data from 2 csv workbooks into the "MasterCSV"

DCFreit0s

New Member
Joined
Jul 23, 2024
Messages
11
Office Version
  1. 365
  2. 2016
Platform
  1. Windows
  2. MacOS
I have 3 sample csv files and I want to open/select 2 of the files and copy only the matching data between them into a third Master csv... I have included pictures of the 3 csv files with random data & timestamps. I am new to VBA so my code prolly isn't great but...

1. MasterCSV = the csv i want to copy the data into
2. Target_Time = the csv i want to use to match data (timestamp) against
3. Import_Data = the csv i want to copy the row data from if it matches the timestamp in Target_Time.

  1. So I want the Macro to allow me to select the Target_Time csv & Import_Data csv - these will be a new csv file for each day (24hr period)
  2. Then I want to select the rows of the Import_Data csv that have a timestamp (Column A in both csv's) matching with the timestamps of the Target_Time cvs.
  3. Finally, i want to import ONLY those rows from the Import_Data csv into the MasterCSV.
  4. I have some code already in my macro to adjust the timestamp cells into a "Date" and "Time" column so the copied rows need to start on column 3 of the MasterCSV.
  5. Finally I would like to create another macro (to use with another button) that saves the MasterCSV with the "date" of the cells in column A (which should all be the same since it's all data from a 24hr period).
PLEASE HELP!!! Ive been googling and testing different codes for days!!!

VBA Code:
Sub ImportData()
    Dim ImportFile As String
    Dim TargetFile As String
    Dim MyDateTime As Date
    Dim TargetColumn As Range
    
    TargetFile = Application.GetOpenFilename
    If TargetFile = "False" Then
        Exit Sub
    End If
    Set TargetWorkbook = Workbooks.Open(filename:=TargetFile)
    
    
    ImportFile = Application.GetOpenFilename
    If ImportFile = "False" Then
        Exit Sub
    End If
    
    Application.ScreenUpdating = False
    'Set the source and target sheets
    Set ImportWorkbook = Workbooks.Open(filename:=ImportFile)
    Set MasterSheet = ThisWorkbook.Worksheets("Data")
    Set TargetColumn = TargetWorkbook.Worksheets(1).Range("A2:A")
    
    'Find the last row in the source sheet
    lastRow = ImportWorkbook.Worksheets(1).Cells(ImportWorkbook.Worksheets(1).Rows.Count, "A").End(xlUp).Row
    'Find the last row in the Target Sheet
    TargetDTRow = TargetWorkbook.Worksheets(1).Cells(TargetWorkbook.Worksheets(1).Rows.Count, "A").End(xlUp).Row
    'Find the last row in the master sheet
    MasterLastRow = MasterSheet.Cells(MasterSheet.Rows.Count, "A").End(xlUp).Row
    
    
    'Loop through each row in the source sheet
    For i = 2 To lastRow
    'Check if cell in column A contains "Target Date/Time"
    If ImportWorkbook.Cells(i, "A").Values = TargetColumn Then
    'Copy the entire row to the target sheet
    ImportWorkbook.Rows("Bi:B").Copy Destination:=MasterSheet.Range("C, MasterLastRow")
    
    MyDateTime = ImportWorkbook.Worksheets(1).Range("A2").Value

    'get date
    ThisWorkbook.Worksheets(2).Range("A3").Value = Int(MyDateTime)
    ThisWorkbook.Worksheets(2).Range("A3").NumberFormat = "YYYY-MM-DD"

    'get time
    ThisWorkbook.Worksheets(2).Range("B3").Value = MyDateTime - Int(MyDateTime)
    ThisWorkbook.Worksheets(2).Range("B3").NumberFormat = "hh:mm:ss"
    
    ImportWorkbook.Close
    Application.ScreenUpdating = True
    End If
    Next i
End Sub
 

Attachments

  • Target_Time_CSV.png
    Target_Time_CSV.png
    33.2 KB · Views: 35
  • Import_Data_CSV.png
    Import_Data_CSV.png
    55.2 KB · Views: 29
  • MasterCSV.png
    MasterCSV.png
    48.5 KB · Views: 30
Well it's a bit of a mystery but try this updated code.

VBA Code:
Sub ImportData()
    Dim Flag As Boolean
    Dim fileNumTarget As Integer, fileNumImport As Integer, fileNumMaster As Integer
    Dim ImportFile As String
    Dim TargetFile As String
    Dim txtLineImport As String, txtLineTarget As String, txtLineOutput As String
    Dim fdate As String, fday As String, fmonth As String, fyear As String, ftime As String
    TargetFile = Application.GetOpenFilename(, , "Target file")
    ImportFile = Application.GetOpenFilename(, , "Import file")
    fileNumTarget = FreeFile
    Open TargetFile For Input As #fileNumTarget
    fileNumImport = FreeFile
    '
    ' Throw away the first line of each file
    '
    Line Input #fileNumTarget, txtLineTarget
    While Not EOF(fileNumTarget)
        Line Input #fileNumTarget, txtLineTarget
        Open ImportFile For Input As #fileNumImport
    Line Input #fileNumImport, txtLineImport
        While Not EOF(fileNumImport)
            Line Input #fileNumImport, txtLineImport
            If Left(txtLineImport, Len(txtLineTarget)) = txtLineTarget Then
                If Not Flag Then
                    fyear = Mid(Trim(txtLineTarget), 7, 4)
                    fmonth = Left(Trim(txtLineTarget), 2)
                    fday = Mid(Trim(txtLineTarget), 4, 2)
                    fdate = fyear & fmonth & fday
                    fileNumMaster = FreeFile
                    Open "Master" & fdate & ".csv" For Output As #fileNumMaster
                    Flag = True
                End If
                fdate = fyear & "-" & fmonth & "-" & fday
                ftime = Mid(Trim(txtLineTarget), 12, 8)
                txtLineOutput = fdate & ", " & ftime & ", " & _
                        Mid(txtLineImport, InStr(1, txtLineImport, ",") + 1)
                Print #fileNumMaster, txtLineOutput
            End If
        Wend
        Close #fileNumImport
    Wend
    Close
End Sub
I only got 1 error with that updated code and of course it's a different error. It said path not found and highlighted the line shown in the attached image. Also, just a side note. I was able to get a windows computer running Microsoft Office 365 so we shouldnt have to worry about any differences there.
 

Attachments

  • error 3 debug.png
    error 3 debug.png
    76.9 KB · Views: 7
Upvote 0

Excel Facts

Quick Sum
Select a range of cells. The total appears in bottom right of Excel screen. Right-click total to add Max, Min, Count, Average.
That's odd because we've never provided a path to the output file - only the file name itself.

Can you rerun this modified code and tell me what it reports as the value of fdate, and also can you advise the error number it gives when it errors.
VBA Code:
Sub ImportData()
    Dim Flag As Boolean
    Dim fileNumTarget As Integer, fileNumImport As Integer, fileNumMaster As Integer
    Dim ImportFile As String
    Dim TargetFile As String
    Dim txtLineImport As String, txtLineTarget As String, txtLineOutput As String
    Dim fdate As String, fday As String, fmonth As String, fyear As String, ftime As String
    TargetFile = Application.GetOpenFilename(, , "Target file")
    ImportFile = Application.GetOpenFilename(, , "Import file")
    fileNumTarget = FreeFile
    Open TargetFile For Input As #fileNumTarget
    fileNumImport = FreeFile
    '
    ' Throw away the first line of each file
    '
    Line Input #fileNumTarget, txtLineTarget
    While Not EOF(fileNumTarget)
        Line Input #fileNumTarget, txtLineTarget
        Open ImportFile For Input As #fileNumImport
    Line Input #fileNumImport, txtLineImport
        While Not EOF(fileNumImport)
            Line Input #fileNumImport, txtLineImport
            If Left(txtLineImport, Len(txtLineTarget)) = txtLineTarget Then
                If Not Flag Then
                    fyear = Mid(Trim(txtLineTarget), 7, 4)
                    fmonth = Left(Trim(txtLineTarget), 2)
                    fday = Mid(Trim(txtLineTarget), 4, 2)
                    fdate = fyear & fmonth & fday
                    msgbox "Value of fdate is " & fdate
                    fileNumMaster = FreeFile
                    Open "Master" & fdate & ".csv" For Output As #fileNumMaster
                    Flag = True
                End If
                fdate = fyear & "-" & fmonth & "-" & fday
                ftime = Mid(Trim(txtLineTarget), 12, 8)
                txtLineOutput = fdate & ", " & ftime & ", " & _
                        Mid(txtLineImport, InStr(1, txtLineImport, ",") + 1)
                Print #fileNumMaster, txtLineOutput
            End If
        Wend
        Close #fileNumImport
    Wend
    Close
End Sub
 
Upvote 0
That's odd because we've never provided a path to the output file - only the file name itself.

Can you rerun this modified code and tell me what it reports as the value of fdate, and also can you advise the error number it gives when it errors.
VBA Code:
Sub ImportData()
    Dim Flag As Boolean
    Dim fileNumTarget As Integer, fileNumImport As Integer, fileNumMaster As Integer
    Dim ImportFile As String
    Dim TargetFile As String
    Dim txtLineImport As String, txtLineTarget As String, txtLineOutput As String
    Dim fdate As String, fday As String, fmonth As String, fyear As String, ftime As String
    TargetFile = Application.GetOpenFilename(, , "Target file")
    ImportFile = Application.GetOpenFilename(, , "Import file")
    fileNumTarget = FreeFile
    Open TargetFile For Input As #fileNumTarget
    fileNumImport = FreeFile
    '
    ' Throw away the first line of each file
    '
    Line Input #fileNumTarget, txtLineTarget
    While Not EOF(fileNumTarget)
        Line Input #fileNumTarget, txtLineTarget
        Open ImportFile For Input As #fileNumImport
    Line Input #fileNumImport, txtLineImport
        While Not EOF(fileNumImport)
            Line Input #fileNumImport, txtLineImport
            If Left(txtLineImport, Len(txtLineTarget)) = txtLineTarget Then
                If Not Flag Then
                    fyear = Mid(Trim(txtLineTarget), 7, 4)
                    fmonth = Left(Trim(txtLineTarget), 2)
                    fday = Mid(Trim(txtLineTarget), 4, 2)
                    fdate = fyear & fmonth & fday
                    msgbox "Value of fdate is " & fdate
                    fileNumMaster = FreeFile
                    Open "Master" & fdate & ".csv" For Output As #fileNumMaster
                    Flag = True
                End If
                fdate = fyear & "-" & fmonth & "-" & fday
                ftime = Mid(Trim(txtLineTarget), 12, 8)
                txtLineOutput = fdate & ", " & ftime & ", " & _
                        Mid(txtLineImport, InStr(1, txtLineImport, ",") + 1)
                Print #fileNumMaster, txtLineOutput
            End If
        Wend
        Close #fileNumImport
    Wend
    Close
End Sub
The message gave this for a value of fdate.
 

Attachments

  • fdate value.png
    fdate value.png
    7.5 KB · Views: 7
Upvote 0
Yeah that was never going to work was it! It's hard working blind.

Try this then:

VBA Code:
Sub ImportData()
    Dim Flag As Boolean
    Dim fileNumTarget As Integer, fileNumImport As Integer, fileNumMaster As Integer, spos As Integer
    Dim ImportFile As String, TargetFile As String
    Dim txtLineImport As String, txtLineTarget As String, txtLineOutput As String
    Dim fdate As String, fdate2 As String, ftime As String
    TargetFile = Application.GetOpenFilename(, , "Target file")
    ImportFile = Application.GetOpenFilename(, , "Import file")
    fileNumTarget = FreeFile
    Open TargetFile For Input As #fileNumTarget
    fileNumImport = FreeFile
    '
    ' Throw away the first line of each file
    '
    Line Input #fileNumTarget, txtLineTarget
    While Not EOF(fileNumTarget)
        Line Input #fileNumTarget, txtLineTarget
        Open ImportFile For Input As #fileNumImport
    Line Input #fileNumImport, txtLineImport
        While Not EOF(fileNumImport)
            Line Input #fileNumImport, txtLineImport
            If Left(txtLineImport, Len(txtLineTarget)) = txtLineTarget Then
                If Not Flag Then
                    spos = InStr(1, Trim(txtLineTarget), " ") - 1
                    fdate = Format(Left(Trim(txtLineTarget), spos), "YYYYMMDD")
                    fileNumMaster = FreeFile
                    Open "Master" & fdate & ".csv" For Output As #fileNumMaster
                    Flag = True
                End If
                spos = InStr(1, Trim(txtLineTarget), " ") - 1
                fdate2 = Format(Left(Trim(txtLineTarget), spos), "YYYY-MM-DD")
                ftime = Mid(Trim(txtLineTarget), spos + 2, 8)
                txtLineOutput = fdate & ", " & ftime & ", " & _
                        Mid(txtLineImport, InStr(1, txtLineImport, ",") + 1)
                Print #fileNumMaster, txtLineOutput
            End If
        Wend
        Close #fileNumImport
    Wend
    Close
    MsgBox "Finished"
End Sub
 
Upvote 0
Solution
Yeah that was never going to work was it! It's hard working blind.

Try this then:

VBA Code:
Sub ImportData()
    Dim Flag As Boolean
    Dim fileNumTarget As Integer, fileNumImport As Integer, fileNumMaster As Integer, spos As Integer
    Dim ImportFile As String, TargetFile As String
    Dim txtLineImport As String, txtLineTarget As String, txtLineOutput As String
    Dim fdate As String, fdate2 As String, ftime As String
    TargetFile = Application.GetOpenFilename(, , "Target file")
    ImportFile = Application.GetOpenFilename(, , "Import file")
    fileNumTarget = FreeFile
    Open TargetFile For Input As #fileNumTarget
    fileNumImport = FreeFile
    '
    ' Throw away the first line of each file
    '
    Line Input #fileNumTarget, txtLineTarget
    While Not EOF(fileNumTarget)
        Line Input #fileNumTarget, txtLineTarget
        Open ImportFile For Input As #fileNumImport
    Line Input #fileNumImport, txtLineImport
        While Not EOF(fileNumImport)
            Line Input #fileNumImport, txtLineImport
            If Left(txtLineImport, Len(txtLineTarget)) = txtLineTarget Then
                If Not Flag Then
                    spos = InStr(1, Trim(txtLineTarget), " ") - 1
                    fdate = Format(Left(Trim(txtLineTarget), spos), "YYYYMMDD")
                    fileNumMaster = FreeFile
                    Open "Master" & fdate & ".csv" For Output As #fileNumMaster
                    Flag = True
                End If
                spos = InStr(1, Trim(txtLineTarget), " ") - 1
                fdate2 = Format(Left(Trim(txtLineTarget), spos), "YYYY-MM-DD")
                ftime = Mid(Trim(txtLineTarget), spos + 2, 8)
                txtLineOutput = fdate & ", " & ftime & ", " & _
                        Mid(txtLineImport, InStr(1, txtLineImport, ",") + 1)
                Print #fileNumMaster, txtLineOutput
            End If
        Wend
        Close #fileNumImport
    Wend
    Close
    MsgBox "Finished"
End Sub
That worked great! Thank you so much; this had been driving me mad for the lat 2 weeks! I added a few little things...

1. The time had lost the "seconds" for some reason
2. Added a different filename, an "_", and "-" in the date of the cvs export

I did notice that whenever I run the Macro it saves/exports the new csv, but also "re-saves" the "MasterWB" as well... Is it supposed to?

My plan is to use this AWESOME code you gave me as one button in the "MasterWB" (which is a .xlsm), and then have a second button to import the data from the new csv into the xlsm (which has all the proper headers, formating, and formulas (on other sheets).
- If I use the "MasterWB" to do this... will the data from previous "runs" of the macro be overwritten when the macro "re-saves" the MasterWB on each run?
 
Upvote 0
That worked great! Thank you so much; this had been driving me mad for the lat 2 weeks! I added a few little things...

1. The time had lost the "seconds" for some reason
2. Added a different filename, an "_", and "-" in the date of the cvs export

I did notice that whenever I run the Macro it saves/exports the new csv, but also "re-saves" the "MasterWB" as well... Is it supposed to?

My plan is to use this AWESOME code you gave me as one button in the "MasterWB" (which is a .xlsm), and then have a second button to import the data from the new csv into the xlsm (which has all the proper headers, formating, and formulas (on other sheets).
- If I use the "MasterWB" to do this... will the data from previous "runs" of the macro be overwritten when the macro "re-saves" the MasterWB on each run?
Sorry I forgot to add the code...

VBA Code:
Sub ImportData()
    Dim Flag As Boolean
    Dim fileNumTarget As Integer, fileNumImport As Integer, fileNumMaster As Integer, stringpos As Integer
    Dim ImportFile As String, TargetFile As String
    Dim txtLineImport As String, txtLineTarget As String, txtLineOutput As String
    Dim fdate As String, fdate2 As String, ftime As String
    Dim OutFileName As String
    Set MasterWB = ActiveWorkbook
    
    TargetFile = Application.GetOpenFilename(, , "Target file")
    ImportFile = Application.GetOpenFilename(, , "Import file")
    fileNumTarget = FreeFile
    Open TargetFile For Input As #fileNumTarget
    fileNumImport = FreeFile
    OutputFileName = Left(MasterWB.Name, InStrRev(MasterWB.Name, ".") - 1)
    
    Line Input #fileNumTarget, txtLineTarget
    While Not EOF(fileNumTarget)
        Line Input #fileNumTarget, txtLineTarget
        Open ImportFile For Input As #fileNumImport
    Line Input #fileNumImport, txtLineImport
        While Not EOF(fileNumImport)
            Line Input #fileNumImport, txtLineImport
            If Left(txtLineImport, Len(txtLineTarget)) = txtLineTarget Then
                If Not Flag Then
                    stringpos = InStr(1, Trim(txtLineTarget), " ") - 1
                    fdate = Format(Left(Trim(txtLineTarget), stringpos), "YYYYMMDD")
                    fileNumMaster = FreeFile
                    Open "IMPORT" & "_" & OutputFileName & "_" & fdate & ".csv" For Output As #fileNumMaster
                    Flag = True
                End If
                stringpos = InStr(1, Trim(txtLineTarget), " ") - 1
                fdate2 = Format(Left(Trim(txtLineTarget), stringpos), "YYYY-MM-DD")
                ftime = Format(Mid(Trim(txtLineTarget), stringpos + 2, 8), "HH:MM:SS")
                txtLineOutput = fdate & ", " & ftime & ", " & _
                        Mid(txtLineImport, InStr(1, txtLineImport, ",") + 1)
                Print #fileNumMaster, txtLineOutput
            End If
        Wend
        Close #fileNumImport
    Wend
    Close
    MsgBox "Finished"
End Sub
 
Upvote 0
Never mind my last reply... it wont make a difference because the appended date to the end of the filename will change from day to day.

Again, i cant thank you enough for all you help! I was going a bit mad trying to figure this out! I added a few more things to prompt for a file path for the output file. Here is my final code working and wonderful!!! (Thanks to you!)

VBA Code:
Sub ImportData()
    Dim Flag As Boolean
    Dim fileNumTarget As Integer, fileNumImport As Integer, fileNumMaster As Integer, stringpos As Integer
    Dim ImportFile As String, TargetFile As String
    Dim txtLineImport As String, txtLineTarget As String, txtLineOutput As String
    Dim fdate As String, fdate2 As String, ftime As String
    Dim OutFileName As String
    Set MasterWB = ActiveWorkbook
    
    TargetFile = Application.GetOpenFilename(, , "Target file")
    ImportFile = Application.GetOpenFilename(, , "Import file")
    fileNumTarget = FreeFile
    Open TargetFile For Input As #fileNumTarget
    fileNumImport = FreeFile
    OutputFileName = Left(MasterWB.Name, InStrRev(MasterWB.Name, ".") - 1)

    
    Line Input #fileNumTarget, txtLineTarget
    While Not EOF(fileNumTarget)
        Line Input #fileNumTarget, txtLineTarget
        Open ImportFile For Input As #fileNumImport
    Line Input #fileNumImport, txtLineImport
        While Not EOF(fileNumImport)
            Line Input #fileNumImport, txtLineImport
            If Left(txtLineImport, Len(txtLineTarget)) = txtLineTarget Then
                If Not Flag Then
                    stringpos = InStr(1, Trim(txtLineTarget), " ") - 1
                    fdate = Format(Left(Trim(txtLineTarget), stringpos), "YYYYMMDD")
                    fileNumMaster = FreeFile
                    FilePath = ExportFilePath
                    OutPutFilePath = FilePath & "\" & "IMPORT" & "_" & OutputFileName & "_" & fdate & ".csv"
                    Open OutPutFilePath For Output As #fileNumMaster
                    Flag = True
                End If
                stringpos = InStr(1, Trim(txtLineTarget), " ") - 1
                fdate2 = Format(Left(Trim(txtLineTarget), stringpos), "YYYY-MM-DD")
                ftime = Format(Mid(Trim(txtLineTarget), stringpos + 2, 8), "HH:MM:SS")
                txtLineOutput = fdate & ", " & ftime & ", " & _
                        Mid(txtLineImport, InStr(1, txtLineImport, ",") + 1)
                Print #fileNumMaster, txtLineOutput
            End If
        Wend
        Close #fileNumImport
    Wend
    Close
    MsgBox "Finished"
End Sub
 
Upvote 0

Forum statistics

Threads
1,224,732
Messages
6,180,625
Members
452,991
Latest member
JM_000888

We've detected that you are using an adblocker.

We have a great community of people providing Excel help here, but the hosting costs are enormous. You can help keep this site running by allowing ads on MrExcel.com.
Allow Ads at MrExcel

Which adblocker are you using?

Disable AdBlock

Follow these easy steps to disable AdBlock

1)Click on the icon in the browser’s toolbar.
2)Click on the icon in the browser’s toolbar.
2)Click on the "Pause on this site" option.
Go back

Disable AdBlock Plus

Follow these easy steps to disable AdBlock Plus

1)Click on the icon in the browser’s toolbar.
2)Click on the toggle to disable it for "mrexcel.com".
Go back

Disable uBlock Origin

Follow these easy steps to disable uBlock Origin

1)Click on the icon in the browser’s toolbar.
2)Click on the "Power" button.
3)Click on the "Refresh" button.
Go back

Disable uBlock

Follow these easy steps to disable uBlock

1)Click on the icon in the browser’s toolbar.
2)Click on the "Power" button.
3)Click on the "Refresh" button.
Go back
Back
Top